ActivityManagerService.java revision c7c04890beaf459808aeecb7418913939abbd169
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.service.voice.IVoiceInteractionSession; 52import android.util.ArrayMap; 53import android.util.ArraySet; 54import android.util.SparseIntArray; 55 56import com.android.internal.R; 57import com.android.internal.annotations.GuardedBy; 58import com.android.internal.app.IAppOpsService; 59import com.android.internal.app.IVoiceInteractor; 60import com.android.internal.app.ProcessMap; 61import com.android.internal.app.ProcessStats; 62import com.android.internal.content.PackageMonitor; 63import com.android.internal.os.BackgroundThread; 64import com.android.internal.os.BatteryStatsImpl; 65import com.android.internal.os.ProcessCpuTracker; 66import com.android.internal.os.TransferPipe; 67import com.android.internal.os.Zygote; 68import com.android.internal.util.FastPrintWriter; 69import com.android.internal.util.FastXmlSerializer; 70import com.android.internal.util.MemInfoReader; 71import com.android.internal.util.Preconditions; 72import com.android.server.AppOpsService; 73import com.android.server.AttributeCache; 74import com.android.server.IntentResolver; 75import com.android.server.LocalServices; 76import com.android.server.ServiceThread; 77import com.android.server.SystemService; 78import com.android.server.SystemServiceManager; 79import com.android.server.Watchdog; 80import com.android.server.am.ActivityStack.ActivityState; 81import com.android.server.firewall.IntentFirewall; 82import com.android.server.pm.UserManagerService; 83import com.android.server.wm.AppTransition; 84import com.android.server.wm.WindowManagerService; 85import com.google.android.collect.Lists; 86import com.google.android.collect.Maps; 87 88import libcore.io.IoUtils; 89 90import org.xmlpull.v1.XmlPullParser; 91import org.xmlpull.v1.XmlPullParserException; 92import org.xmlpull.v1.XmlSerializer; 93 94import android.app.Activity; 95import android.app.ActivityManager; 96import android.app.ActivityManager.RunningTaskInfo; 97import android.app.ActivityManager.StackInfo; 98import android.app.ActivityManagerInternal; 99import android.app.ActivityManagerNative; 100import android.app.ActivityOptions; 101import android.app.ActivityThread; 102import android.app.AlertDialog; 103import android.app.AppGlobals; 104import android.app.ApplicationErrorReport; 105import android.app.Dialog; 106import android.app.IActivityController; 107import android.app.IApplicationThread; 108import android.app.IInstrumentationWatcher; 109import android.app.INotificationManager; 110import android.app.IProcessObserver; 111import android.app.IServiceConnection; 112import android.app.IStopUserCallback; 113import android.app.IUiAutomationConnection; 114import android.app.IUserSwitchObserver; 115import android.app.Instrumentation; 116import android.app.Notification; 117import android.app.NotificationManager; 118import android.app.PendingIntent; 119import android.app.backup.IBackupManager; 120import android.content.ActivityNotFoundException; 121import android.content.BroadcastReceiver; 122import android.content.ClipData; 123import android.content.ComponentCallbacks2; 124import android.content.ComponentName; 125import android.content.ContentProvider; 126import android.content.ContentResolver; 127import android.content.Context; 128import android.content.DialogInterface; 129import android.content.IContentProvider; 130import android.content.IIntentReceiver; 131import android.content.IIntentSender; 132import android.content.Intent; 133import android.content.IntentFilter; 134import android.content.IntentSender; 135import android.content.pm.ActivityInfo; 136import android.content.pm.ApplicationInfo; 137import android.content.pm.ConfigurationInfo; 138import android.content.pm.IPackageDataObserver; 139import android.content.pm.IPackageManager; 140import android.content.pm.InstrumentationInfo; 141import android.content.pm.PackageInfo; 142import android.content.pm.PackageManager; 143import android.content.pm.ParceledListSlice; 144import android.content.pm.UserInfo; 145import android.content.pm.PackageManager.NameNotFoundException; 146import android.content.pm.PathPermission; 147import android.content.pm.ProviderInfo; 148import android.content.pm.ResolveInfo; 149import android.content.pm.ServiceInfo; 150import android.content.res.CompatibilityInfo; 151import android.content.res.Configuration; 152import android.net.Proxy; 153import android.net.ProxyInfo; 154import android.net.Uri; 155import android.os.Binder; 156import android.os.Build; 157import android.os.Bundle; 158import android.os.Debug; 159import android.os.DropBoxManager; 160import android.os.Environment; 161import android.os.FactoryTest; 162import android.os.FileObserver; 163import android.os.FileUtils; 164import android.os.Handler; 165import android.os.IBinder; 166import android.os.IPermissionController; 167import android.os.IRemoteCallback; 168import android.os.IUserManager; 169import android.os.Looper; 170import android.os.Message; 171import android.os.Parcel; 172import android.os.ParcelFileDescriptor; 173import android.os.Process; 174import android.os.RemoteCallbackList; 175import android.os.RemoteException; 176import android.os.SELinux; 177import android.os.ServiceManager; 178import android.os.StrictMode; 179import android.os.SystemClock; 180import android.os.SystemProperties; 181import android.os.UpdateLock; 182import android.os.UserHandle; 183import android.provider.Settings; 184import android.text.format.DateUtils; 185import android.text.format.Time; 186import android.util.AtomicFile; 187import android.util.EventLog; 188import android.util.Log; 189import android.util.Pair; 190import android.util.PrintWriterPrinter; 191import android.util.Slog; 192import android.util.SparseArray; 193import android.util.TimeUtils; 194import android.util.Xml; 195import android.view.Gravity; 196import android.view.LayoutInflater; 197import android.view.View; 198import android.view.WindowManager; 199import dalvik.system.VMRuntime; 200 201import java.io.BufferedInputStream; 202import java.io.BufferedOutputStream; 203import java.io.DataInputStream; 204import java.io.DataOutputStream; 205import java.io.File; 206import java.io.FileDescriptor; 207import java.io.FileInputStream; 208import java.io.FileNotFoundException; 209import java.io.FileOutputStream; 210import java.io.IOException; 211import java.io.InputStreamReader; 212import java.io.PrintWriter; 213import java.io.StringWriter; 214import java.lang.ref.WeakReference; 215import java.util.ArrayList; 216import java.util.Arrays; 217import java.util.Collections; 218import java.util.Comparator; 219import java.util.HashMap; 220import java.util.HashSet; 221import java.util.Iterator; 222import java.util.List; 223import java.util.Locale; 224import java.util.Map; 225import java.util.Set; 226import java.util.concurrent.atomic.AtomicBoolean; 227import java.util.concurrent.atomic.AtomicLong; 228 229public final class ActivityManagerService extends ActivityManagerNative 230 implements Watchdog.Monitor, BatteryStatsImpl.BatteryCallback { 231 232 private static final String USER_DATA_DIR = "/data/user/"; 233 // File that stores last updated system version and called preboot receivers 234 static final String CALLED_PRE_BOOTS_FILENAME = "called_pre_boots.dat"; 235 236 static final String TAG = "ActivityManager"; 237 static final String TAG_MU = "ActivityManagerServiceMU"; 238 static final boolean DEBUG = false; 239 static final boolean localLOGV = DEBUG; 240 static final boolean DEBUG_BACKUP = localLOGV || false; 241 static final boolean DEBUG_BROADCAST = localLOGV || false; 242 static final boolean DEBUG_BROADCAST_LIGHT = DEBUG_BROADCAST || false; 243 static final boolean DEBUG_BACKGROUND_BROADCAST = DEBUG_BROADCAST || false; 244 static final boolean DEBUG_CLEANUP = localLOGV || false; 245 static final boolean DEBUG_CONFIGURATION = localLOGV || false; 246 static final boolean DEBUG_FOCUS = false; 247 static final boolean DEBUG_IMMERSIVE = localLOGV || false; 248 static final boolean DEBUG_MU = localLOGV || false; 249 static final boolean DEBUG_OOM_ADJ = localLOGV || false; 250 static final boolean DEBUG_LRU = localLOGV || false; 251 static final boolean DEBUG_PAUSE = localLOGV || false; 252 static final boolean DEBUG_POWER = localLOGV || false; 253 static final boolean DEBUG_POWER_QUICK = DEBUG_POWER || false; 254 static final boolean DEBUG_PROCESS_OBSERVERS = localLOGV || false; 255 static final boolean DEBUG_PROCESSES = localLOGV || false; 256 static final boolean DEBUG_PROVIDER = localLOGV || false; 257 static final boolean DEBUG_RESULTS = localLOGV || false; 258 static final boolean DEBUG_SERVICE = localLOGV || false; 259 static final boolean DEBUG_SERVICE_EXECUTING = localLOGV || false; 260 static final boolean DEBUG_STACK = localLOGV || false; 261 static final boolean DEBUG_SWITCH = localLOGV || false; 262 static final boolean DEBUG_TASKS = localLOGV || false; 263 static final boolean DEBUG_THUMBNAILS = localLOGV || false; 264 static final boolean DEBUG_TRANSITION = localLOGV || false; 265 static final boolean DEBUG_URI_PERMISSION = localLOGV || false; 266 static final boolean DEBUG_USER_LEAVING = localLOGV || false; 267 static final boolean DEBUG_VISBILITY = localLOGV || false; 268 static final boolean DEBUG_PSS = localLOGV || false; 269 static final boolean DEBUG_LOCKSCREEN = localLOGV || false; 270 static final boolean DEBUG_RECENTS = localLOGV || false; 271 static final boolean VALIDATE_TOKENS = false; 272 static final boolean SHOW_ACTIVITY_START_TIME = true; 273 274 // Control over CPU and battery monitoring. 275 static final long BATTERY_STATS_TIME = 30*60*1000; // write battery stats every 30 minutes. 276 static final boolean MONITOR_CPU_USAGE = true; 277 static final long MONITOR_CPU_MIN_TIME = 5*1000; // don't sample cpu less than every 5 seconds. 278 static final long MONITOR_CPU_MAX_TIME = 0x0fffffff; // wait possibly forever for next cpu sample. 279 static final boolean MONITOR_THREAD_CPU_USAGE = false; 280 281 // The flags that are set for all calls we make to the package manager. 282 static final int STOCK_PM_FLAGS = PackageManager.GET_SHARED_LIBRARY_FILES; 283 284 private static final String SYSTEM_DEBUGGABLE = "ro.debuggable"; 285 286 static final boolean IS_USER_BUILD = "user".equals(Build.TYPE); 287 288 // Maximum number recent bitmaps to keep in memory. 289 static final int MAX_RECENT_BITMAPS = 5; 290 291 // Amount of time after a call to stopAppSwitches() during which we will 292 // prevent further untrusted switches from happening. 293 static final long APP_SWITCH_DELAY_TIME = 5*1000; 294 295 // How long we wait for a launched process to attach to the activity manager 296 // before we decide it's never going to come up for real. 297 static final int PROC_START_TIMEOUT = 10*1000; 298 299 // How long we wait for a launched process to attach to the activity manager 300 // before we decide it's never going to come up for real, when the process was 301 // started with a wrapper for instrumentation (such as Valgrind) because it 302 // could take much longer than usual. 303 static final int PROC_START_TIMEOUT_WITH_WRAPPER = 1200*1000; 304 305 // How long to wait after going idle before forcing apps to GC. 306 static final int GC_TIMEOUT = 5*1000; 307 308 // The minimum amount of time between successive GC requests for a process. 309 static final int GC_MIN_INTERVAL = 60*1000; 310 311 // The minimum amount of time between successive PSS requests for a process. 312 static final int FULL_PSS_MIN_INTERVAL = 10*60*1000; 313 314 // The minimum amount of time between successive PSS requests for a process 315 // when the request is due to the memory state being lowered. 316 static final int FULL_PSS_LOWERED_INTERVAL = 2*60*1000; 317 318 // The rate at which we check for apps using excessive power -- 15 mins. 319 static final int POWER_CHECK_DELAY = (DEBUG_POWER_QUICK ? 2 : 15) * 60*1000; 320 321 // The minimum sample duration we will allow before deciding we have 322 // enough data on wake locks to start killing things. 323 static final int WAKE_LOCK_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 324 325 // The minimum sample duration we will allow before deciding we have 326 // enough data on CPU usage to start killing things. 327 static final int CPU_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 328 329 // How long we allow a receiver to run before giving up on it. 330 static final int BROADCAST_FG_TIMEOUT = 10*1000; 331 static final int BROADCAST_BG_TIMEOUT = 60*1000; 332 333 // How long we wait until we timeout on key dispatching. 334 static final int KEY_DISPATCHING_TIMEOUT = 5*1000; 335 336 // How long we wait until we timeout on key dispatching during instrumentation. 337 static final int INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT = 60*1000; 338 339 // Amount of time we wait for observers to handle a user switch before 340 // giving up on them and unfreezing the screen. 341 static final int USER_SWITCH_TIMEOUT = 2*1000; 342 343 // Maximum number of users we allow to be running at a time. 344 static final int MAX_RUNNING_USERS = 3; 345 346 // How long to wait in getAssistContextExtras for the activity and foreground services 347 // to respond with the result. 348 static final int PENDING_ASSIST_EXTRAS_TIMEOUT = 500; 349 350 // Maximum number of persisted Uri grants a package is allowed 351 static final int MAX_PERSISTED_URI_GRANTS = 128; 352 353 static final int MY_PID = Process.myPid(); 354 355 static final String[] EMPTY_STRING_ARRAY = new String[0]; 356 357 // How many bytes to write into the dropbox log before truncating 358 static final int DROPBOX_MAX_SIZE = 256 * 1024; 359 360 // Access modes for handleIncomingUser. 361 static final int ALLOW_NON_FULL = 0; 362 static final int ALLOW_NON_FULL_IN_PROFILE = 1; 363 static final int ALLOW_FULL_ONLY = 2; 364 365 static final int LAST_PREBOOT_DELIVERED_FILE_VERSION = 10000; 366 367 /** All system services */ 368 SystemServiceManager mSystemServiceManager; 369 370 /** Run all ActivityStacks through this */ 371 ActivityStackSupervisor mStackSupervisor; 372 373 public IntentFirewall mIntentFirewall; 374 375 // Whether we should show our dialogs (ANR, crash, etc) or just perform their 376 // default actuion automatically. Important for devices without direct input 377 // devices. 378 private boolean mShowDialogs = true; 379 380 BroadcastQueue mFgBroadcastQueue; 381 BroadcastQueue mBgBroadcastQueue; 382 // Convenient for easy iteration over the queues. Foreground is first 383 // so that dispatch of foreground broadcasts gets precedence. 384 final BroadcastQueue[] mBroadcastQueues = new BroadcastQueue[2]; 385 386 BroadcastQueue broadcastQueueForIntent(Intent intent) { 387 final boolean isFg = (intent.getFlags() & Intent.FLAG_RECEIVER_FOREGROUND) != 0; 388 if (DEBUG_BACKGROUND_BROADCAST) { 389 Slog.i(TAG, "Broadcast intent " + intent + " on " 390 + (isFg ? "foreground" : "background") 391 + " queue"); 392 } 393 return (isFg) ? mFgBroadcastQueue : mBgBroadcastQueue; 394 } 395 396 BroadcastRecord broadcastRecordForReceiverLocked(IBinder receiver) { 397 for (BroadcastQueue queue : mBroadcastQueues) { 398 BroadcastRecord r = queue.getMatchingOrderedReceiver(receiver); 399 if (r != null) { 400 return r; 401 } 402 } 403 return null; 404 } 405 406 /** 407 * Activity we have told the window manager to have key focus. 408 */ 409 ActivityRecord mFocusedActivity = null; 410 411 /** 412 * List of intents that were used to start the most recent tasks. 413 */ 414 ArrayList<TaskRecord> mRecentTasks; 415 ArraySet<TaskRecord> mTmpRecents = new ArraySet<TaskRecord>(); 416 417 /** 418 * For addAppTask: cached of the last activity component that was added. 419 */ 420 ComponentName mLastAddedTaskComponent; 421 422 /** 423 * For addAppTask: cached of the last activity uid that was added. 424 */ 425 int mLastAddedTaskUid; 426 427 /** 428 * For addAppTask: cached of the last ActivityInfo that was added. 429 */ 430 ActivityInfo mLastAddedTaskActivity; 431 432 public class PendingAssistExtras extends Binder implements Runnable { 433 public final ActivityRecord activity; 434 public boolean haveResult = false; 435 public Bundle result = null; 436 public PendingAssistExtras(ActivityRecord _activity) { 437 activity = _activity; 438 } 439 @Override 440 public void run() { 441 Slog.w(TAG, "getAssistContextExtras failed: timeout retrieving from " + activity); 442 synchronized (this) { 443 haveResult = true; 444 notifyAll(); 445 } 446 } 447 } 448 449 final ArrayList<PendingAssistExtras> mPendingAssistExtras 450 = new ArrayList<PendingAssistExtras>(); 451 452 /** 453 * Process management. 454 */ 455 final ProcessList mProcessList = new ProcessList(); 456 457 /** 458 * All of the applications we currently have running organized by name. 459 * The keys are strings of the application package name (as 460 * returned by the package manager), and the keys are ApplicationRecord 461 * objects. 462 */ 463 final ProcessMap<ProcessRecord> mProcessNames = new ProcessMap<ProcessRecord>(); 464 465 /** 466 * Tracking long-term execution of processes to look for abuse and other 467 * bad app behavior. 468 */ 469 final ProcessStatsService mProcessStats; 470 471 /** 472 * The currently running isolated processes. 473 */ 474 final SparseArray<ProcessRecord> mIsolatedProcesses = new SparseArray<ProcessRecord>(); 475 476 /** 477 * Counter for assigning isolated process uids, to avoid frequently reusing the 478 * same ones. 479 */ 480 int mNextIsolatedProcessUid = 0; 481 482 /** 483 * The currently running heavy-weight process, if any. 484 */ 485 ProcessRecord mHeavyWeightProcess = null; 486 487 /** 488 * The last time that various processes have crashed. 489 */ 490 final ProcessMap<Long> mProcessCrashTimes = new ProcessMap<Long>(); 491 492 /** 493 * Information about a process that is currently marked as bad. 494 */ 495 static final class BadProcessInfo { 496 BadProcessInfo(long time, String shortMsg, String longMsg, String stack) { 497 this.time = time; 498 this.shortMsg = shortMsg; 499 this.longMsg = longMsg; 500 this.stack = stack; 501 } 502 503 final long time; 504 final String shortMsg; 505 final String longMsg; 506 final String stack; 507 } 508 509 /** 510 * Set of applications that we consider to be bad, and will reject 511 * incoming broadcasts from (which the user has no control over). 512 * Processes are added to this set when they have crashed twice within 513 * a minimum amount of time; they are removed from it when they are 514 * later restarted (hopefully due to some user action). The value is the 515 * time it was added to the list. 516 */ 517 final ProcessMap<BadProcessInfo> mBadProcesses = new ProcessMap<BadProcessInfo>(); 518 519 /** 520 * All of the processes we currently have running organized by pid. 521 * The keys are the pid running the application. 522 * 523 * <p>NOTE: This object is protected by its own lock, NOT the global 524 * activity manager lock! 525 */ 526 final SparseArray<ProcessRecord> mPidsSelfLocked = new SparseArray<ProcessRecord>(); 527 528 /** 529 * All of the processes that have been forced to be foreground. The key 530 * is the pid of the caller who requested it (we hold a death 531 * link on it). 532 */ 533 abstract class ForegroundToken implements IBinder.DeathRecipient { 534 int pid; 535 IBinder token; 536 } 537 final SparseArray<ForegroundToken> mForegroundProcesses = new SparseArray<ForegroundToken>(); 538 539 /** 540 * List of records for processes that someone had tried to start before the 541 * system was ready. We don't start them at that point, but ensure they 542 * are started by the time booting is complete. 543 */ 544 final ArrayList<ProcessRecord> mProcessesOnHold = new ArrayList<ProcessRecord>(); 545 546 /** 547 * List of persistent applications that are in the process 548 * of being started. 549 */ 550 final ArrayList<ProcessRecord> mPersistentStartingProcesses = new ArrayList<ProcessRecord>(); 551 552 /** 553 * Processes that are being forcibly torn down. 554 */ 555 final ArrayList<ProcessRecord> mRemovedProcesses = new ArrayList<ProcessRecord>(); 556 557 /** 558 * List of running applications, sorted by recent usage. 559 * The first entry in the list is the least recently used. 560 */ 561 final ArrayList<ProcessRecord> mLruProcesses = new ArrayList<ProcessRecord>(); 562 563 /** 564 * Where in mLruProcesses that the processes hosting activities start. 565 */ 566 int mLruProcessActivityStart = 0; 567 568 /** 569 * Where in mLruProcesses that the processes hosting services start. 570 * This is after (lower index) than mLruProcessesActivityStart. 571 */ 572 int mLruProcessServiceStart = 0; 573 574 /** 575 * List of processes that should gc as soon as things are idle. 576 */ 577 final ArrayList<ProcessRecord> mProcessesToGc = new ArrayList<ProcessRecord>(); 578 579 /** 580 * Processes we want to collect PSS data from. 581 */ 582 final ArrayList<ProcessRecord> mPendingPssProcesses = new ArrayList<ProcessRecord>(); 583 584 /** 585 * Last time we requested PSS data of all processes. 586 */ 587 long mLastFullPssTime = SystemClock.uptimeMillis(); 588 589 /** 590 * If set, the next time we collect PSS data we should do a full collection 591 * with data from native processes and the kernel. 592 */ 593 boolean mFullPssPending = false; 594 595 /** 596 * This is the process holding what we currently consider to be 597 * the "home" activity. 598 */ 599 ProcessRecord mHomeProcess; 600 601 /** 602 * This is the process holding the activity the user last visited that 603 * is in a different process from the one they are currently in. 604 */ 605 ProcessRecord mPreviousProcess; 606 607 /** 608 * The time at which the previous process was last visible. 609 */ 610 long mPreviousProcessVisibleTime; 611 612 /** 613 * Which uses have been started, so are allowed to run code. 614 */ 615 final SparseArray<UserStartedState> mStartedUsers = new SparseArray<UserStartedState>(); 616 617 /** 618 * LRU list of history of current users. Most recently current is at the end. 619 */ 620 final ArrayList<Integer> mUserLru = new ArrayList<Integer>(); 621 622 /** 623 * Constant array of the users that are currently started. 624 */ 625 int[] mStartedUserArray = new int[] { 0 }; 626 627 /** 628 * Registered observers of the user switching mechanics. 629 */ 630 final RemoteCallbackList<IUserSwitchObserver> mUserSwitchObservers 631 = new RemoteCallbackList<IUserSwitchObserver>(); 632 633 /** 634 * Currently active user switch. 635 */ 636 Object mCurUserSwitchCallback; 637 638 /** 639 * Packages that the user has asked to have run in screen size 640 * compatibility mode instead of filling the screen. 641 */ 642 final CompatModePackages mCompatModePackages; 643 644 /** 645 * Set of IntentSenderRecord objects that are currently active. 646 */ 647 final HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>> mIntentSenderRecords 648 = new HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>>(); 649 650 /** 651 * Fingerprints (hashCode()) of stack traces that we've 652 * already logged DropBox entries for. Guarded by itself. If 653 * something (rogue user app) forces this over 654 * MAX_DUP_SUPPRESSED_STACKS entries, the contents are cleared. 655 */ 656 private final HashSet<Integer> mAlreadyLoggedViolatedStacks = new HashSet<Integer>(); 657 private static final int MAX_DUP_SUPPRESSED_STACKS = 5000; 658 659 /** 660 * Strict Mode background batched logging state. 661 * 662 * The string buffer is guarded by itself, and its lock is also 663 * used to determine if another batched write is already 664 * in-flight. 665 */ 666 private final StringBuilder mStrictModeBuffer = new StringBuilder(); 667 668 /** 669 * Keeps track of all IIntentReceivers that have been registered for 670 * broadcasts. Hash keys are the receiver IBinder, hash value is 671 * a ReceiverList. 672 */ 673 final HashMap<IBinder, ReceiverList> mRegisteredReceivers = 674 new HashMap<IBinder, ReceiverList>(); 675 676 /** 677 * Resolver for broadcast intents to registered receivers. 678 * Holds BroadcastFilter (subclass of IntentFilter). 679 */ 680 final IntentResolver<BroadcastFilter, BroadcastFilter> mReceiverResolver 681 = new IntentResolver<BroadcastFilter, BroadcastFilter>() { 682 @Override 683 protected boolean allowFilterResult( 684 BroadcastFilter filter, List<BroadcastFilter> dest) { 685 IBinder target = filter.receiverList.receiver.asBinder(); 686 for (int i=dest.size()-1; i>=0; i--) { 687 if (dest.get(i).receiverList.receiver.asBinder() == target) { 688 return false; 689 } 690 } 691 return true; 692 } 693 694 @Override 695 protected BroadcastFilter newResult(BroadcastFilter filter, int match, int userId) { 696 if (userId == UserHandle.USER_ALL || filter.owningUserId == UserHandle.USER_ALL 697 || userId == filter.owningUserId) { 698 return super.newResult(filter, match, userId); 699 } 700 return null; 701 } 702 703 @Override 704 protected BroadcastFilter[] newArray(int size) { 705 return new BroadcastFilter[size]; 706 } 707 708 @Override 709 protected boolean isPackageForFilter(String packageName, BroadcastFilter filter) { 710 return packageName.equals(filter.packageName); 711 } 712 }; 713 714 /** 715 * State of all active sticky broadcasts per user. Keys are the action of the 716 * sticky Intent, values are an ArrayList of all broadcasted intents with 717 * that action (which should usually be one). The SparseArray is keyed 718 * by the user ID the sticky is for, and can include UserHandle.USER_ALL 719 * for stickies that are sent to all users. 720 */ 721 final SparseArray<ArrayMap<String, ArrayList<Intent>>> mStickyBroadcasts = 722 new SparseArray<ArrayMap<String, ArrayList<Intent>>>(); 723 724 final ActiveServices mServices; 725 726 /** 727 * Backup/restore process management 728 */ 729 String mBackupAppName = null; 730 BackupRecord mBackupTarget = null; 731 732 final ProviderMap mProviderMap; 733 734 /** 735 * List of content providers who have clients waiting for them. The 736 * application is currently being launched and the provider will be 737 * removed from this list once it is published. 738 */ 739 final ArrayList<ContentProviderRecord> mLaunchingProviders 740 = new ArrayList<ContentProviderRecord>(); 741 742 /** 743 * File storing persisted {@link #mGrantedUriPermissions}. 744 */ 745 private final AtomicFile mGrantFile; 746 747 /** XML constants used in {@link #mGrantFile} */ 748 private static final String TAG_URI_GRANTS = "uri-grants"; 749 private static final String TAG_URI_GRANT = "uri-grant"; 750 private static final String ATTR_USER_HANDLE = "userHandle"; 751 private static final String ATTR_SOURCE_USER_ID = "sourceUserId"; 752 private static final String ATTR_TARGET_USER_ID = "targetUserId"; 753 private static final String ATTR_SOURCE_PKG = "sourcePkg"; 754 private static final String ATTR_TARGET_PKG = "targetPkg"; 755 private static final String ATTR_URI = "uri"; 756 private static final String ATTR_MODE_FLAGS = "modeFlags"; 757 private static final String ATTR_CREATED_TIME = "createdTime"; 758 private static final String ATTR_PREFIX = "prefix"; 759 760 /** 761 * Global set of specific {@link Uri} permissions that have been granted. 762 * This optimized lookup structure maps from {@link UriPermission#targetUid} 763 * to {@link UriPermission#uri} to {@link UriPermission}. 764 */ 765 @GuardedBy("this") 766 private final SparseArray<ArrayMap<GrantUri, UriPermission>> 767 mGrantedUriPermissions = new SparseArray<ArrayMap<GrantUri, UriPermission>>(); 768 769 public static class GrantUri { 770 public final int sourceUserId; 771 public final Uri uri; 772 public boolean prefix; 773 774 public GrantUri(int sourceUserId, Uri uri, boolean prefix) { 775 this.sourceUserId = sourceUserId; 776 this.uri = uri; 777 this.prefix = prefix; 778 } 779 780 @Override 781 public int hashCode() { 782 return toString().hashCode(); 783 } 784 785 @Override 786 public boolean equals(Object o) { 787 if (o instanceof GrantUri) { 788 GrantUri other = (GrantUri) o; 789 return uri.equals(other.uri) && (sourceUserId == other.sourceUserId) 790 && prefix == other.prefix; 791 } 792 return false; 793 } 794 795 @Override 796 public String toString() { 797 String result = Integer.toString(sourceUserId) + " @ " + uri.toString(); 798 if (prefix) result += " [prefix]"; 799 return result; 800 } 801 802 public String toSafeString() { 803 String result = Integer.toString(sourceUserId) + " @ " + uri.toSafeString(); 804 if (prefix) result += " [prefix]"; 805 return result; 806 } 807 808 public static GrantUri resolve(int defaultSourceUserHandle, Uri uri) { 809 return new GrantUri(ContentProvider.getUserIdFromUri(uri, defaultSourceUserHandle), 810 ContentProvider.getUriWithoutUserId(uri), false); 811 } 812 } 813 814 CoreSettingsObserver mCoreSettingsObserver; 815 816 /** 817 * Thread-local storage used to carry caller permissions over through 818 * indirect content-provider access. 819 */ 820 private class Identity { 821 public int pid; 822 public int uid; 823 824 Identity(int _pid, int _uid) { 825 pid = _pid; 826 uid = _uid; 827 } 828 } 829 830 private static final ThreadLocal<Identity> sCallerIdentity = new ThreadLocal<Identity>(); 831 832 /** 833 * All information we have collected about the runtime performance of 834 * any user id that can impact battery performance. 835 */ 836 final BatteryStatsService mBatteryStatsService; 837 838 /** 839 * Information about component usage 840 */ 841 UsageStatsManagerInternal mUsageStatsService; 842 843 /** 844 * Information about and control over application operations 845 */ 846 final AppOpsService mAppOpsService; 847 848 /** 849 * Save recent tasks information across reboots. 850 */ 851 final TaskPersister mTaskPersister; 852 853 /** 854 * Current configuration information. HistoryRecord objects are given 855 * a reference to this object to indicate which configuration they are 856 * currently running in, so this object must be kept immutable. 857 */ 858 Configuration mConfiguration = new Configuration(); 859 860 /** 861 * Current sequencing integer of the configuration, for skipping old 862 * configurations. 863 */ 864 int mConfigurationSeq = 0; 865 866 /** 867 * Hardware-reported OpenGLES version. 868 */ 869 final int GL_ES_VERSION; 870 871 /** 872 * List of initialization arguments to pass to all processes when binding applications to them. 873 * For example, references to the commonly used services. 874 */ 875 HashMap<String, IBinder> mAppBindArgs; 876 877 /** 878 * Temporary to avoid allocations. Protected by main lock. 879 */ 880 final StringBuilder mStringBuilder = new StringBuilder(256); 881 882 /** 883 * Used to control how we initialize the service. 884 */ 885 ComponentName mTopComponent; 886 String mTopAction = Intent.ACTION_MAIN; 887 String mTopData; 888 boolean mProcessesReady = false; 889 boolean mSystemReady = false; 890 boolean mBooting = false; 891 boolean mWaitingUpdate = false; 892 boolean mDidUpdate = false; 893 boolean mOnBattery = false; 894 boolean mLaunchWarningShown = false; 895 896 Context mContext; 897 898 int mFactoryTest; 899 900 boolean mCheckedForSetup; 901 902 /** 903 * The time at which we will allow normal application switches again, 904 * after a call to {@link #stopAppSwitches()}. 905 */ 906 long mAppSwitchesAllowedTime; 907 908 /** 909 * This is set to true after the first switch after mAppSwitchesAllowedTime 910 * is set; any switches after that will clear the time. 911 */ 912 boolean mDidAppSwitch; 913 914 /** 915 * Last time (in realtime) at which we checked for power usage. 916 */ 917 long mLastPowerCheckRealtime; 918 919 /** 920 * Last time (in uptime) at which we checked for power usage. 921 */ 922 long mLastPowerCheckUptime; 923 924 /** 925 * Set while we are wanting to sleep, to prevent any 926 * activities from being started/resumed. 927 */ 928 private boolean mSleeping = false; 929 930 /** 931 * Set while we are running a voice interaction. This overrides 932 * sleeping while it is active. 933 */ 934 private boolean mRunningVoice = false; 935 936 /** 937 * State of external calls telling us if the device is asleep. 938 */ 939 private boolean mWentToSleep = false; 940 941 /** 942 * State of external call telling us if the lock screen is shown. 943 */ 944 private boolean mLockScreenShown = false; 945 946 /** 947 * Set if we are shutting down the system, similar to sleeping. 948 */ 949 boolean mShuttingDown = false; 950 951 /** 952 * Current sequence id for oom_adj computation traversal. 953 */ 954 int mAdjSeq = 0; 955 956 /** 957 * Current sequence id for process LRU updating. 958 */ 959 int mLruSeq = 0; 960 961 /** 962 * Keep track of the non-cached/empty process we last found, to help 963 * determine how to distribute cached/empty processes next time. 964 */ 965 int mNumNonCachedProcs = 0; 966 967 /** 968 * Keep track of the number of cached hidden procs, to balance oom adj 969 * distribution between those and empty procs. 970 */ 971 int mNumCachedHiddenProcs = 0; 972 973 /** 974 * Keep track of the number of service processes we last found, to 975 * determine on the next iteration which should be B services. 976 */ 977 int mNumServiceProcs = 0; 978 int mNewNumAServiceProcs = 0; 979 int mNewNumServiceProcs = 0; 980 981 /** 982 * Allow the current computed overall memory level of the system to go down? 983 * This is set to false when we are killing processes for reasons other than 984 * memory management, so that the now smaller process list will not be taken as 985 * an indication that memory is tighter. 986 */ 987 boolean mAllowLowerMemLevel = false; 988 989 /** 990 * The last computed memory level, for holding when we are in a state that 991 * processes are going away for other reasons. 992 */ 993 int mLastMemoryLevel = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 994 995 /** 996 * The last total number of process we have, to determine if changes actually look 997 * like a shrinking number of process due to lower RAM. 998 */ 999 int mLastNumProcesses; 1000 1001 /** 1002 * The uptime of the last time we performed idle maintenance. 1003 */ 1004 long mLastIdleTime = SystemClock.uptimeMillis(); 1005 1006 /** 1007 * Total time spent with RAM that has been added in the past since the last idle time. 1008 */ 1009 long mLowRamTimeSinceLastIdle = 0; 1010 1011 /** 1012 * If RAM is currently low, when that horrible situation started. 1013 */ 1014 long mLowRamStartTime = 0; 1015 1016 /** 1017 * For reporting to battery stats the current top application. 1018 */ 1019 private String mCurResumedPackage = null; 1020 private int mCurResumedUid = -1; 1021 1022 /** 1023 * For reporting to battery stats the apps currently running foreground 1024 * service. The ProcessMap is package/uid tuples; each of these contain 1025 * an array of the currently foreground processes. 1026 */ 1027 final ProcessMap<ArrayList<ProcessRecord>> mForegroundPackages 1028 = new ProcessMap<ArrayList<ProcessRecord>>(); 1029 1030 /** 1031 * This is set if we had to do a delayed dexopt of an app before launching 1032 * it, to increase the ANR timeouts in that case. 1033 */ 1034 boolean mDidDexOpt; 1035 1036 /** 1037 * Set if the systemServer made a call to enterSafeMode. 1038 */ 1039 boolean mSafeMode; 1040 1041 String mDebugApp = null; 1042 boolean mWaitForDebugger = false; 1043 boolean mDebugTransient = false; 1044 String mOrigDebugApp = null; 1045 boolean mOrigWaitForDebugger = false; 1046 boolean mAlwaysFinishActivities = false; 1047 IActivityController mController = null; 1048 String mProfileApp = null; 1049 ProcessRecord mProfileProc = null; 1050 String mProfileFile; 1051 ParcelFileDescriptor mProfileFd; 1052 int mSamplingInterval = 0; 1053 boolean mAutoStopProfiler = false; 1054 int mProfileType = 0; 1055 String mOpenGlTraceApp = null; 1056 1057 static class ProcessChangeItem { 1058 static final int CHANGE_ACTIVITIES = 1<<0; 1059 static final int CHANGE_PROCESS_STATE = 1<<1; 1060 int changes; 1061 int uid; 1062 int pid; 1063 int processState; 1064 boolean foregroundActivities; 1065 } 1066 1067 final RemoteCallbackList<IProcessObserver> mProcessObservers 1068 = new RemoteCallbackList<IProcessObserver>(); 1069 ProcessChangeItem[] mActiveProcessChanges = new ProcessChangeItem[5]; 1070 1071 final ArrayList<ProcessChangeItem> mPendingProcessChanges 1072 = new ArrayList<ProcessChangeItem>(); 1073 final ArrayList<ProcessChangeItem> mAvailProcessChanges 1074 = new ArrayList<ProcessChangeItem>(); 1075 1076 /** 1077 * Runtime CPU use collection thread. This object's lock is used to 1078 * protect all related state. 1079 */ 1080 final Thread mProcessCpuThread; 1081 1082 /** 1083 * Used to collect process stats when showing not responding dialog. 1084 * Protected by mProcessCpuThread. 1085 */ 1086 final ProcessCpuTracker mProcessCpuTracker = new ProcessCpuTracker( 1087 MONITOR_THREAD_CPU_USAGE); 1088 final AtomicLong mLastCpuTime = new AtomicLong(0); 1089 final AtomicBoolean mProcessCpuMutexFree = new AtomicBoolean(true); 1090 1091 long mLastWriteTime = 0; 1092 1093 /** 1094 * Used to retain an update lock when the foreground activity is in 1095 * immersive mode. 1096 */ 1097 final UpdateLock mUpdateLock = new UpdateLock("immersive"); 1098 1099 /** 1100 * Set to true after the system has finished booting. 1101 */ 1102 boolean mBooted = false; 1103 1104 int mProcessLimit = ProcessList.MAX_CACHED_APPS; 1105 int mProcessLimitOverride = -1; 1106 1107 WindowManagerService mWindowManager; 1108 1109 final ActivityThread mSystemThread; 1110 1111 // Holds the current foreground user's id 1112 int mCurrentUserId = 0; 1113 // Holds the target user's id during a user switch 1114 int mTargetUserId = UserHandle.USER_NULL; 1115 // If there are multiple profiles for the current user, their ids are here 1116 // Currently only the primary user can have managed profiles 1117 int[] mCurrentProfileIds = new int[] {UserHandle.USER_OWNER}; // Accessed by ActivityStack 1118 1119 /** 1120 * Mapping from each known user ID to the profile group ID it is associated with. 1121 */ 1122 SparseIntArray mUserProfileGroupIdsSelfLocked = new SparseIntArray(); 1123 1124 private UserManagerService mUserManager; 1125 1126 private final class AppDeathRecipient implements IBinder.DeathRecipient { 1127 final ProcessRecord mApp; 1128 final int mPid; 1129 final IApplicationThread mAppThread; 1130 1131 AppDeathRecipient(ProcessRecord app, int pid, 1132 IApplicationThread thread) { 1133 if (localLOGV) Slog.v( 1134 TAG, "New death recipient " + this 1135 + " for thread " + thread.asBinder()); 1136 mApp = app; 1137 mPid = pid; 1138 mAppThread = thread; 1139 } 1140 1141 @Override 1142 public void binderDied() { 1143 if (localLOGV) Slog.v( 1144 TAG, "Death received in " + this 1145 + " for thread " + mAppThread.asBinder()); 1146 synchronized(ActivityManagerService.this) { 1147 appDiedLocked(mApp, mPid, mAppThread); 1148 } 1149 } 1150 } 1151 1152 static final int SHOW_ERROR_MSG = 1; 1153 static final int SHOW_NOT_RESPONDING_MSG = 2; 1154 static final int SHOW_FACTORY_ERROR_MSG = 3; 1155 static final int UPDATE_CONFIGURATION_MSG = 4; 1156 static final int GC_BACKGROUND_PROCESSES_MSG = 5; 1157 static final int WAIT_FOR_DEBUGGER_MSG = 6; 1158 static final int SERVICE_TIMEOUT_MSG = 12; 1159 static final int UPDATE_TIME_ZONE = 13; 1160 static final int SHOW_UID_ERROR_MSG = 14; 1161 static final int IM_FEELING_LUCKY_MSG = 15; 1162 static final int PROC_START_TIMEOUT_MSG = 20; 1163 static final int DO_PENDING_ACTIVITY_LAUNCHES_MSG = 21; 1164 static final int KILL_APPLICATION_MSG = 22; 1165 static final int FINALIZE_PENDING_INTENT_MSG = 23; 1166 static final int POST_HEAVY_NOTIFICATION_MSG = 24; 1167 static final int CANCEL_HEAVY_NOTIFICATION_MSG = 25; 1168 static final int SHOW_STRICT_MODE_VIOLATION_MSG = 26; 1169 static final int CHECK_EXCESSIVE_WAKE_LOCKS_MSG = 27; 1170 static final int CLEAR_DNS_CACHE_MSG = 28; 1171 static final int UPDATE_HTTP_PROXY_MSG = 29; 1172 static final int SHOW_COMPAT_MODE_DIALOG_MSG = 30; 1173 static final int DISPATCH_PROCESSES_CHANGED = 31; 1174 static final int DISPATCH_PROCESS_DIED = 32; 1175 static final int REPORT_MEM_USAGE_MSG = 33; 1176 static final int REPORT_USER_SWITCH_MSG = 34; 1177 static final int CONTINUE_USER_SWITCH_MSG = 35; 1178 static final int USER_SWITCH_TIMEOUT_MSG = 36; 1179 static final int IMMERSIVE_MODE_LOCK_MSG = 37; 1180 static final int PERSIST_URI_GRANTS_MSG = 38; 1181 static final int REQUEST_ALL_PSS_MSG = 39; 1182 static final int START_PROFILES_MSG = 40; 1183 static final int UPDATE_TIME = 41; 1184 static final int SYSTEM_USER_START_MSG = 42; 1185 static final int SYSTEM_USER_CURRENT_MSG = 43; 1186 static final int ENTER_ANIMATION_COMPLETE_MSG = 44; 1187 static final int ENABLE_SCREEN_AFTER_BOOT_MSG = 45; 1188 static final int START_USER_SWITCH_MSG = 46; 1189 1190 static final int FIRST_ACTIVITY_STACK_MSG = 100; 1191 static final int FIRST_BROADCAST_QUEUE_MSG = 200; 1192 static final int FIRST_COMPAT_MODE_MSG = 300; 1193 static final int FIRST_SUPERVISOR_STACK_MSG = 100; 1194 1195 AlertDialog mUidAlert; 1196 CompatModeDialog mCompatModeDialog; 1197 long mLastMemUsageReportTime = 0; 1198 1199 private LockToAppRequestDialog mLockToAppRequest; 1200 1201 /** 1202 * Flag whether the current user is a "monkey", i.e. whether 1203 * the UI is driven by a UI automation tool. 1204 */ 1205 private boolean mUserIsMonkey; 1206 1207 /** Flag whether the device has a Recents UI */ 1208 boolean mHasRecents; 1209 1210 /** The dimensions of the thumbnails in the Recents UI. */ 1211 int mThumbnailWidth; 1212 int mThumbnailHeight; 1213 1214 final ServiceThread mHandlerThread; 1215 final MainHandler mHandler; 1216 1217 final class MainHandler extends Handler { 1218 public MainHandler(Looper looper) { 1219 super(looper, null, true); 1220 } 1221 1222 @Override 1223 public void handleMessage(Message msg) { 1224 switch (msg.what) { 1225 case SHOW_ERROR_MSG: { 1226 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1227 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 1228 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 1229 synchronized (ActivityManagerService.this) { 1230 ProcessRecord proc = (ProcessRecord)data.get("app"); 1231 AppErrorResult res = (AppErrorResult) data.get("result"); 1232 if (proc != null && proc.crashDialog != null) { 1233 Slog.e(TAG, "App already has crash dialog: " + proc); 1234 if (res != null) { 1235 res.set(0); 1236 } 1237 return; 1238 } 1239 boolean isBackground = (UserHandle.getAppId(proc.uid) 1240 >= Process.FIRST_APPLICATION_UID 1241 && proc.pid != MY_PID); 1242 for (int userId : mCurrentProfileIds) { 1243 isBackground &= (proc.userId != userId); 1244 } 1245 if (isBackground && !showBackground) { 1246 Slog.w(TAG, "Skipping crash dialog of " + proc + ": background"); 1247 if (res != null) { 1248 res.set(0); 1249 } 1250 return; 1251 } 1252 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1253 Dialog d = new AppErrorDialog(mContext, 1254 ActivityManagerService.this, res, proc); 1255 d.show(); 1256 proc.crashDialog = d; 1257 } else { 1258 // The device is asleep, so just pretend that the user 1259 // saw a crash dialog and hit "force quit". 1260 if (res != null) { 1261 res.set(0); 1262 } 1263 } 1264 } 1265 1266 ensureBootCompleted(); 1267 } break; 1268 case SHOW_NOT_RESPONDING_MSG: { 1269 synchronized (ActivityManagerService.this) { 1270 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1271 ProcessRecord proc = (ProcessRecord)data.get("app"); 1272 if (proc != null && proc.anrDialog != null) { 1273 Slog.e(TAG, "App already has anr dialog: " + proc); 1274 return; 1275 } 1276 1277 Intent intent = new Intent("android.intent.action.ANR"); 1278 if (!mProcessesReady) { 1279 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 1280 | Intent.FLAG_RECEIVER_FOREGROUND); 1281 } 1282 broadcastIntentLocked(null, null, intent, 1283 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 1284 false, false, MY_PID, Process.SYSTEM_UID, 0 /* TODO: Verify */); 1285 1286 if (mShowDialogs) { 1287 Dialog d = new AppNotRespondingDialog(ActivityManagerService.this, 1288 mContext, proc, (ActivityRecord)data.get("activity"), 1289 msg.arg1 != 0); 1290 d.show(); 1291 proc.anrDialog = d; 1292 } else { 1293 // Just kill the app if there is no dialog to be shown. 1294 killAppAtUsersRequest(proc, null); 1295 } 1296 } 1297 1298 ensureBootCompleted(); 1299 } break; 1300 case SHOW_STRICT_MODE_VIOLATION_MSG: { 1301 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1302 synchronized (ActivityManagerService.this) { 1303 ProcessRecord proc = (ProcessRecord) data.get("app"); 1304 if (proc == null) { 1305 Slog.e(TAG, "App not found when showing strict mode dialog."); 1306 break; 1307 } 1308 if (proc.crashDialog != null) { 1309 Slog.e(TAG, "App already has strict mode dialog: " + proc); 1310 return; 1311 } 1312 AppErrorResult res = (AppErrorResult) data.get("result"); 1313 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1314 Dialog d = new StrictModeViolationDialog(mContext, 1315 ActivityManagerService.this, res, proc); 1316 d.show(); 1317 proc.crashDialog = d; 1318 } else { 1319 // The device is asleep, so just pretend that the user 1320 // saw a crash dialog and hit "force quit". 1321 res.set(0); 1322 } 1323 } 1324 ensureBootCompleted(); 1325 } break; 1326 case SHOW_FACTORY_ERROR_MSG: { 1327 Dialog d = new FactoryErrorDialog( 1328 mContext, msg.getData().getCharSequence("msg")); 1329 d.show(); 1330 ensureBootCompleted(); 1331 } break; 1332 case UPDATE_CONFIGURATION_MSG: { 1333 final ContentResolver resolver = mContext.getContentResolver(); 1334 Settings.System.putConfiguration(resolver, (Configuration)msg.obj); 1335 } break; 1336 case GC_BACKGROUND_PROCESSES_MSG: { 1337 synchronized (ActivityManagerService.this) { 1338 performAppGcsIfAppropriateLocked(); 1339 } 1340 } break; 1341 case WAIT_FOR_DEBUGGER_MSG: { 1342 synchronized (ActivityManagerService.this) { 1343 ProcessRecord app = (ProcessRecord)msg.obj; 1344 if (msg.arg1 != 0) { 1345 if (!app.waitedForDebugger) { 1346 Dialog d = new AppWaitingForDebuggerDialog( 1347 ActivityManagerService.this, 1348 mContext, app); 1349 app.waitDialog = d; 1350 app.waitedForDebugger = true; 1351 d.show(); 1352 } 1353 } else { 1354 if (app.waitDialog != null) { 1355 app.waitDialog.dismiss(); 1356 app.waitDialog = null; 1357 } 1358 } 1359 } 1360 } break; 1361 case SERVICE_TIMEOUT_MSG: { 1362 if (mDidDexOpt) { 1363 mDidDexOpt = false; 1364 Message nmsg = mHandler.obtainMessage(SERVICE_TIMEOUT_MSG); 1365 nmsg.obj = msg.obj; 1366 mHandler.sendMessageDelayed(nmsg, ActiveServices.SERVICE_TIMEOUT); 1367 return; 1368 } 1369 mServices.serviceTimeout((ProcessRecord)msg.obj); 1370 } break; 1371 case UPDATE_TIME_ZONE: { 1372 synchronized (ActivityManagerService.this) { 1373 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1374 ProcessRecord r = mLruProcesses.get(i); 1375 if (r.thread != null) { 1376 try { 1377 r.thread.updateTimeZone(); 1378 } catch (RemoteException ex) { 1379 Slog.w(TAG, "Failed to update time zone for: " + r.info.processName); 1380 } 1381 } 1382 } 1383 } 1384 } break; 1385 case CLEAR_DNS_CACHE_MSG: { 1386 synchronized (ActivityManagerService.this) { 1387 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1388 ProcessRecord r = mLruProcesses.get(i); 1389 if (r.thread != null) { 1390 try { 1391 r.thread.clearDnsCache(); 1392 } catch (RemoteException ex) { 1393 Slog.w(TAG, "Failed to clear dns cache for: " + r.info.processName); 1394 } 1395 } 1396 } 1397 } 1398 } break; 1399 case UPDATE_HTTP_PROXY_MSG: { 1400 ProxyInfo proxy = (ProxyInfo)msg.obj; 1401 String host = ""; 1402 String port = ""; 1403 String exclList = ""; 1404 Uri pacFileUrl = Uri.EMPTY; 1405 if (proxy != null) { 1406 host = proxy.getHost(); 1407 port = Integer.toString(proxy.getPort()); 1408 exclList = proxy.getExclusionListAsString(); 1409 pacFileUrl = proxy.getPacFileUrl(); 1410 } 1411 synchronized (ActivityManagerService.this) { 1412 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1413 ProcessRecord r = mLruProcesses.get(i); 1414 if (r.thread != null) { 1415 try { 1416 r.thread.setHttpProxy(host, port, exclList, pacFileUrl); 1417 } catch (RemoteException ex) { 1418 Slog.w(TAG, "Failed to update http proxy for: " + 1419 r.info.processName); 1420 } 1421 } 1422 } 1423 } 1424 } break; 1425 case SHOW_UID_ERROR_MSG: { 1426 String title = "System UIDs Inconsistent"; 1427 String text = "UIDs on the system are inconsistent, you need to wipe your" 1428 + " data partition or your device will be unstable."; 1429 Log.e(TAG, title + ": " + text); 1430 if (mShowDialogs) { 1431 // XXX This is a temporary dialog, no need to localize. 1432 AlertDialog d = new BaseErrorDialog(mContext); 1433 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 1434 d.setCancelable(false); 1435 d.setTitle(title); 1436 d.setMessage(text); 1437 d.setButton(DialogInterface.BUTTON_POSITIVE, "I'm Feeling Lucky", 1438 mHandler.obtainMessage(IM_FEELING_LUCKY_MSG)); 1439 mUidAlert = d; 1440 d.show(); 1441 } 1442 } break; 1443 case IM_FEELING_LUCKY_MSG: { 1444 if (mUidAlert != null) { 1445 mUidAlert.dismiss(); 1446 mUidAlert = null; 1447 } 1448 } break; 1449 case PROC_START_TIMEOUT_MSG: { 1450 if (mDidDexOpt) { 1451 mDidDexOpt = false; 1452 Message nmsg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 1453 nmsg.obj = msg.obj; 1454 mHandler.sendMessageDelayed(nmsg, PROC_START_TIMEOUT); 1455 return; 1456 } 1457 ProcessRecord app = (ProcessRecord)msg.obj; 1458 synchronized (ActivityManagerService.this) { 1459 processStartTimedOutLocked(app); 1460 } 1461 } break; 1462 case DO_PENDING_ACTIVITY_LAUNCHES_MSG: { 1463 synchronized (ActivityManagerService.this) { 1464 mStackSupervisor.doPendingActivityLaunchesLocked(true); 1465 } 1466 } break; 1467 case KILL_APPLICATION_MSG: { 1468 synchronized (ActivityManagerService.this) { 1469 int appid = msg.arg1; 1470 boolean restart = (msg.arg2 == 1); 1471 Bundle bundle = (Bundle)msg.obj; 1472 String pkg = bundle.getString("pkg"); 1473 String reason = bundle.getString("reason"); 1474 forceStopPackageLocked(pkg, appid, restart, false, true, false, 1475 false, UserHandle.USER_ALL, reason); 1476 } 1477 } break; 1478 case FINALIZE_PENDING_INTENT_MSG: { 1479 ((PendingIntentRecord)msg.obj).completeFinalize(); 1480 } break; 1481 case POST_HEAVY_NOTIFICATION_MSG: { 1482 INotificationManager inm = NotificationManager.getService(); 1483 if (inm == null) { 1484 return; 1485 } 1486 1487 ActivityRecord root = (ActivityRecord)msg.obj; 1488 ProcessRecord process = root.app; 1489 if (process == null) { 1490 return; 1491 } 1492 1493 try { 1494 Context context = mContext.createPackageContext(process.info.packageName, 0); 1495 String text = mContext.getString(R.string.heavy_weight_notification, 1496 context.getApplicationInfo().loadLabel(context.getPackageManager())); 1497 Notification notification = new Notification(); 1498 notification.icon = com.android.internal.R.drawable.stat_sys_adb; //context.getApplicationInfo().icon; 1499 notification.when = 0; 1500 notification.flags = Notification.FLAG_ONGOING_EVENT; 1501 notification.tickerText = text; 1502 notification.defaults = 0; // please be quiet 1503 notification.sound = null; 1504 notification.vibrate = null; 1505 notification.color = mContext.getResources().getColor( 1506 com.android.internal.R.color.system_notification_accent_color); 1507 notification.setLatestEventInfo(context, text, 1508 mContext.getText(R.string.heavy_weight_notification_detail), 1509 PendingIntent.getActivityAsUser(mContext, 0, root.intent, 1510 PendingIntent.FLAG_CANCEL_CURRENT, null, 1511 new UserHandle(root.userId))); 1512 1513 try { 1514 int[] outId = new int[1]; 1515 inm.enqueueNotificationWithTag("android", "android", null, 1516 R.string.heavy_weight_notification, 1517 notification, outId, root.userId); 1518 } catch (RuntimeException e) { 1519 Slog.w(ActivityManagerService.TAG, 1520 "Error showing notification for heavy-weight app", e); 1521 } catch (RemoteException e) { 1522 } 1523 } catch (NameNotFoundException e) { 1524 Slog.w(TAG, "Unable to create context for heavy notification", e); 1525 } 1526 } break; 1527 case CANCEL_HEAVY_NOTIFICATION_MSG: { 1528 INotificationManager inm = NotificationManager.getService(); 1529 if (inm == null) { 1530 return; 1531 } 1532 try { 1533 inm.cancelNotificationWithTag("android", null, 1534 R.string.heavy_weight_notification, msg.arg1); 1535 } catch (RuntimeException e) { 1536 Slog.w(ActivityManagerService.TAG, 1537 "Error canceling notification for service", e); 1538 } catch (RemoteException e) { 1539 } 1540 } break; 1541 case CHECK_EXCESSIVE_WAKE_LOCKS_MSG: { 1542 synchronized (ActivityManagerService.this) { 1543 checkExcessivePowerUsageLocked(true); 1544 removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1545 Message nmsg = obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1546 sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 1547 } 1548 } break; 1549 case SHOW_COMPAT_MODE_DIALOG_MSG: { 1550 synchronized (ActivityManagerService.this) { 1551 ActivityRecord ar = (ActivityRecord)msg.obj; 1552 if (mCompatModeDialog != null) { 1553 if (mCompatModeDialog.mAppInfo.packageName.equals( 1554 ar.info.applicationInfo.packageName)) { 1555 return; 1556 } 1557 mCompatModeDialog.dismiss(); 1558 mCompatModeDialog = null; 1559 } 1560 if (ar != null && false) { 1561 if (mCompatModePackages.getPackageAskCompatModeLocked( 1562 ar.packageName)) { 1563 int mode = mCompatModePackages.computeCompatModeLocked( 1564 ar.info.applicationInfo); 1565 if (mode == ActivityManager.COMPAT_MODE_DISABLED 1566 || mode == ActivityManager.COMPAT_MODE_ENABLED) { 1567 mCompatModeDialog = new CompatModeDialog( 1568 ActivityManagerService.this, mContext, 1569 ar.info.applicationInfo); 1570 mCompatModeDialog.show(); 1571 } 1572 } 1573 } 1574 } 1575 break; 1576 } 1577 case DISPATCH_PROCESSES_CHANGED: { 1578 dispatchProcessesChanged(); 1579 break; 1580 } 1581 case DISPATCH_PROCESS_DIED: { 1582 final int pid = msg.arg1; 1583 final int uid = msg.arg2; 1584 dispatchProcessDied(pid, uid); 1585 break; 1586 } 1587 case REPORT_MEM_USAGE_MSG: { 1588 final ArrayList<ProcessMemInfo> memInfos = (ArrayList<ProcessMemInfo>)msg.obj; 1589 Thread thread = new Thread() { 1590 @Override public void run() { 1591 final SparseArray<ProcessMemInfo> infoMap 1592 = new SparseArray<ProcessMemInfo>(memInfos.size()); 1593 for (int i=0, N=memInfos.size(); i<N; i++) { 1594 ProcessMemInfo mi = memInfos.get(i); 1595 infoMap.put(mi.pid, mi); 1596 } 1597 updateCpuStatsNow(); 1598 synchronized (mProcessCpuThread) { 1599 final int N = mProcessCpuTracker.countStats(); 1600 for (int i=0; i<N; i++) { 1601 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 1602 if (st.vsize > 0) { 1603 long pss = Debug.getPss(st.pid, null); 1604 if (pss > 0) { 1605 if (infoMap.indexOfKey(st.pid) < 0) { 1606 ProcessMemInfo mi = new ProcessMemInfo(st.name, st.pid, 1607 ProcessList.NATIVE_ADJ, -1, "native", null); 1608 mi.pss = pss; 1609 memInfos.add(mi); 1610 } 1611 } 1612 } 1613 } 1614 } 1615 1616 long totalPss = 0; 1617 for (int i=0, N=memInfos.size(); i<N; i++) { 1618 ProcessMemInfo mi = memInfos.get(i); 1619 if (mi.pss == 0) { 1620 mi.pss = Debug.getPss(mi.pid, null); 1621 } 1622 totalPss += mi.pss; 1623 } 1624 Collections.sort(memInfos, new Comparator<ProcessMemInfo>() { 1625 @Override public int compare(ProcessMemInfo lhs, ProcessMemInfo rhs) { 1626 if (lhs.oomAdj != rhs.oomAdj) { 1627 return lhs.oomAdj < rhs.oomAdj ? -1 : 1; 1628 } 1629 if (lhs.pss != rhs.pss) { 1630 return lhs.pss < rhs.pss ? 1 : -1; 1631 } 1632 return 0; 1633 } 1634 }); 1635 1636 StringBuilder tag = new StringBuilder(128); 1637 StringBuilder stack = new StringBuilder(128); 1638 tag.append("Low on memory -- "); 1639 appendMemBucket(tag, totalPss, "total", false); 1640 appendMemBucket(stack, totalPss, "total", true); 1641 1642 StringBuilder logBuilder = new StringBuilder(1024); 1643 logBuilder.append("Low on memory:\n"); 1644 1645 boolean firstLine = true; 1646 int lastOomAdj = Integer.MIN_VALUE; 1647 for (int i=0, N=memInfos.size(); i<N; i++) { 1648 ProcessMemInfo mi = memInfos.get(i); 1649 1650 if (mi.oomAdj != ProcessList.NATIVE_ADJ 1651 && (mi.oomAdj < ProcessList.SERVICE_ADJ 1652 || mi.oomAdj == ProcessList.HOME_APP_ADJ 1653 || mi.oomAdj == ProcessList.PREVIOUS_APP_ADJ)) { 1654 if (lastOomAdj != mi.oomAdj) { 1655 lastOomAdj = mi.oomAdj; 1656 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1657 tag.append(" / "); 1658 } 1659 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ) { 1660 if (firstLine) { 1661 stack.append(":"); 1662 firstLine = false; 1663 } 1664 stack.append("\n\t at "); 1665 } else { 1666 stack.append("$"); 1667 } 1668 } else { 1669 tag.append(" "); 1670 stack.append("$"); 1671 } 1672 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1673 appendMemBucket(tag, mi.pss, mi.name, false); 1674 } 1675 appendMemBucket(stack, mi.pss, mi.name, true); 1676 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ 1677 && ((i+1) >= N || memInfos.get(i+1).oomAdj != lastOomAdj)) { 1678 stack.append("("); 1679 for (int k=0; k<DUMP_MEM_OOM_ADJ.length; k++) { 1680 if (DUMP_MEM_OOM_ADJ[k] == mi.oomAdj) { 1681 stack.append(DUMP_MEM_OOM_LABEL[k]); 1682 stack.append(":"); 1683 stack.append(DUMP_MEM_OOM_ADJ[k]); 1684 } 1685 } 1686 stack.append(")"); 1687 } 1688 } 1689 1690 logBuilder.append(" "); 1691 logBuilder.append(ProcessList.makeOomAdjString(mi.oomAdj)); 1692 logBuilder.append(' '); 1693 logBuilder.append(ProcessList.makeProcStateString(mi.procState)); 1694 logBuilder.append(' '); 1695 ProcessList.appendRamKb(logBuilder, mi.pss); 1696 logBuilder.append(" kB: "); 1697 logBuilder.append(mi.name); 1698 logBuilder.append(" ("); 1699 logBuilder.append(mi.pid); 1700 logBuilder.append(") "); 1701 logBuilder.append(mi.adjType); 1702 logBuilder.append('\n'); 1703 if (mi.adjReason != null) { 1704 logBuilder.append(" "); 1705 logBuilder.append(mi.adjReason); 1706 logBuilder.append('\n'); 1707 } 1708 } 1709 1710 logBuilder.append(" "); 1711 ProcessList.appendRamKb(logBuilder, totalPss); 1712 logBuilder.append(" kB: TOTAL\n"); 1713 1714 long[] infos = new long[Debug.MEMINFO_COUNT]; 1715 Debug.getMemInfo(infos); 1716 logBuilder.append(" MemInfo: "); 1717 logBuilder.append(infos[Debug.MEMINFO_SLAB]).append(" kB slab, "); 1718 logBuilder.append(infos[Debug.MEMINFO_SHMEM]).append(" kB shmem, "); 1719 logBuilder.append(infos[Debug.MEMINFO_BUFFERS]).append(" kB buffers, "); 1720 logBuilder.append(infos[Debug.MEMINFO_CACHED]).append(" kB cached, "); 1721 logBuilder.append(infos[Debug.MEMINFO_FREE]).append(" kB free\n"); 1722 if (infos[Debug.MEMINFO_ZRAM_TOTAL] != 0) { 1723 logBuilder.append(" ZRAM: "); 1724 logBuilder.append(infos[Debug.MEMINFO_ZRAM_TOTAL]); 1725 logBuilder.append(" kB RAM, "); 1726 logBuilder.append(infos[Debug.MEMINFO_SWAP_TOTAL]); 1727 logBuilder.append(" kB swap total, "); 1728 logBuilder.append(infos[Debug.MEMINFO_SWAP_FREE]); 1729 logBuilder.append(" kB swap free\n"); 1730 } 1731 Slog.i(TAG, logBuilder.toString()); 1732 1733 StringBuilder dropBuilder = new StringBuilder(1024); 1734 /* 1735 StringWriter oomSw = new StringWriter(); 1736 PrintWriter oomPw = new FastPrintWriter(oomSw, false, 256); 1737 StringWriter catSw = new StringWriter(); 1738 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1739 String[] emptyArgs = new String[] { }; 1740 dumpApplicationMemoryUsage(null, oomPw, " ", emptyArgs, true, catPw); 1741 oomPw.flush(); 1742 String oomString = oomSw.toString(); 1743 */ 1744 dropBuilder.append(stack); 1745 dropBuilder.append('\n'); 1746 dropBuilder.append('\n'); 1747 dropBuilder.append(logBuilder); 1748 dropBuilder.append('\n'); 1749 /* 1750 dropBuilder.append(oomString); 1751 dropBuilder.append('\n'); 1752 */ 1753 StringWriter catSw = new StringWriter(); 1754 synchronized (ActivityManagerService.this) { 1755 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1756 String[] emptyArgs = new String[] { }; 1757 catPw.println(); 1758 dumpProcessesLocked(null, catPw, emptyArgs, 0, false, null); 1759 catPw.println(); 1760 mServices.dumpServicesLocked(null, catPw, emptyArgs, 0, 1761 false, false, null); 1762 catPw.println(); 1763 dumpActivitiesLocked(null, catPw, emptyArgs, 0, false, false, null); 1764 catPw.flush(); 1765 } 1766 dropBuilder.append(catSw.toString()); 1767 addErrorToDropBox("lowmem", null, "system_server", null, 1768 null, tag.toString(), dropBuilder.toString(), null, null); 1769 //Slog.i(TAG, "Sent to dropbox:"); 1770 //Slog.i(TAG, dropBuilder.toString()); 1771 synchronized (ActivityManagerService.this) { 1772 long now = SystemClock.uptimeMillis(); 1773 if (mLastMemUsageReportTime < now) { 1774 mLastMemUsageReportTime = now; 1775 } 1776 } 1777 } 1778 }; 1779 thread.start(); 1780 break; 1781 } 1782 case START_USER_SWITCH_MSG: { 1783 showUserSwitchDialog(msg.arg1, (String) msg.obj); 1784 break; 1785 } 1786 case REPORT_USER_SWITCH_MSG: { 1787 dispatchUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1788 break; 1789 } 1790 case CONTINUE_USER_SWITCH_MSG: { 1791 continueUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1792 break; 1793 } 1794 case USER_SWITCH_TIMEOUT_MSG: { 1795 timeoutUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1796 break; 1797 } 1798 case IMMERSIVE_MODE_LOCK_MSG: { 1799 final boolean nextState = (msg.arg1 != 0); 1800 if (mUpdateLock.isHeld() != nextState) { 1801 if (DEBUG_IMMERSIVE) { 1802 final ActivityRecord r = (ActivityRecord) msg.obj; 1803 Slog.d(TAG, "Applying new update lock state '" + nextState + "' for " + r); 1804 } 1805 if (nextState) { 1806 mUpdateLock.acquire(); 1807 } else { 1808 mUpdateLock.release(); 1809 } 1810 } 1811 break; 1812 } 1813 case PERSIST_URI_GRANTS_MSG: { 1814 writeGrantedUriPermissions(); 1815 break; 1816 } 1817 case REQUEST_ALL_PSS_MSG: { 1818 requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, false); 1819 break; 1820 } 1821 case START_PROFILES_MSG: { 1822 synchronized (ActivityManagerService.this) { 1823 startProfilesLocked(); 1824 } 1825 break; 1826 } 1827 case UPDATE_TIME: { 1828 synchronized (ActivityManagerService.this) { 1829 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1830 ProcessRecord r = mLruProcesses.get(i); 1831 if (r.thread != null) { 1832 try { 1833 r.thread.updateTimePrefs(msg.arg1 == 0 ? false : true); 1834 } catch (RemoteException ex) { 1835 Slog.w(TAG, "Failed to update preferences for: " + r.info.processName); 1836 } 1837 } 1838 } 1839 } 1840 break; 1841 } 1842 case SYSTEM_USER_START_MSG: { 1843 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 1844 Integer.toString(msg.arg1), msg.arg1); 1845 mSystemServiceManager.startUser(msg.arg1); 1846 break; 1847 } 1848 case SYSTEM_USER_CURRENT_MSG: { 1849 mBatteryStatsService.noteEvent( 1850 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_FINISH, 1851 Integer.toString(msg.arg2), msg.arg2); 1852 mBatteryStatsService.noteEvent( 1853 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 1854 Integer.toString(msg.arg1), msg.arg1); 1855 mSystemServiceManager.switchUser(msg.arg1); 1856 mLockToAppRequest.clearPrompt(); 1857 break; 1858 } 1859 case ENTER_ANIMATION_COMPLETE_MSG: { 1860 synchronized (ActivityManagerService.this) { 1861 ActivityRecord r = ActivityRecord.forToken((IBinder) msg.obj); 1862 if (r != null && r.app != null && r.app.thread != null) { 1863 try { 1864 r.app.thread.scheduleEnterAnimationComplete(r.appToken); 1865 } catch (RemoteException e) { 1866 } 1867 } 1868 } 1869 break; 1870 } 1871 case ENABLE_SCREEN_AFTER_BOOT_MSG: { 1872 enableScreenAfterBoot(); 1873 break; 1874 } 1875 } 1876 } 1877 }; 1878 1879 static final int COLLECT_PSS_BG_MSG = 1; 1880 1881 final Handler mBgHandler = new Handler(BackgroundThread.getHandler().getLooper()) { 1882 @Override 1883 public void handleMessage(Message msg) { 1884 switch (msg.what) { 1885 case COLLECT_PSS_BG_MSG: { 1886 long start = SystemClock.uptimeMillis(); 1887 MemInfoReader memInfo = null; 1888 synchronized (ActivityManagerService.this) { 1889 if (mFullPssPending) { 1890 mFullPssPending = false; 1891 memInfo = new MemInfoReader(); 1892 } 1893 } 1894 if (memInfo != null) { 1895 updateCpuStatsNow(); 1896 long nativeTotalPss = 0; 1897 synchronized (mProcessCpuThread) { 1898 final int N = mProcessCpuTracker.countStats(); 1899 for (int j=0; j<N; j++) { 1900 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(j); 1901 if (st.vsize <= 0 || st.uid >= Process.FIRST_APPLICATION_UID) { 1902 // This is definitely an application process; skip it. 1903 continue; 1904 } 1905 synchronized (mPidsSelfLocked) { 1906 if (mPidsSelfLocked.indexOfKey(st.pid) >= 0) { 1907 // This is one of our own processes; skip it. 1908 continue; 1909 } 1910 } 1911 nativeTotalPss += Debug.getPss(st.pid, null); 1912 } 1913 } 1914 memInfo.readMemInfo(); 1915 synchronized (this) { 1916 if (DEBUG_PSS) Slog.d(TAG, "Collected native and kernel memory in " 1917 + (SystemClock.uptimeMillis()-start) + "ms"); 1918 mProcessStats.addSysMemUsageLocked(memInfo.getCachedSizeKb(), 1919 memInfo.getFreeSizeKb(), memInfo.getZramTotalSizeKb(), 1920 memInfo.getBuffersSizeKb()+memInfo.getShmemSizeKb() 1921 +memInfo.getSlabSizeKb(), 1922 nativeTotalPss); 1923 } 1924 } 1925 1926 int i=0, num=0; 1927 long[] tmp = new long[1]; 1928 do { 1929 ProcessRecord proc; 1930 int procState; 1931 int pid; 1932 synchronized (ActivityManagerService.this) { 1933 if (i >= mPendingPssProcesses.size()) { 1934 if (DEBUG_PSS) Slog.d(TAG, "Collected PSS of " + num + " of " + i 1935 + " processes in " + (SystemClock.uptimeMillis()-start) + "ms"); 1936 mPendingPssProcesses.clear(); 1937 return; 1938 } 1939 proc = mPendingPssProcesses.get(i); 1940 procState = proc.pssProcState; 1941 if (proc.thread != null && procState == proc.setProcState) { 1942 pid = proc.pid; 1943 } else { 1944 proc = null; 1945 pid = 0; 1946 } 1947 i++; 1948 } 1949 if (proc != null) { 1950 long pss = Debug.getPss(pid, tmp); 1951 synchronized (ActivityManagerService.this) { 1952 if (proc.thread != null && proc.setProcState == procState 1953 && proc.pid == pid) { 1954 num++; 1955 proc.lastPssTime = SystemClock.uptimeMillis(); 1956 proc.baseProcessTracker.addPss(pss, tmp[0], true, proc.pkgList); 1957 if (DEBUG_PSS) Slog.d(TAG, "PSS of " + proc.toShortString() 1958 + ": " + pss + " lastPss=" + proc.lastPss 1959 + " state=" + ProcessList.makeProcStateString(procState)); 1960 if (proc.initialIdlePss == 0) { 1961 proc.initialIdlePss = pss; 1962 } 1963 proc.lastPss = pss; 1964 if (procState >= ActivityManager.PROCESS_STATE_HOME) { 1965 proc.lastCachedPss = pss; 1966 } 1967 } 1968 } 1969 } 1970 } while (true); 1971 } 1972 } 1973 } 1974 }; 1975 1976 /** 1977 * Monitor for package changes and update our internal state. 1978 */ 1979 private final PackageMonitor mPackageMonitor = new PackageMonitor() { 1980 @Override 1981 public void onPackageRemoved(String packageName, int uid) { 1982 // Remove all tasks with activities in the specified package from the list of recent tasks 1983 synchronized (ActivityManagerService.this) { 1984 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 1985 TaskRecord tr = mRecentTasks.get(i); 1986 ComponentName cn = tr.intent.getComponent(); 1987 if (cn != null && cn.getPackageName().equals(packageName)) { 1988 // If the package name matches, remove the task and kill the process 1989 removeTaskByIdLocked(tr.taskId, ActivityManager.REMOVE_TASK_KILL_PROCESS); 1990 } 1991 } 1992 } 1993 } 1994 1995 @Override 1996 public boolean onPackageChanged(String packageName, int uid, String[] components) { 1997 onPackageModified(packageName); 1998 return true; 1999 } 2000 2001 @Override 2002 public void onPackageModified(String packageName) { 2003 final PackageManager pm = mContext.getPackageManager(); 2004 final ArrayList<Pair<Intent, Integer>> recentTaskIntents = 2005 new ArrayList<Pair<Intent, Integer>>(); 2006 final ArrayList<Integer> tasksToRemove = new ArrayList<Integer>(); 2007 // Copy the list of recent tasks so that we don't hold onto the lock on 2008 // ActivityManagerService for long periods while checking if components exist. 2009 synchronized (ActivityManagerService.this) { 2010 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 2011 TaskRecord tr = mRecentTasks.get(i); 2012 recentTaskIntents.add(new Pair<Intent, Integer>(tr.intent, tr.taskId)); 2013 } 2014 } 2015 // Check the recent tasks and filter out all tasks with components that no longer exist. 2016 Intent tmpI = new Intent(); 2017 for (int i = recentTaskIntents.size() - 1; i >= 0; i--) { 2018 Pair<Intent, Integer> p = recentTaskIntents.get(i); 2019 ComponentName cn = p.first.getComponent(); 2020 if (cn != null && cn.getPackageName().equals(packageName)) { 2021 try { 2022 // Add the task to the list to remove if the component no longer exists 2023 tmpI.setComponent(cn); 2024 if (pm.queryIntentActivities(tmpI, PackageManager.MATCH_DEFAULT_ONLY).isEmpty()) { 2025 tasksToRemove.add(p.second); 2026 } 2027 } catch (Exception e) {} 2028 } 2029 } 2030 // Prune all the tasks with removed components from the list of recent tasks 2031 synchronized (ActivityManagerService.this) { 2032 for (int i = tasksToRemove.size() - 1; i >= 0; i--) { 2033 // Remove the task but don't kill the process (since other components in that 2034 // package may still be running and in the background) 2035 removeTaskByIdLocked(tasksToRemove.get(i), 0); 2036 } 2037 } 2038 } 2039 2040 @Override 2041 public boolean onHandleForceStop(Intent intent, String[] packages, int uid, boolean doit) { 2042 // Force stop the specified packages 2043 if (packages != null) { 2044 for (String pkg : packages) { 2045 synchronized (ActivityManagerService.this) { 2046 if (forceStopPackageLocked(pkg, -1, false, false, false, false, false, 0, 2047 "finished booting")) { 2048 return true; 2049 } 2050 } 2051 } 2052 } 2053 return false; 2054 } 2055 }; 2056 2057 public void setSystemProcess() { 2058 try { 2059 ServiceManager.addService(Context.ACTIVITY_SERVICE, this, true); 2060 ServiceManager.addService(ProcessStats.SERVICE_NAME, mProcessStats); 2061 ServiceManager.addService("meminfo", new MemBinder(this)); 2062 ServiceManager.addService("gfxinfo", new GraphicsBinder(this)); 2063 ServiceManager.addService("dbinfo", new DbBinder(this)); 2064 if (MONITOR_CPU_USAGE) { 2065 ServiceManager.addService("cpuinfo", new CpuBinder(this)); 2066 } 2067 ServiceManager.addService("permission", new PermissionController(this)); 2068 2069 ApplicationInfo info = mContext.getPackageManager().getApplicationInfo( 2070 "android", STOCK_PM_FLAGS); 2071 mSystemThread.installSystemApplicationInfo(info, getClass().getClassLoader()); 2072 2073 synchronized (this) { 2074 ProcessRecord app = newProcessRecordLocked(info, info.processName, false, 0); 2075 app.persistent = true; 2076 app.pid = MY_PID; 2077 app.maxAdj = ProcessList.SYSTEM_ADJ; 2078 app.makeActive(mSystemThread.getApplicationThread(), mProcessStats); 2079 mProcessNames.put(app.processName, app.uid, app); 2080 synchronized (mPidsSelfLocked) { 2081 mPidsSelfLocked.put(app.pid, app); 2082 } 2083 updateLruProcessLocked(app, false, null); 2084 updateOomAdjLocked(); 2085 } 2086 } catch (PackageManager.NameNotFoundException e) { 2087 throw new RuntimeException( 2088 "Unable to find android system package", e); 2089 } 2090 } 2091 2092 public void setWindowManager(WindowManagerService wm) { 2093 mWindowManager = wm; 2094 mStackSupervisor.setWindowManager(wm); 2095 } 2096 2097 public void setUsageStatsManager(UsageStatsManagerInternal usageStatsManager) { 2098 mUsageStatsService = usageStatsManager; 2099 } 2100 2101 public void startObservingNativeCrashes() { 2102 final NativeCrashListener ncl = new NativeCrashListener(this); 2103 ncl.start(); 2104 } 2105 2106 public IAppOpsService getAppOpsService() { 2107 return mAppOpsService; 2108 } 2109 2110 static class MemBinder extends Binder { 2111 ActivityManagerService mActivityManagerService; 2112 MemBinder(ActivityManagerService activityManagerService) { 2113 mActivityManagerService = activityManagerService; 2114 } 2115 2116 @Override 2117 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2118 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2119 != PackageManager.PERMISSION_GRANTED) { 2120 pw.println("Permission Denial: can't dump meminfo from from pid=" 2121 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2122 + " without permission " + android.Manifest.permission.DUMP); 2123 return; 2124 } 2125 2126 mActivityManagerService.dumpApplicationMemoryUsage(fd, pw, " ", args, false, null); 2127 } 2128 } 2129 2130 static class GraphicsBinder extends Binder { 2131 ActivityManagerService mActivityManagerService; 2132 GraphicsBinder(ActivityManagerService activityManagerService) { 2133 mActivityManagerService = activityManagerService; 2134 } 2135 2136 @Override 2137 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2138 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2139 != PackageManager.PERMISSION_GRANTED) { 2140 pw.println("Permission Denial: can't dump gfxinfo from from pid=" 2141 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2142 + " without permission " + android.Manifest.permission.DUMP); 2143 return; 2144 } 2145 2146 mActivityManagerService.dumpGraphicsHardwareUsage(fd, pw, args); 2147 } 2148 } 2149 2150 static class DbBinder extends Binder { 2151 ActivityManagerService mActivityManagerService; 2152 DbBinder(ActivityManagerService activityManagerService) { 2153 mActivityManagerService = activityManagerService; 2154 } 2155 2156 @Override 2157 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2158 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2159 != PackageManager.PERMISSION_GRANTED) { 2160 pw.println("Permission Denial: can't dump dbinfo from from pid=" 2161 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2162 + " without permission " + android.Manifest.permission.DUMP); 2163 return; 2164 } 2165 2166 mActivityManagerService.dumpDbInfo(fd, pw, args); 2167 } 2168 } 2169 2170 static class CpuBinder extends Binder { 2171 ActivityManagerService mActivityManagerService; 2172 CpuBinder(ActivityManagerService activityManagerService) { 2173 mActivityManagerService = activityManagerService; 2174 } 2175 2176 @Override 2177 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2178 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2179 != PackageManager.PERMISSION_GRANTED) { 2180 pw.println("Permission Denial: can't dump cpuinfo from from pid=" 2181 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2182 + " without permission " + android.Manifest.permission.DUMP); 2183 return; 2184 } 2185 2186 synchronized (mActivityManagerService.mProcessCpuThread) { 2187 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentLoad()); 2188 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentState( 2189 SystemClock.uptimeMillis())); 2190 } 2191 } 2192 } 2193 2194 public static final class Lifecycle extends SystemService { 2195 private final ActivityManagerService mService; 2196 2197 public Lifecycle(Context context) { 2198 super(context); 2199 mService = new ActivityManagerService(context); 2200 } 2201 2202 @Override 2203 public void onStart() { 2204 mService.start(); 2205 } 2206 2207 public ActivityManagerService getService() { 2208 return mService; 2209 } 2210 } 2211 2212 // Note: This method is invoked on the main thread but may need to attach various 2213 // handlers to other threads. So take care to be explicit about the looper. 2214 public ActivityManagerService(Context systemContext) { 2215 mContext = systemContext; 2216 mFactoryTest = FactoryTest.getMode(); 2217 mSystemThread = ActivityThread.currentActivityThread(); 2218 2219 Slog.i(TAG, "Memory class: " + ActivityManager.staticGetMemoryClass()); 2220 2221 mHandlerThread = new ServiceThread(TAG, 2222 android.os.Process.THREAD_PRIORITY_FOREGROUND, false /*allowIo*/); 2223 mHandlerThread.start(); 2224 mHandler = new MainHandler(mHandlerThread.getLooper()); 2225 2226 mFgBroadcastQueue = new BroadcastQueue(this, mHandler, 2227 "foreground", BROADCAST_FG_TIMEOUT, false); 2228 mBgBroadcastQueue = new BroadcastQueue(this, mHandler, 2229 "background", BROADCAST_BG_TIMEOUT, true); 2230 mBroadcastQueues[0] = mFgBroadcastQueue; 2231 mBroadcastQueues[1] = mBgBroadcastQueue; 2232 2233 mServices = new ActiveServices(this); 2234 mProviderMap = new ProviderMap(this); 2235 2236 // TODO: Move creation of battery stats service outside of activity manager service. 2237 File dataDir = Environment.getDataDirectory(); 2238 File systemDir = new File(dataDir, "system"); 2239 systemDir.mkdirs(); 2240 mBatteryStatsService = new BatteryStatsService(systemDir, mHandler); 2241 mBatteryStatsService.getActiveStatistics().readLocked(); 2242 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2243 mOnBattery = DEBUG_POWER ? true 2244 : mBatteryStatsService.getActiveStatistics().getIsOnBattery(); 2245 mBatteryStatsService.getActiveStatistics().setCallback(this); 2246 2247 mProcessStats = new ProcessStatsService(this, new File(systemDir, "procstats")); 2248 2249 mAppOpsService = new AppOpsService(new File(systemDir, "appops.xml"), mHandler); 2250 2251 mGrantFile = new AtomicFile(new File(systemDir, "urigrants.xml")); 2252 2253 // User 0 is the first and only user that runs at boot. 2254 mStartedUsers.put(0, new UserStartedState(new UserHandle(0), true)); 2255 mUserLru.add(Integer.valueOf(0)); 2256 updateStartedUserArrayLocked(); 2257 2258 GL_ES_VERSION = SystemProperties.getInt("ro.opengles.version", 2259 ConfigurationInfo.GL_ES_VERSION_UNDEFINED); 2260 2261 mConfiguration.setToDefaults(); 2262 mConfiguration.setLocale(Locale.getDefault()); 2263 2264 mConfigurationSeq = mConfiguration.seq = 1; 2265 mProcessCpuTracker.init(); 2266 2267 mCompatModePackages = new CompatModePackages(this, systemDir, mHandler); 2268 mIntentFirewall = new IntentFirewall(new IntentFirewallInterface(), mHandler); 2269 mStackSupervisor = new ActivityStackSupervisor(this); 2270 mTaskPersister = new TaskPersister(systemDir, mStackSupervisor); 2271 2272 mProcessCpuThread = new Thread("CpuTracker") { 2273 @Override 2274 public void run() { 2275 while (true) { 2276 try { 2277 try { 2278 synchronized(this) { 2279 final long now = SystemClock.uptimeMillis(); 2280 long nextCpuDelay = (mLastCpuTime.get()+MONITOR_CPU_MAX_TIME)-now; 2281 long nextWriteDelay = (mLastWriteTime+BATTERY_STATS_TIME)-now; 2282 //Slog.i(TAG, "Cpu delay=" + nextCpuDelay 2283 // + ", write delay=" + nextWriteDelay); 2284 if (nextWriteDelay < nextCpuDelay) { 2285 nextCpuDelay = nextWriteDelay; 2286 } 2287 if (nextCpuDelay > 0) { 2288 mProcessCpuMutexFree.set(true); 2289 this.wait(nextCpuDelay); 2290 } 2291 } 2292 } catch (InterruptedException e) { 2293 } 2294 updateCpuStatsNow(); 2295 } catch (Exception e) { 2296 Slog.e(TAG, "Unexpected exception collecting process stats", e); 2297 } 2298 } 2299 } 2300 }; 2301 2302 mLockToAppRequest = new LockToAppRequestDialog(mContext, this); 2303 2304 Watchdog.getInstance().addMonitor(this); 2305 Watchdog.getInstance().addThread(mHandler); 2306 } 2307 2308 public void setSystemServiceManager(SystemServiceManager mgr) { 2309 mSystemServiceManager = mgr; 2310 } 2311 2312 private void start() { 2313 Process.removeAllProcessGroups(); 2314 mProcessCpuThread.start(); 2315 2316 mBatteryStatsService.publish(mContext); 2317 mAppOpsService.publish(mContext); 2318 Slog.d("AppOps", "AppOpsService published"); 2319 LocalServices.addService(ActivityManagerInternal.class, new LocalService()); 2320 } 2321 2322 public void initPowerManagement() { 2323 mStackSupervisor.initPowerManagement(); 2324 mBatteryStatsService.initPowerManagement(); 2325 } 2326 2327 @Override 2328 public boolean onTransact(int code, Parcel data, Parcel reply, int flags) 2329 throws RemoteException { 2330 if (code == SYSPROPS_TRANSACTION) { 2331 // We need to tell all apps about the system property change. 2332 ArrayList<IBinder> procs = new ArrayList<IBinder>(); 2333 synchronized(this) { 2334 final int NP = mProcessNames.getMap().size(); 2335 for (int ip=0; ip<NP; ip++) { 2336 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 2337 final int NA = apps.size(); 2338 for (int ia=0; ia<NA; ia++) { 2339 ProcessRecord app = apps.valueAt(ia); 2340 if (app.thread != null) { 2341 procs.add(app.thread.asBinder()); 2342 } 2343 } 2344 } 2345 } 2346 2347 int N = procs.size(); 2348 for (int i=0; i<N; i++) { 2349 Parcel data2 = Parcel.obtain(); 2350 try { 2351 procs.get(i).transact(IBinder.SYSPROPS_TRANSACTION, data2, null, 0); 2352 } catch (RemoteException e) { 2353 } 2354 data2.recycle(); 2355 } 2356 } 2357 try { 2358 return super.onTransact(code, data, reply, flags); 2359 } catch (RuntimeException e) { 2360 // The activity manager only throws security exceptions, so let's 2361 // log all others. 2362 if (!(e instanceof SecurityException)) { 2363 Slog.wtf(TAG, "Activity Manager Crash", e); 2364 } 2365 throw e; 2366 } 2367 } 2368 2369 void updateCpuStats() { 2370 final long now = SystemClock.uptimeMillis(); 2371 if (mLastCpuTime.get() >= now - MONITOR_CPU_MIN_TIME) { 2372 return; 2373 } 2374 if (mProcessCpuMutexFree.compareAndSet(true, false)) { 2375 synchronized (mProcessCpuThread) { 2376 mProcessCpuThread.notify(); 2377 } 2378 } 2379 } 2380 2381 void updateCpuStatsNow() { 2382 synchronized (mProcessCpuThread) { 2383 mProcessCpuMutexFree.set(false); 2384 final long now = SystemClock.uptimeMillis(); 2385 boolean haveNewCpuStats = false; 2386 2387 if (MONITOR_CPU_USAGE && 2388 mLastCpuTime.get() < (now-MONITOR_CPU_MIN_TIME)) { 2389 mLastCpuTime.set(now); 2390 haveNewCpuStats = true; 2391 mProcessCpuTracker.update(); 2392 //Slog.i(TAG, mProcessCpu.printCurrentState()); 2393 //Slog.i(TAG, "Total CPU usage: " 2394 // + mProcessCpu.getTotalCpuPercent() + "%"); 2395 2396 // Slog the cpu usage if the property is set. 2397 if ("true".equals(SystemProperties.get("events.cpu"))) { 2398 int user = mProcessCpuTracker.getLastUserTime(); 2399 int system = mProcessCpuTracker.getLastSystemTime(); 2400 int iowait = mProcessCpuTracker.getLastIoWaitTime(); 2401 int irq = mProcessCpuTracker.getLastIrqTime(); 2402 int softIrq = mProcessCpuTracker.getLastSoftIrqTime(); 2403 int idle = mProcessCpuTracker.getLastIdleTime(); 2404 2405 int total = user + system + iowait + irq + softIrq + idle; 2406 if (total == 0) total = 1; 2407 2408 EventLog.writeEvent(EventLogTags.CPU, 2409 ((user+system+iowait+irq+softIrq) * 100) / total, 2410 (user * 100) / total, 2411 (system * 100) / total, 2412 (iowait * 100) / total, 2413 (irq * 100) / total, 2414 (softIrq * 100) / total); 2415 } 2416 } 2417 2418 long[] cpuSpeedTimes = mProcessCpuTracker.getLastCpuSpeedTimes(); 2419 final BatteryStatsImpl bstats = mBatteryStatsService.getActiveStatistics(); 2420 synchronized(bstats) { 2421 synchronized(mPidsSelfLocked) { 2422 if (haveNewCpuStats) { 2423 if (mOnBattery) { 2424 int perc = bstats.startAddingCpuLocked(); 2425 int totalUTime = 0; 2426 int totalSTime = 0; 2427 final int N = mProcessCpuTracker.countStats(); 2428 for (int i=0; i<N; i++) { 2429 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 2430 if (!st.working) { 2431 continue; 2432 } 2433 ProcessRecord pr = mPidsSelfLocked.get(st.pid); 2434 int otherUTime = (st.rel_utime*perc)/100; 2435 int otherSTime = (st.rel_stime*perc)/100; 2436 totalUTime += otherUTime; 2437 totalSTime += otherSTime; 2438 if (pr != null) { 2439 BatteryStatsImpl.Uid.Proc ps = pr.curProcBatteryStats; 2440 if (ps == null || !ps.isActive()) { 2441 pr.curProcBatteryStats = ps = bstats.getProcessStatsLocked( 2442 pr.info.uid, pr.processName); 2443 } 2444 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2445 st.rel_stime-otherSTime); 2446 ps.addSpeedStepTimes(cpuSpeedTimes); 2447 pr.curCpuTime += (st.rel_utime+st.rel_stime) * 10; 2448 } else { 2449 BatteryStatsImpl.Uid.Proc ps = st.batteryStats; 2450 if (ps == null || !ps.isActive()) { 2451 st.batteryStats = ps = bstats.getProcessStatsLocked( 2452 bstats.mapUid(st.uid), st.name); 2453 } 2454 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2455 st.rel_stime-otherSTime); 2456 ps.addSpeedStepTimes(cpuSpeedTimes); 2457 } 2458 } 2459 bstats.finishAddingCpuLocked(perc, totalUTime, 2460 totalSTime, cpuSpeedTimes); 2461 } 2462 } 2463 } 2464 2465 if (mLastWriteTime < (now-BATTERY_STATS_TIME)) { 2466 mLastWriteTime = now; 2467 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2468 } 2469 } 2470 } 2471 } 2472 2473 @Override 2474 public void batteryNeedsCpuUpdate() { 2475 updateCpuStatsNow(); 2476 } 2477 2478 @Override 2479 public void batteryPowerChanged(boolean onBattery) { 2480 // When plugging in, update the CPU stats first before changing 2481 // the plug state. 2482 updateCpuStatsNow(); 2483 synchronized (this) { 2484 synchronized(mPidsSelfLocked) { 2485 mOnBattery = DEBUG_POWER ? true : onBattery; 2486 } 2487 } 2488 } 2489 2490 /** 2491 * Initialize the application bind args. These are passed to each 2492 * process when the bindApplication() IPC is sent to the process. They're 2493 * lazily setup to make sure the services are running when they're asked for. 2494 */ 2495 private HashMap<String, IBinder> getCommonServicesLocked() { 2496 if (mAppBindArgs == null) { 2497 mAppBindArgs = new HashMap<String, IBinder>(); 2498 2499 // Setup the application init args 2500 mAppBindArgs.put("package", ServiceManager.getService("package")); 2501 mAppBindArgs.put("window", ServiceManager.getService("window")); 2502 mAppBindArgs.put(Context.ALARM_SERVICE, 2503 ServiceManager.getService(Context.ALARM_SERVICE)); 2504 } 2505 return mAppBindArgs; 2506 } 2507 2508 final void setFocusedActivityLocked(ActivityRecord r) { 2509 if (mFocusedActivity != r) { 2510 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedActivityLocked: r=" + r); 2511 mFocusedActivity = r; 2512 if (r.task != null && r.task.voiceInteractor != null) { 2513 startRunningVoiceLocked(); 2514 } else { 2515 finishRunningVoiceLocked(); 2516 } 2517 mStackSupervisor.setFocusedStack(r); 2518 if (r != null) { 2519 mWindowManager.setFocusedApp(r.appToken, true); 2520 } 2521 applyUpdateLockStateLocked(r); 2522 } 2523 } 2524 2525 final void clearFocusedActivity(ActivityRecord r) { 2526 if (mFocusedActivity == r) { 2527 mFocusedActivity = null; 2528 } 2529 } 2530 2531 @Override 2532 public void setFocusedStack(int stackId) { 2533 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedStack: stackId=" + stackId); 2534 synchronized (ActivityManagerService.this) { 2535 ActivityStack stack = mStackSupervisor.getStack(stackId); 2536 if (stack != null) { 2537 ActivityRecord r = stack.topRunningActivityLocked(null); 2538 if (r != null) { 2539 setFocusedActivityLocked(r); 2540 } 2541 } 2542 } 2543 } 2544 2545 @Override 2546 public void notifyActivityDrawn(IBinder token) { 2547 if (DEBUG_VISBILITY) Slog.d(TAG, "notifyActivityDrawn: token=" + token); 2548 synchronized (this) { 2549 ActivityRecord r= mStackSupervisor.isInAnyStackLocked(token); 2550 if (r != null) { 2551 r.task.stack.notifyActivityDrawnLocked(r); 2552 } 2553 } 2554 } 2555 2556 final void applyUpdateLockStateLocked(ActivityRecord r) { 2557 // Modifications to the UpdateLock state are done on our handler, outside 2558 // the activity manager's locks. The new state is determined based on the 2559 // state *now* of the relevant activity record. The object is passed to 2560 // the handler solely for logging detail, not to be consulted/modified. 2561 final boolean nextState = r != null && r.immersive; 2562 mHandler.sendMessage( 2563 mHandler.obtainMessage(IMMERSIVE_MODE_LOCK_MSG, (nextState) ? 1 : 0, 0, r)); 2564 } 2565 2566 final void showAskCompatModeDialogLocked(ActivityRecord r) { 2567 Message msg = Message.obtain(); 2568 msg.what = SHOW_COMPAT_MODE_DIALOG_MSG; 2569 msg.obj = r.task.askedCompatMode ? null : r; 2570 mHandler.sendMessage(msg); 2571 } 2572 2573 private final int updateLruProcessInternalLocked(ProcessRecord app, long now, int index, 2574 String what, Object obj, ProcessRecord srcApp) { 2575 app.lastActivityTime = now; 2576 2577 if (app.activities.size() > 0) { 2578 // Don't want to touch dependent processes that are hosting activities. 2579 return index; 2580 } 2581 2582 int lrui = mLruProcesses.lastIndexOf(app); 2583 if (lrui < 0) { 2584 Slog.wtf(TAG, "Adding dependent process " + app + " not on LRU list: " 2585 + what + " " + obj + " from " + srcApp); 2586 return index; 2587 } 2588 2589 if (lrui >= index) { 2590 // Don't want to cause this to move dependent processes *back* in the 2591 // list as if they were less frequently used. 2592 return index; 2593 } 2594 2595 if (lrui >= mLruProcessActivityStart) { 2596 // Don't want to touch dependent processes that are hosting activities. 2597 return index; 2598 } 2599 2600 mLruProcesses.remove(lrui); 2601 if (index > 0) { 2602 index--; 2603 } 2604 if (DEBUG_LRU) Slog.d(TAG, "Moving dep from " + lrui + " to " + index 2605 + " in LRU list: " + app); 2606 mLruProcesses.add(index, app); 2607 return index; 2608 } 2609 2610 final void removeLruProcessLocked(ProcessRecord app) { 2611 int lrui = mLruProcesses.lastIndexOf(app); 2612 if (lrui >= 0) { 2613 if (lrui <= mLruProcessActivityStart) { 2614 mLruProcessActivityStart--; 2615 } 2616 if (lrui <= mLruProcessServiceStart) { 2617 mLruProcessServiceStart--; 2618 } 2619 mLruProcesses.remove(lrui); 2620 } 2621 } 2622 2623 final void updateLruProcessLocked(ProcessRecord app, boolean activityChange, 2624 ProcessRecord client) { 2625 final boolean hasActivity = app.activities.size() > 0 || app.hasClientActivities 2626 || app.treatLikeActivity; 2627 final boolean hasService = false; // not impl yet. app.services.size() > 0; 2628 if (!activityChange && hasActivity) { 2629 // The process has activities, so we are only allowing activity-based adjustments 2630 // to move it. It should be kept in the front of the list with other 2631 // processes that have activities, and we don't want those to change their 2632 // order except due to activity operations. 2633 return; 2634 } 2635 2636 mLruSeq++; 2637 final long now = SystemClock.uptimeMillis(); 2638 app.lastActivityTime = now; 2639 2640 // First a quick reject: if the app is already at the position we will 2641 // put it, then there is nothing to do. 2642 if (hasActivity) { 2643 final int N = mLruProcesses.size(); 2644 if (N > 0 && mLruProcesses.get(N-1) == app) { 2645 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top activity: " + app); 2646 return; 2647 } 2648 } else { 2649 if (mLruProcessServiceStart > 0 2650 && mLruProcesses.get(mLruProcessServiceStart-1) == app) { 2651 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top other: " + app); 2652 return; 2653 } 2654 } 2655 2656 int lrui = mLruProcesses.lastIndexOf(app); 2657 2658 if (app.persistent && lrui >= 0) { 2659 // We don't care about the position of persistent processes, as long as 2660 // they are in the list. 2661 if (DEBUG_LRU) Slog.d(TAG, "Not moving, persistent: " + app); 2662 return; 2663 } 2664 2665 /* In progress: compute new position first, so we can avoid doing work 2666 if the process is not actually going to move. Not yet working. 2667 int addIndex; 2668 int nextIndex; 2669 boolean inActivity = false, inService = false; 2670 if (hasActivity) { 2671 // Process has activities, put it at the very tipsy-top. 2672 addIndex = mLruProcesses.size(); 2673 nextIndex = mLruProcessServiceStart; 2674 inActivity = true; 2675 } else if (hasService) { 2676 // Process has services, put it at the top of the service list. 2677 addIndex = mLruProcessActivityStart; 2678 nextIndex = mLruProcessServiceStart; 2679 inActivity = true; 2680 inService = true; 2681 } else { 2682 // Process not otherwise of interest, it goes to the top of the non-service area. 2683 addIndex = mLruProcessServiceStart; 2684 if (client != null) { 2685 int clientIndex = mLruProcesses.lastIndexOf(client); 2686 if (clientIndex < 0) Slog.d(TAG, "Unknown client " + client + " when updating " 2687 + app); 2688 if (clientIndex >= 0 && addIndex > clientIndex) { 2689 addIndex = clientIndex; 2690 } 2691 } 2692 nextIndex = addIndex > 0 ? addIndex-1 : addIndex; 2693 } 2694 2695 Slog.d(TAG, "Update LRU at " + lrui + " to " + addIndex + " (act=" 2696 + mLruProcessActivityStart + "): " + app); 2697 */ 2698 2699 if (lrui >= 0) { 2700 if (lrui < mLruProcessActivityStart) { 2701 mLruProcessActivityStart--; 2702 } 2703 if (lrui < mLruProcessServiceStart) { 2704 mLruProcessServiceStart--; 2705 } 2706 /* 2707 if (addIndex > lrui) { 2708 addIndex--; 2709 } 2710 if (nextIndex > lrui) { 2711 nextIndex--; 2712 } 2713 */ 2714 mLruProcesses.remove(lrui); 2715 } 2716 2717 /* 2718 mLruProcesses.add(addIndex, app); 2719 if (inActivity) { 2720 mLruProcessActivityStart++; 2721 } 2722 if (inService) { 2723 mLruProcessActivityStart++; 2724 } 2725 */ 2726 2727 int nextIndex; 2728 if (hasActivity) { 2729 final int N = mLruProcesses.size(); 2730 if (app.activities.size() == 0 && mLruProcessActivityStart < (N-1)) { 2731 // Process doesn't have activities, but has clients with 2732 // activities... move it up, but one below the top (the top 2733 // should always have a real activity). 2734 if (DEBUG_LRU) Slog.d(TAG, "Adding to second-top of LRU activity list: " + app); 2735 mLruProcesses.add(N-1, app); 2736 // To keep it from spamming the LRU list (by making a bunch of clients), 2737 // we will push down any other entries owned by the app. 2738 final int uid = app.info.uid; 2739 for (int i=N-2; i>mLruProcessActivityStart; i--) { 2740 ProcessRecord subProc = mLruProcesses.get(i); 2741 if (subProc.info.uid == uid) { 2742 // We want to push this one down the list. If the process after 2743 // it is for the same uid, however, don't do so, because we don't 2744 // want them internally to be re-ordered. 2745 if (mLruProcesses.get(i-1).info.uid != uid) { 2746 if (DEBUG_LRU) Slog.d(TAG, "Pushing uid " + uid + " swapping at " + i 2747 + ": " + mLruProcesses.get(i) + " : " + mLruProcesses.get(i-1)); 2748 ProcessRecord tmp = mLruProcesses.get(i); 2749 mLruProcesses.set(i, mLruProcesses.get(i-1)); 2750 mLruProcesses.set(i-1, tmp); 2751 i--; 2752 } 2753 } else { 2754 // A gap, we can stop here. 2755 break; 2756 } 2757 } 2758 } else { 2759 // Process has activities, put it at the very tipsy-top. 2760 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU activity list: " + app); 2761 mLruProcesses.add(app); 2762 } 2763 nextIndex = mLruProcessServiceStart; 2764 } else if (hasService) { 2765 // Process has services, put it at the top of the service list. 2766 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU service list: " + app); 2767 mLruProcesses.add(mLruProcessActivityStart, app); 2768 nextIndex = mLruProcessServiceStart; 2769 mLruProcessActivityStart++; 2770 } else { 2771 // Process not otherwise of interest, it goes to the top of the non-service area. 2772 int index = mLruProcessServiceStart; 2773 if (client != null) { 2774 // If there is a client, don't allow the process to be moved up higher 2775 // in the list than that client. 2776 int clientIndex = mLruProcesses.lastIndexOf(client); 2777 if (DEBUG_LRU && clientIndex < 0) Slog.d(TAG, "Unknown client " + client 2778 + " when updating " + app); 2779 if (clientIndex <= lrui) { 2780 // Don't allow the client index restriction to push it down farther in the 2781 // list than it already is. 2782 clientIndex = lrui; 2783 } 2784 if (clientIndex >= 0 && index > clientIndex) { 2785 index = clientIndex; 2786 } 2787 } 2788 if (DEBUG_LRU) Slog.d(TAG, "Adding at " + index + " of LRU list: " + app); 2789 mLruProcesses.add(index, app); 2790 nextIndex = index-1; 2791 mLruProcessActivityStart++; 2792 mLruProcessServiceStart++; 2793 } 2794 2795 // If the app is currently using a content provider or service, 2796 // bump those processes as well. 2797 for (int j=app.connections.size()-1; j>=0; j--) { 2798 ConnectionRecord cr = app.connections.valueAt(j); 2799 if (cr.binding != null && !cr.serviceDead && cr.binding.service != null 2800 && cr.binding.service.app != null 2801 && cr.binding.service.app.lruSeq != mLruSeq 2802 && !cr.binding.service.app.persistent) { 2803 nextIndex = updateLruProcessInternalLocked(cr.binding.service.app, now, nextIndex, 2804 "service connection", cr, app); 2805 } 2806 } 2807 for (int j=app.conProviders.size()-1; j>=0; j--) { 2808 ContentProviderRecord cpr = app.conProviders.get(j).provider; 2809 if (cpr.proc != null && cpr.proc.lruSeq != mLruSeq && !cpr.proc.persistent) { 2810 nextIndex = updateLruProcessInternalLocked(cpr.proc, now, nextIndex, 2811 "provider reference", cpr, app); 2812 } 2813 } 2814 } 2815 2816 final ProcessRecord getProcessRecordLocked(String processName, int uid, boolean keepIfLarge) { 2817 if (uid == Process.SYSTEM_UID) { 2818 // The system gets to run in any process. If there are multiple 2819 // processes with the same uid, just pick the first (this 2820 // should never happen). 2821 SparseArray<ProcessRecord> procs = mProcessNames.getMap().get(processName); 2822 if (procs == null) return null; 2823 final int N = procs.size(); 2824 for (int i = 0; i < N; i++) { 2825 if (UserHandle.isSameUser(procs.keyAt(i), uid)) return procs.valueAt(i); 2826 } 2827 } 2828 ProcessRecord proc = mProcessNames.get(processName, uid); 2829 if (false && proc != null && !keepIfLarge 2830 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY 2831 && proc.lastCachedPss >= 4000) { 2832 // Turn this condition on to cause killing to happen regularly, for testing. 2833 if (proc.baseProcessTracker != null) { 2834 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2835 } 2836 proc.kill(Long.toString(proc.lastCachedPss) + "k from cached", true); 2837 } else if (proc != null && !keepIfLarge 2838 && mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 2839 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 2840 if (DEBUG_PSS) Slog.d(TAG, "May not keep " + proc + ": pss=" + proc.lastCachedPss); 2841 if (proc.lastCachedPss >= mProcessList.getCachedRestoreThresholdKb()) { 2842 if (proc.baseProcessTracker != null) { 2843 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2844 } 2845 proc.kill(Long.toString(proc.lastCachedPss) + "k from cached", true); 2846 } 2847 } 2848 return proc; 2849 } 2850 2851 void ensurePackageDexOpt(String packageName) { 2852 IPackageManager pm = AppGlobals.getPackageManager(); 2853 try { 2854 if (pm.performDexOptIfNeeded(packageName, null /* instruction set */)) { 2855 mDidDexOpt = true; 2856 } 2857 } catch (RemoteException e) { 2858 } 2859 } 2860 2861 boolean isNextTransitionForward() { 2862 int transit = mWindowManager.getPendingAppTransition(); 2863 return transit == AppTransition.TRANSIT_ACTIVITY_OPEN 2864 || transit == AppTransition.TRANSIT_TASK_OPEN 2865 || transit == AppTransition.TRANSIT_TASK_TO_FRONT; 2866 } 2867 2868 int startIsolatedProcess(String entryPoint, String[] entryPointArgs, 2869 String processName, String abiOverride, int uid, Runnable crashHandler) { 2870 synchronized(this) { 2871 ApplicationInfo info = new ApplicationInfo(); 2872 // In general the ApplicationInfo.uid isn't neccesarily equal to ProcessRecord.uid. 2873 // For isolated processes, the former contains the parent's uid and the latter the 2874 // actual uid of the isolated process. 2875 // In the special case introduced by this method (which is, starting an isolated 2876 // process directly from the SystemServer without an actual parent app process) the 2877 // closest thing to a parent's uid is SYSTEM_UID. 2878 // The only important thing here is to keep AI.uid != PR.uid, in order to trigger 2879 // the |isolated| logic in the ProcessRecord constructor. 2880 info.uid = Process.SYSTEM_UID; 2881 info.processName = processName; 2882 info.className = entryPoint; 2883 info.packageName = "android"; 2884 ProcessRecord proc = startProcessLocked(processName, info /* info */, 2885 false /* knownToBeDead */, 0 /* intentFlags */, "" /* hostingType */, 2886 null /* hostingName */, true /* allowWhileBooting */, true /* isolated */, 2887 uid, true /* keepIfLarge */, abiOverride, entryPoint, entryPointArgs, 2888 crashHandler); 2889 return proc != null ? proc.pid : 0; 2890 } 2891 } 2892 2893 final ProcessRecord startProcessLocked(String processName, 2894 ApplicationInfo info, boolean knownToBeDead, int intentFlags, 2895 String hostingType, ComponentName hostingName, boolean allowWhileBooting, 2896 boolean isolated, boolean keepIfLarge) { 2897 return startProcessLocked(processName, info, knownToBeDead, intentFlags, hostingType, 2898 hostingName, allowWhileBooting, isolated, 0 /* isolatedUid */, keepIfLarge, 2899 null /* ABI override */, null /* entryPoint */, null /* entryPointArgs */, 2900 null /* crashHandler */); 2901 } 2902 2903 final ProcessRecord startProcessLocked(String processName, ApplicationInfo info, 2904 boolean knownToBeDead, int intentFlags, String hostingType, ComponentName hostingName, 2905 boolean allowWhileBooting, boolean isolated, int isolatedUid, boolean keepIfLarge, 2906 String abiOverride, String entryPoint, String[] entryPointArgs, Runnable crashHandler) { 2907 long startTime = SystemClock.elapsedRealtime(); 2908 ProcessRecord app; 2909 if (!isolated) { 2910 app = getProcessRecordLocked(processName, info.uid, keepIfLarge); 2911 checkTime(startTime, "startProcess: after getProcessRecord"); 2912 } else { 2913 // If this is an isolated process, it can't re-use an existing process. 2914 app = null; 2915 } 2916 // We don't have to do anything more if: 2917 // (1) There is an existing application record; and 2918 // (2) The caller doesn't think it is dead, OR there is no thread 2919 // object attached to it so we know it couldn't have crashed; and 2920 // (3) There is a pid assigned to it, so it is either starting or 2921 // already running. 2922 if (DEBUG_PROCESSES) Slog.v(TAG, "startProcess: name=" + processName 2923 + " app=" + app + " knownToBeDead=" + knownToBeDead 2924 + " thread=" + (app != null ? app.thread : null) 2925 + " pid=" + (app != null ? app.pid : -1)); 2926 if (app != null && app.pid > 0) { 2927 if (!knownToBeDead || app.thread == null) { 2928 // We already have the app running, or are waiting for it to 2929 // come up (we have a pid but not yet its thread), so keep it. 2930 if (DEBUG_PROCESSES) Slog.v(TAG, "App already running: " + app); 2931 // If this is a new package in the process, add the package to the list 2932 app.addPackage(info.packageName, info.versionCode, mProcessStats); 2933 checkTime(startTime, "startProcess: done, added package to proc"); 2934 return app; 2935 } 2936 2937 // An application record is attached to a previous process, 2938 // clean it up now. 2939 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, "App died: " + app); 2940 checkTime(startTime, "startProcess: bad proc running, killing"); 2941 Process.killProcessGroup(app.info.uid, app.pid); 2942 handleAppDiedLocked(app, true, true); 2943 checkTime(startTime, "startProcess: done killing old proc"); 2944 } 2945 2946 String hostingNameStr = hostingName != null 2947 ? hostingName.flattenToShortString() : null; 2948 2949 if (!isolated) { 2950 if ((intentFlags&Intent.FLAG_FROM_BACKGROUND) != 0) { 2951 // If we are in the background, then check to see if this process 2952 // is bad. If so, we will just silently fail. 2953 if (mBadProcesses.get(info.processName, info.uid) != null) { 2954 if (DEBUG_PROCESSES) Slog.v(TAG, "Bad process: " + info.uid 2955 + "/" + info.processName); 2956 return null; 2957 } 2958 } else { 2959 // When the user is explicitly starting a process, then clear its 2960 // crash count so that we won't make it bad until they see at 2961 // least one crash dialog again, and make the process good again 2962 // if it had been bad. 2963 if (DEBUG_PROCESSES) Slog.v(TAG, "Clearing bad process: " + info.uid 2964 + "/" + info.processName); 2965 mProcessCrashTimes.remove(info.processName, info.uid); 2966 if (mBadProcesses.get(info.processName, info.uid) != null) { 2967 EventLog.writeEvent(EventLogTags.AM_PROC_GOOD, 2968 UserHandle.getUserId(info.uid), info.uid, 2969 info.processName); 2970 mBadProcesses.remove(info.processName, info.uid); 2971 if (app != null) { 2972 app.bad = false; 2973 } 2974 } 2975 } 2976 } 2977 2978 if (app == null) { 2979 checkTime(startTime, "startProcess: creating new process record"); 2980 app = newProcessRecordLocked(info, processName, isolated, isolatedUid); 2981 app.crashHandler = crashHandler; 2982 if (app == null) { 2983 Slog.w(TAG, "Failed making new process record for " 2984 + processName + "/" + info.uid + " isolated=" + isolated); 2985 return null; 2986 } 2987 mProcessNames.put(processName, app.uid, app); 2988 if (isolated) { 2989 mIsolatedProcesses.put(app.uid, app); 2990 } 2991 checkTime(startTime, "startProcess: done creating new process record"); 2992 } else { 2993 // If this is a new package in the process, add the package to the list 2994 app.addPackage(info.packageName, info.versionCode, mProcessStats); 2995 checkTime(startTime, "startProcess: added package to existing proc"); 2996 } 2997 2998 // If the system is not ready yet, then hold off on starting this 2999 // process until it is. 3000 if (!mProcessesReady 3001 && !isAllowedWhileBooting(info) 3002 && !allowWhileBooting) { 3003 if (!mProcessesOnHold.contains(app)) { 3004 mProcessesOnHold.add(app); 3005 } 3006 if (DEBUG_PROCESSES) Slog.v(TAG, "System not ready, putting on hold: " + app); 3007 checkTime(startTime, "startProcess: returning with proc on hold"); 3008 return app; 3009 } 3010 3011 checkTime(startTime, "startProcess: stepping in to startProcess"); 3012 startProcessLocked( 3013 app, hostingType, hostingNameStr, abiOverride, entryPoint, entryPointArgs); 3014 checkTime(startTime, "startProcess: done starting proc!"); 3015 return (app.pid != 0) ? app : null; 3016 } 3017 3018 boolean isAllowedWhileBooting(ApplicationInfo ai) { 3019 return (ai.flags&ApplicationInfo.FLAG_PERSISTENT) != 0; 3020 } 3021 3022 private final void startProcessLocked(ProcessRecord app, 3023 String hostingType, String hostingNameStr) { 3024 startProcessLocked(app, hostingType, hostingNameStr, null /* abiOverride */, 3025 null /* entryPoint */, null /* entryPointArgs */); 3026 } 3027 3028 private final void startProcessLocked(ProcessRecord app, String hostingType, 3029 String hostingNameStr, String abiOverride, String entryPoint, String[] entryPointArgs) { 3030 long startTime = SystemClock.elapsedRealtime(); 3031 if (app.pid > 0 && app.pid != MY_PID) { 3032 checkTime(startTime, "startProcess: removing from pids map"); 3033 synchronized (mPidsSelfLocked) { 3034 mPidsSelfLocked.remove(app.pid); 3035 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 3036 } 3037 checkTime(startTime, "startProcess: done removing from pids map"); 3038 app.setPid(0); 3039 } 3040 3041 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 3042 "startProcessLocked removing on hold: " + app); 3043 mProcessesOnHold.remove(app); 3044 3045 checkTime(startTime, "startProcess: starting to update cpu stats"); 3046 updateCpuStats(); 3047 checkTime(startTime, "startProcess: done updating cpu stats"); 3048 3049 try { 3050 int uid = app.uid; 3051 3052 int[] gids = null; 3053 int mountExternal = Zygote.MOUNT_EXTERNAL_NONE; 3054 if (!app.isolated) { 3055 int[] permGids = null; 3056 try { 3057 checkTime(startTime, "startProcess: getting gids from package manager"); 3058 final PackageManager pm = mContext.getPackageManager(); 3059 permGids = pm.getPackageGids(app.info.packageName); 3060 3061 if (Environment.isExternalStorageEmulated()) { 3062 checkTime(startTime, "startProcess: checking external storage perm"); 3063 if (pm.checkPermission( 3064 android.Manifest.permission.ACCESS_ALL_EXTERNAL_STORAGE, 3065 app.info.packageName) == PERMISSION_GRANTED) { 3066 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER_ALL; 3067 } else { 3068 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER; 3069 } 3070 } 3071 } catch (PackageManager.NameNotFoundException e) { 3072 Slog.w(TAG, "Unable to retrieve gids", e); 3073 } 3074 3075 /* 3076 * Add shared application and profile GIDs so applications can share some 3077 * resources like shared libraries and access user-wide resources 3078 */ 3079 if (permGids == null) { 3080 gids = new int[2]; 3081 } else { 3082 gids = new int[permGids.length + 2]; 3083 System.arraycopy(permGids, 0, gids, 2, permGids.length); 3084 } 3085 gids[0] = UserHandle.getSharedAppGid(UserHandle.getAppId(uid)); 3086 gids[1] = UserHandle.getUserGid(UserHandle.getUserId(uid)); 3087 } 3088 checkTime(startTime, "startProcess: building args"); 3089 if (mFactoryTest != FactoryTest.FACTORY_TEST_OFF) { 3090 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3091 && mTopComponent != null 3092 && app.processName.equals(mTopComponent.getPackageName())) { 3093 uid = 0; 3094 } 3095 if (mFactoryTest == FactoryTest.FACTORY_TEST_HIGH_LEVEL 3096 && (app.info.flags&ApplicationInfo.FLAG_FACTORY_TEST) != 0) { 3097 uid = 0; 3098 } 3099 } 3100 int debugFlags = 0; 3101 if ((app.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 3102 debugFlags |= Zygote.DEBUG_ENABLE_DEBUGGER; 3103 // Also turn on CheckJNI for debuggable apps. It's quite 3104 // awkward to turn on otherwise. 3105 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 3106 } 3107 // Run the app in safe mode if its manifest requests so or the 3108 // system is booted in safe mode. 3109 if ((app.info.flags & ApplicationInfo.FLAG_VM_SAFE_MODE) != 0 || 3110 mSafeMode == true) { 3111 debugFlags |= Zygote.DEBUG_ENABLE_SAFEMODE; 3112 } 3113 if ("1".equals(SystemProperties.get("debug.checkjni"))) { 3114 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 3115 } 3116 if ("1".equals(SystemProperties.get("debug.jni.logging"))) { 3117 debugFlags |= Zygote.DEBUG_ENABLE_JNI_LOGGING; 3118 } 3119 if ("1".equals(SystemProperties.get("debug.assert"))) { 3120 debugFlags |= Zygote.DEBUG_ENABLE_ASSERT; 3121 } 3122 3123 String requiredAbi = (abiOverride != null) ? abiOverride : app.info.primaryCpuAbi; 3124 if (requiredAbi == null) { 3125 requiredAbi = Build.SUPPORTED_ABIS[0]; 3126 } 3127 3128 String instructionSet = null; 3129 if (app.info.primaryCpuAbi != null) { 3130 instructionSet = VMRuntime.getInstructionSet(app.info.primaryCpuAbi); 3131 } 3132 3133 // Start the process. It will either succeed and return a result containing 3134 // the PID of the new process, or else throw a RuntimeException. 3135 boolean isActivityProcess = (entryPoint == null); 3136 if (entryPoint == null) entryPoint = "android.app.ActivityThread"; 3137 checkTime(startTime, "startProcess: asking zygote to start proc"); 3138 Process.ProcessStartResult startResult = Process.start(entryPoint, 3139 app.processName, uid, uid, gids, debugFlags, mountExternal, 3140 app.info.targetSdkVersion, app.info.seinfo, requiredAbi, instructionSet, 3141 entryPointArgs); 3142 checkTime(startTime, "startProcess: returned from zygote!"); 3143 3144 if (app.isolated) { 3145 mBatteryStatsService.addIsolatedUid(app.uid, app.info.uid); 3146 } 3147 mBatteryStatsService.noteProcessStart(app.processName, app.info.uid); 3148 checkTime(startTime, "startProcess: done updating battery stats"); 3149 3150 EventLog.writeEvent(EventLogTags.AM_PROC_START, 3151 UserHandle.getUserId(uid), startResult.pid, uid, 3152 app.processName, hostingType, 3153 hostingNameStr != null ? hostingNameStr : ""); 3154 3155 if (app.persistent) { 3156 Watchdog.getInstance().processStarted(app.processName, startResult.pid); 3157 } 3158 3159 checkTime(startTime, "startProcess: building log message"); 3160 StringBuilder buf = mStringBuilder; 3161 buf.setLength(0); 3162 buf.append("Start proc "); 3163 buf.append(app.processName); 3164 if (!isActivityProcess) { 3165 buf.append(" ["); 3166 buf.append(entryPoint); 3167 buf.append("]"); 3168 } 3169 buf.append(" for "); 3170 buf.append(hostingType); 3171 if (hostingNameStr != null) { 3172 buf.append(" "); 3173 buf.append(hostingNameStr); 3174 } 3175 buf.append(": pid="); 3176 buf.append(startResult.pid); 3177 buf.append(" uid="); 3178 buf.append(uid); 3179 buf.append(" gids={"); 3180 if (gids != null) { 3181 for (int gi=0; gi<gids.length; gi++) { 3182 if (gi != 0) buf.append(", "); 3183 buf.append(gids[gi]); 3184 3185 } 3186 } 3187 buf.append("}"); 3188 if (requiredAbi != null) { 3189 buf.append(" abi="); 3190 buf.append(requiredAbi); 3191 } 3192 Slog.i(TAG, buf.toString()); 3193 app.setPid(startResult.pid); 3194 app.usingWrapper = startResult.usingWrapper; 3195 app.removed = false; 3196 app.killedByAm = false; 3197 checkTime(startTime, "startProcess: starting to update pids map"); 3198 synchronized (mPidsSelfLocked) { 3199 this.mPidsSelfLocked.put(startResult.pid, app); 3200 if (isActivityProcess) { 3201 Message msg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 3202 msg.obj = app; 3203 mHandler.sendMessageDelayed(msg, startResult.usingWrapper 3204 ? PROC_START_TIMEOUT_WITH_WRAPPER : PROC_START_TIMEOUT); 3205 } 3206 } 3207 checkTime(startTime, "startProcess: done updating pids map"); 3208 } catch (RuntimeException e) { 3209 // XXX do better error recovery. 3210 app.setPid(0); 3211 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 3212 if (app.isolated) { 3213 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 3214 } 3215 Slog.e(TAG, "Failure starting process " + app.processName, e); 3216 } 3217 } 3218 3219 void updateUsageStats(ActivityRecord component, boolean resumed) { 3220 if (DEBUG_SWITCH) Slog.d(TAG, "updateUsageStats: comp=" + component + "res=" + resumed); 3221 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 3222 if (resumed) { 3223 if (mUsageStatsService != null) { 3224 mUsageStatsService.reportEvent(component.realActivity, component.userId, 3225 UsageEvents.Event.MOVE_TO_FOREGROUND); 3226 } 3227 synchronized (stats) { 3228 stats.noteActivityResumedLocked(component.app.uid); 3229 } 3230 } else { 3231 if (mUsageStatsService != null) { 3232 mUsageStatsService.reportEvent(component.realActivity, component.userId, 3233 UsageEvents.Event.MOVE_TO_BACKGROUND); 3234 } 3235 synchronized (stats) { 3236 stats.noteActivityPausedLocked(component.app.uid); 3237 } 3238 } 3239 } 3240 3241 Intent getHomeIntent() { 3242 Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null); 3243 intent.setComponent(mTopComponent); 3244 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 3245 intent.addCategory(Intent.CATEGORY_HOME); 3246 } 3247 return intent; 3248 } 3249 3250 boolean startHomeActivityLocked(int userId) { 3251 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3252 && mTopAction == null) { 3253 // We are running in factory test mode, but unable to find 3254 // the factory test app, so just sit around displaying the 3255 // error message and don't try to start anything. 3256 return false; 3257 } 3258 Intent intent = getHomeIntent(); 3259 ActivityInfo aInfo = 3260 resolveActivityInfo(intent, STOCK_PM_FLAGS, userId); 3261 if (aInfo != null) { 3262 intent.setComponent(new ComponentName( 3263 aInfo.applicationInfo.packageName, aInfo.name)); 3264 // Don't do this if the home app is currently being 3265 // instrumented. 3266 aInfo = new ActivityInfo(aInfo); 3267 aInfo.applicationInfo = getAppInfoForUser(aInfo.applicationInfo, userId); 3268 ProcessRecord app = getProcessRecordLocked(aInfo.processName, 3269 aInfo.applicationInfo.uid, true); 3270 if (app == null || app.instrumentationClass == null) { 3271 intent.setFlags(intent.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK); 3272 mStackSupervisor.startHomeActivity(intent, aInfo); 3273 } 3274 } 3275 3276 return true; 3277 } 3278 3279 private ActivityInfo resolveActivityInfo(Intent intent, int flags, int userId) { 3280 ActivityInfo ai = null; 3281 ComponentName comp = intent.getComponent(); 3282 try { 3283 if (comp != null) { 3284 ai = AppGlobals.getPackageManager().getActivityInfo(comp, flags, userId); 3285 } else { 3286 ResolveInfo info = AppGlobals.getPackageManager().resolveIntent( 3287 intent, 3288 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 3289 flags, userId); 3290 3291 if (info != null) { 3292 ai = info.activityInfo; 3293 } 3294 } 3295 } catch (RemoteException e) { 3296 // ignore 3297 } 3298 3299 return ai; 3300 } 3301 3302 /** 3303 * Starts the "new version setup screen" if appropriate. 3304 */ 3305 void startSetupActivityLocked() { 3306 // Only do this once per boot. 3307 if (mCheckedForSetup) { 3308 return; 3309 } 3310 3311 // We will show this screen if the current one is a different 3312 // version than the last one shown, and we are not running in 3313 // low-level factory test mode. 3314 final ContentResolver resolver = mContext.getContentResolver(); 3315 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL && 3316 Settings.Global.getInt(resolver, 3317 Settings.Global.DEVICE_PROVISIONED, 0) != 0) { 3318 mCheckedForSetup = true; 3319 3320 // See if we should be showing the platform update setup UI. 3321 Intent intent = new Intent(Intent.ACTION_UPGRADE_SETUP); 3322 List<ResolveInfo> ris = mContext.getPackageManager() 3323 .queryIntentActivities(intent, PackageManager.GET_META_DATA); 3324 3325 // We don't allow third party apps to replace this. 3326 ResolveInfo ri = null; 3327 for (int i=0; ris != null && i<ris.size(); i++) { 3328 if ((ris.get(i).activityInfo.applicationInfo.flags 3329 & ApplicationInfo.FLAG_SYSTEM) != 0) { 3330 ri = ris.get(i); 3331 break; 3332 } 3333 } 3334 3335 if (ri != null) { 3336 String vers = ri.activityInfo.metaData != null 3337 ? ri.activityInfo.metaData.getString(Intent.METADATA_SETUP_VERSION) 3338 : null; 3339 if (vers == null && ri.activityInfo.applicationInfo.metaData != null) { 3340 vers = ri.activityInfo.applicationInfo.metaData.getString( 3341 Intent.METADATA_SETUP_VERSION); 3342 } 3343 String lastVers = Settings.Secure.getString( 3344 resolver, Settings.Secure.LAST_SETUP_SHOWN); 3345 if (vers != null && !vers.equals(lastVers)) { 3346 intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 3347 intent.setComponent(new ComponentName( 3348 ri.activityInfo.packageName, ri.activityInfo.name)); 3349 mStackSupervisor.startActivityLocked(null, intent, null, ri.activityInfo, 3350 null, null, null, null, 0, 0, 0, null, 0, null, false, null, null, 3351 null); 3352 } 3353 } 3354 } 3355 } 3356 3357 CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) { 3358 return mCompatModePackages.compatibilityInfoForPackageLocked(ai); 3359 } 3360 3361 void enforceNotIsolatedCaller(String caller) { 3362 if (UserHandle.isIsolated(Binder.getCallingUid())) { 3363 throw new SecurityException("Isolated process not allowed to call " + caller); 3364 } 3365 } 3366 3367 @Override 3368 public int getFrontActivityScreenCompatMode() { 3369 enforceNotIsolatedCaller("getFrontActivityScreenCompatMode"); 3370 synchronized (this) { 3371 return mCompatModePackages.getFrontActivityScreenCompatModeLocked(); 3372 } 3373 } 3374 3375 @Override 3376 public void setFrontActivityScreenCompatMode(int mode) { 3377 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3378 "setFrontActivityScreenCompatMode"); 3379 synchronized (this) { 3380 mCompatModePackages.setFrontActivityScreenCompatModeLocked(mode); 3381 } 3382 } 3383 3384 @Override 3385 public int getPackageScreenCompatMode(String packageName) { 3386 enforceNotIsolatedCaller("getPackageScreenCompatMode"); 3387 synchronized (this) { 3388 return mCompatModePackages.getPackageScreenCompatModeLocked(packageName); 3389 } 3390 } 3391 3392 @Override 3393 public void setPackageScreenCompatMode(String packageName, int mode) { 3394 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3395 "setPackageScreenCompatMode"); 3396 synchronized (this) { 3397 mCompatModePackages.setPackageScreenCompatModeLocked(packageName, mode); 3398 } 3399 } 3400 3401 @Override 3402 public boolean getPackageAskScreenCompat(String packageName) { 3403 enforceNotIsolatedCaller("getPackageAskScreenCompat"); 3404 synchronized (this) { 3405 return mCompatModePackages.getPackageAskCompatModeLocked(packageName); 3406 } 3407 } 3408 3409 @Override 3410 public void setPackageAskScreenCompat(String packageName, boolean ask) { 3411 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3412 "setPackageAskScreenCompat"); 3413 synchronized (this) { 3414 mCompatModePackages.setPackageAskCompatModeLocked(packageName, ask); 3415 } 3416 } 3417 3418 private void dispatchProcessesChanged() { 3419 int N; 3420 synchronized (this) { 3421 N = mPendingProcessChanges.size(); 3422 if (mActiveProcessChanges.length < N) { 3423 mActiveProcessChanges = new ProcessChangeItem[N]; 3424 } 3425 mPendingProcessChanges.toArray(mActiveProcessChanges); 3426 mAvailProcessChanges.addAll(mPendingProcessChanges); 3427 mPendingProcessChanges.clear(); 3428 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "*** Delivering " + N + " process changes"); 3429 } 3430 3431 int i = mProcessObservers.beginBroadcast(); 3432 while (i > 0) { 3433 i--; 3434 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3435 if (observer != null) { 3436 try { 3437 for (int j=0; j<N; j++) { 3438 ProcessChangeItem item = mActiveProcessChanges[j]; 3439 if ((item.changes&ProcessChangeItem.CHANGE_ACTIVITIES) != 0) { 3440 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "ACTIVITIES CHANGED pid=" 3441 + item.pid + " uid=" + item.uid + ": " 3442 + item.foregroundActivities); 3443 observer.onForegroundActivitiesChanged(item.pid, item.uid, 3444 item.foregroundActivities); 3445 } 3446 if ((item.changes&ProcessChangeItem.CHANGE_PROCESS_STATE) != 0) { 3447 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "PROCSTATE CHANGED pid=" 3448 + item.pid + " uid=" + item.uid + ": " + item.processState); 3449 observer.onProcessStateChanged(item.pid, item.uid, item.processState); 3450 } 3451 } 3452 } catch (RemoteException e) { 3453 } 3454 } 3455 } 3456 mProcessObservers.finishBroadcast(); 3457 } 3458 3459 private void dispatchProcessDied(int pid, int uid) { 3460 int i = mProcessObservers.beginBroadcast(); 3461 while (i > 0) { 3462 i--; 3463 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3464 if (observer != null) { 3465 try { 3466 observer.onProcessDied(pid, uid); 3467 } catch (RemoteException e) { 3468 } 3469 } 3470 } 3471 mProcessObservers.finishBroadcast(); 3472 } 3473 3474 @Override 3475 public final int startActivity(IApplicationThread caller, String callingPackage, 3476 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3477 int startFlags, ProfilerInfo profilerInfo, Bundle options) { 3478 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo, 3479 resultWho, requestCode, startFlags, profilerInfo, options, 3480 UserHandle.getCallingUserId()); 3481 } 3482 3483 @Override 3484 public final int startActivityAsUser(IApplicationThread caller, String callingPackage, 3485 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3486 int startFlags, ProfilerInfo profilerInfo, Bundle options, int userId) { 3487 enforceNotIsolatedCaller("startActivity"); 3488 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3489 false, ALLOW_FULL_ONLY, "startActivity", null); 3490 // TODO: Switch to user app stacks here. 3491 return mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, 3492 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3493 profilerInfo, null, null, options, userId, null, null); 3494 } 3495 3496 @Override 3497 public final int startActivityAsCaller(IApplicationThread caller, String callingPackage, 3498 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3499 int startFlags, ProfilerInfo profilerInfo, Bundle options) { 3500 3501 // This is very dangerous -- it allows you to perform a start activity (including 3502 // permission grants) as any app that may launch one of your own activities. So 3503 // we will only allow this to be done from activities that are part of the core framework, 3504 // and then only when they are running as the system. 3505 final ActivityRecord sourceRecord; 3506 final int targetUid; 3507 final String targetPackage; 3508 synchronized (this) { 3509 if (resultTo == null) { 3510 throw new SecurityException("Must be called from an activity"); 3511 } 3512 sourceRecord = mStackSupervisor.isInAnyStackLocked(resultTo); 3513 if (sourceRecord == null) { 3514 throw new SecurityException("Called with bad activity token: " + resultTo); 3515 } 3516 if (!sourceRecord.info.packageName.equals("android")) { 3517 throw new SecurityException( 3518 "Must be called from an activity that is declared in the android package"); 3519 } 3520 if (sourceRecord.app == null) { 3521 throw new SecurityException("Called without a process attached to activity"); 3522 } 3523 if (UserHandle.getAppId(sourceRecord.app.uid) != Process.SYSTEM_UID) { 3524 // This is still okay, as long as this activity is running under the 3525 // uid of the original calling activity. 3526 if (sourceRecord.app.uid != sourceRecord.launchedFromUid) { 3527 throw new SecurityException( 3528 "Calling activity in uid " + sourceRecord.app.uid 3529 + " must be system uid or original calling uid " 3530 + sourceRecord.launchedFromUid); 3531 } 3532 } 3533 targetUid = sourceRecord.launchedFromUid; 3534 targetPackage = sourceRecord.launchedFromPackage; 3535 } 3536 3537 // TODO: Switch to user app stacks here. 3538 try { 3539 int ret = mStackSupervisor.startActivityMayWait(null, targetUid, targetPackage, intent, 3540 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, null, 3541 null, null, options, UserHandle.getUserId(sourceRecord.app.uid), null, null); 3542 return ret; 3543 } catch (SecurityException e) { 3544 // XXX need to figure out how to propagate to original app. 3545 // A SecurityException here is generally actually a fault of the original 3546 // calling activity (such as a fairly granting permissions), so propagate it 3547 // back to them. 3548 /* 3549 StringBuilder msg = new StringBuilder(); 3550 msg.append("While launching"); 3551 msg.append(intent.toString()); 3552 msg.append(": "); 3553 msg.append(e.getMessage()); 3554 */ 3555 throw e; 3556 } 3557 } 3558 3559 @Override 3560 public final WaitResult startActivityAndWait(IApplicationThread caller, String callingPackage, 3561 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3562 int startFlags, ProfilerInfo profilerInfo, Bundle options, int userId) { 3563 enforceNotIsolatedCaller("startActivityAndWait"); 3564 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3565 false, ALLOW_FULL_ONLY, "startActivityAndWait", null); 3566 WaitResult res = new WaitResult(); 3567 // TODO: Switch to user app stacks here. 3568 mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 3569 null, null, resultTo, resultWho, requestCode, startFlags, profilerInfo, res, null, 3570 options, userId, null, null); 3571 return res; 3572 } 3573 3574 @Override 3575 public final int startActivityWithConfig(IApplicationThread caller, String callingPackage, 3576 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3577 int startFlags, Configuration config, Bundle options, int userId) { 3578 enforceNotIsolatedCaller("startActivityWithConfig"); 3579 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3580 false, ALLOW_FULL_ONLY, "startActivityWithConfig", null); 3581 // TODO: Switch to user app stacks here. 3582 int ret = mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, 3583 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3584 null, null, config, options, userId, null, null); 3585 return ret; 3586 } 3587 3588 @Override 3589 public int startActivityIntentSender(IApplicationThread caller, 3590 IntentSender intent, Intent fillInIntent, String resolvedType, 3591 IBinder resultTo, String resultWho, int requestCode, 3592 int flagsMask, int flagsValues, Bundle options) { 3593 enforceNotIsolatedCaller("startActivityIntentSender"); 3594 // Refuse possible leaked file descriptors 3595 if (fillInIntent != null && fillInIntent.hasFileDescriptors()) { 3596 throw new IllegalArgumentException("File descriptors passed in Intent"); 3597 } 3598 3599 IIntentSender sender = intent.getTarget(); 3600 if (!(sender instanceof PendingIntentRecord)) { 3601 throw new IllegalArgumentException("Bad PendingIntent object"); 3602 } 3603 3604 PendingIntentRecord pir = (PendingIntentRecord)sender; 3605 3606 synchronized (this) { 3607 // If this is coming from the currently resumed activity, it is 3608 // effectively saying that app switches are allowed at this point. 3609 final ActivityStack stack = getFocusedStack(); 3610 if (stack.mResumedActivity != null && 3611 stack.mResumedActivity.info.applicationInfo.uid == Binder.getCallingUid()) { 3612 mAppSwitchesAllowedTime = 0; 3613 } 3614 } 3615 int ret = pir.sendInner(0, fillInIntent, resolvedType, null, null, 3616 resultTo, resultWho, requestCode, flagsMask, flagsValues, options, null); 3617 return ret; 3618 } 3619 3620 @Override 3621 public int startVoiceActivity(String callingPackage, int callingPid, int callingUid, 3622 Intent intent, String resolvedType, IVoiceInteractionSession session, 3623 IVoiceInteractor interactor, int startFlags, ProfilerInfo profilerInfo, 3624 Bundle options, int userId) { 3625 if (checkCallingPermission(Manifest.permission.BIND_VOICE_INTERACTION) 3626 != PackageManager.PERMISSION_GRANTED) { 3627 String msg = "Permission Denial: startVoiceActivity() from pid=" 3628 + Binder.getCallingPid() 3629 + ", uid=" + Binder.getCallingUid() 3630 + " requires " + android.Manifest.permission.BIND_VOICE_INTERACTION; 3631 Slog.w(TAG, msg); 3632 throw new SecurityException(msg); 3633 } 3634 if (session == null || interactor == null) { 3635 throw new NullPointerException("null session or interactor"); 3636 } 3637 userId = handleIncomingUser(callingPid, callingUid, userId, 3638 false, ALLOW_FULL_ONLY, "startVoiceActivity", null); 3639 // TODO: Switch to user app stacks here. 3640 return mStackSupervisor.startActivityMayWait(null, callingUid, callingPackage, intent, 3641 resolvedType, session, interactor, null, null, 0, startFlags, profilerInfo, null, 3642 null, options, userId, null, null); 3643 } 3644 3645 @Override 3646 public boolean startNextMatchingActivity(IBinder callingActivity, 3647 Intent intent, Bundle options) { 3648 // Refuse possible leaked file descriptors 3649 if (intent != null && intent.hasFileDescriptors() == true) { 3650 throw new IllegalArgumentException("File descriptors passed in Intent"); 3651 } 3652 3653 synchronized (this) { 3654 final ActivityRecord r = ActivityRecord.isInStackLocked(callingActivity); 3655 if (r == null) { 3656 ActivityOptions.abort(options); 3657 return false; 3658 } 3659 if (r.app == null || r.app.thread == null) { 3660 // The caller is not running... d'oh! 3661 ActivityOptions.abort(options); 3662 return false; 3663 } 3664 intent = new Intent(intent); 3665 // The caller is not allowed to change the data. 3666 intent.setDataAndType(r.intent.getData(), r.intent.getType()); 3667 // And we are resetting to find the next component... 3668 intent.setComponent(null); 3669 3670 final boolean debug = ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0); 3671 3672 ActivityInfo aInfo = null; 3673 try { 3674 List<ResolveInfo> resolves = 3675 AppGlobals.getPackageManager().queryIntentActivities( 3676 intent, r.resolvedType, 3677 PackageManager.MATCH_DEFAULT_ONLY | STOCK_PM_FLAGS, 3678 UserHandle.getCallingUserId()); 3679 3680 // Look for the original activity in the list... 3681 final int N = resolves != null ? resolves.size() : 0; 3682 for (int i=0; i<N; i++) { 3683 ResolveInfo rInfo = resolves.get(i); 3684 if (rInfo.activityInfo.packageName.equals(r.packageName) 3685 && rInfo.activityInfo.name.equals(r.info.name)) { 3686 // We found the current one... the next matching is 3687 // after it. 3688 i++; 3689 if (i<N) { 3690 aInfo = resolves.get(i).activityInfo; 3691 } 3692 if (debug) { 3693 Slog.v(TAG, "Next matching activity: found current " + r.packageName 3694 + "/" + r.info.name); 3695 Slog.v(TAG, "Next matching activity: next is " + aInfo.packageName 3696 + "/" + aInfo.name); 3697 } 3698 break; 3699 } 3700 } 3701 } catch (RemoteException e) { 3702 } 3703 3704 if (aInfo == null) { 3705 // Nobody who is next! 3706 ActivityOptions.abort(options); 3707 if (debug) Slog.d(TAG, "Next matching activity: nothing found"); 3708 return false; 3709 } 3710 3711 intent.setComponent(new ComponentName( 3712 aInfo.applicationInfo.packageName, aInfo.name)); 3713 intent.setFlags(intent.getFlags()&~( 3714 Intent.FLAG_ACTIVITY_FORWARD_RESULT| 3715 Intent.FLAG_ACTIVITY_CLEAR_TOP| 3716 Intent.FLAG_ACTIVITY_MULTIPLE_TASK| 3717 Intent.FLAG_ACTIVITY_NEW_TASK)); 3718 3719 // Okay now we need to start the new activity, replacing the 3720 // currently running activity. This is a little tricky because 3721 // we want to start the new one as if the current one is finished, 3722 // but not finish the current one first so that there is no flicker. 3723 // And thus... 3724 final boolean wasFinishing = r.finishing; 3725 r.finishing = true; 3726 3727 // Propagate reply information over to the new activity. 3728 final ActivityRecord resultTo = r.resultTo; 3729 final String resultWho = r.resultWho; 3730 final int requestCode = r.requestCode; 3731 r.resultTo = null; 3732 if (resultTo != null) { 3733 resultTo.removeResultsLocked(r, resultWho, requestCode); 3734 } 3735 3736 final long origId = Binder.clearCallingIdentity(); 3737 int res = mStackSupervisor.startActivityLocked(r.app.thread, intent, 3738 r.resolvedType, aInfo, null, null, resultTo != null ? resultTo.appToken : null, 3739 resultWho, requestCode, -1, r.launchedFromUid, r.launchedFromPackage, 0, 3740 options, false, null, null, null); 3741 Binder.restoreCallingIdentity(origId); 3742 3743 r.finishing = wasFinishing; 3744 if (res != ActivityManager.START_SUCCESS) { 3745 return false; 3746 } 3747 return true; 3748 } 3749 } 3750 3751 @Override 3752 public final int startActivityFromRecents(int taskId, Bundle options) { 3753 if (checkCallingPermission(START_TASKS_FROM_RECENTS) != PackageManager.PERMISSION_GRANTED) { 3754 String msg = "Permission Denial: startActivityFromRecents called without " + 3755 START_TASKS_FROM_RECENTS; 3756 Slog.w(TAG, msg); 3757 throw new SecurityException(msg); 3758 } 3759 return startActivityFromRecentsInner(taskId, options); 3760 } 3761 3762 final int startActivityFromRecentsInner(int taskId, Bundle options) { 3763 final TaskRecord task; 3764 final int callingUid; 3765 final String callingPackage; 3766 final Intent intent; 3767 final int userId; 3768 synchronized (this) { 3769 task = recentTaskForIdLocked(taskId); 3770 if (task == null) { 3771 throw new IllegalArgumentException("Task " + taskId + " not found."); 3772 } 3773 callingUid = task.mCallingUid; 3774 callingPackage = task.mCallingPackage; 3775 intent = task.intent; 3776 intent.addFlags(Intent.FLAG_ACTIVITY_LAUNCHED_FROM_HISTORY); 3777 userId = task.userId; 3778 } 3779 return startActivityInPackage(callingUid, callingPackage, intent, null, null, null, 0, 0, 3780 options, userId, null, task); 3781 } 3782 3783 final int startActivityInPackage(int uid, String callingPackage, 3784 Intent intent, String resolvedType, IBinder resultTo, 3785 String resultWho, int requestCode, int startFlags, Bundle options, int userId, 3786 IActivityContainer container, TaskRecord inTask) { 3787 3788 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3789 false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 3790 3791 // TODO: Switch to user app stacks here. 3792 int ret = mStackSupervisor.startActivityMayWait(null, uid, callingPackage, intent, 3793 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3794 null, null, null, options, userId, container, inTask); 3795 return ret; 3796 } 3797 3798 @Override 3799 public final int startActivities(IApplicationThread caller, String callingPackage, 3800 Intent[] intents, String[] resolvedTypes, IBinder resultTo, Bundle options, 3801 int userId) { 3802 enforceNotIsolatedCaller("startActivities"); 3803 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3804 false, ALLOW_FULL_ONLY, "startActivity", null); 3805 // TODO: Switch to user app stacks here. 3806 int ret = mStackSupervisor.startActivities(caller, -1, callingPackage, intents, 3807 resolvedTypes, resultTo, options, userId); 3808 return ret; 3809 } 3810 3811 final int startActivitiesInPackage(int uid, String callingPackage, 3812 Intent[] intents, String[] resolvedTypes, IBinder resultTo, 3813 Bundle options, int userId) { 3814 3815 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3816 false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 3817 // TODO: Switch to user app stacks here. 3818 int ret = mStackSupervisor.startActivities(null, uid, callingPackage, intents, resolvedTypes, 3819 resultTo, options, userId); 3820 return ret; 3821 } 3822 3823 //explicitly remove thd old information in mRecentTasks when removing existing user. 3824 private void removeRecentTasksForUserLocked(int userId) { 3825 if(userId <= 0) { 3826 Slog.i(TAG, "Can't remove recent task on user " + userId); 3827 return; 3828 } 3829 3830 for (int i = mRecentTasks.size() - 1; i >= 0; --i) { 3831 TaskRecord tr = mRecentTasks.get(i); 3832 if (tr.userId == userId) { 3833 if(DEBUG_TASKS) Slog.i(TAG, "remove RecentTask " + tr 3834 + " when finishing user" + userId); 3835 mRecentTasks.remove(i); 3836 tr.removedFromRecents(mTaskPersister); 3837 } 3838 } 3839 3840 // Remove tasks from persistent storage. 3841 mTaskPersister.wakeup(null, true); 3842 } 3843 3844 /** 3845 * Update the recent tasks lists: make sure tasks should still be here (their 3846 * applications / activities still exist), update their availability, fixup ordering 3847 * of affiliations. 3848 */ 3849 void cleanupRecentTasksLocked(int userId) { 3850 if (mRecentTasks == null) { 3851 // Happens when called from the packagemanager broadcast before boot. 3852 return; 3853 } 3854 3855 final HashMap<ComponentName, ActivityInfo> availActCache = new HashMap<>(); 3856 final HashMap<String, ApplicationInfo> availAppCache = new HashMap<>(); 3857 final IPackageManager pm = AppGlobals.getPackageManager(); 3858 final ActivityInfo dummyAct = new ActivityInfo(); 3859 final ApplicationInfo dummyApp = new ApplicationInfo(); 3860 3861 int N = mRecentTasks.size(); 3862 3863 int[] users = userId == UserHandle.USER_ALL 3864 ? getUsersLocked() : new int[] { userId }; 3865 for (int user : users) { 3866 for (int i = 0; i < N; i++) { 3867 TaskRecord task = mRecentTasks.get(i); 3868 if (task.userId != user) { 3869 // Only look at tasks for the user ID of interest. 3870 continue; 3871 } 3872 if (task.autoRemoveRecents && task.getTopActivity() == null) { 3873 // This situation is broken, and we should just get rid of it now. 3874 mRecentTasks.remove(i); 3875 task.removedFromRecents(mTaskPersister); 3876 i--; 3877 N--; 3878 Slog.w(TAG, "Removing auto-remove without activity: " + task); 3879 continue; 3880 } 3881 // Check whether this activity is currently available. 3882 if (task.realActivity != null) { 3883 ActivityInfo ai = availActCache.get(task.realActivity); 3884 if (ai == null) { 3885 try { 3886 ai = pm.getActivityInfo(task.realActivity, 3887 PackageManager.GET_UNINSTALLED_PACKAGES 3888 | PackageManager.GET_DISABLED_COMPONENTS, user); 3889 } catch (RemoteException e) { 3890 // Will never happen. 3891 continue; 3892 } 3893 if (ai == null) { 3894 ai = dummyAct; 3895 } 3896 availActCache.put(task.realActivity, ai); 3897 } 3898 if (ai == dummyAct) { 3899 // This could be either because the activity no longer exists, or the 3900 // app is temporarily gone. For the former we want to remove the recents 3901 // entry; for the latter we want to mark it as unavailable. 3902 ApplicationInfo app = availAppCache.get(task.realActivity.getPackageName()); 3903 if (app == null) { 3904 try { 3905 app = pm.getApplicationInfo(task.realActivity.getPackageName(), 3906 PackageManager.GET_UNINSTALLED_PACKAGES 3907 | PackageManager.GET_DISABLED_COMPONENTS, user); 3908 } catch (RemoteException e) { 3909 // Will never happen. 3910 continue; 3911 } 3912 if (app == null) { 3913 app = dummyApp; 3914 } 3915 availAppCache.put(task.realActivity.getPackageName(), app); 3916 } 3917 if (app == dummyApp || (app.flags&ApplicationInfo.FLAG_INSTALLED) == 0) { 3918 // Doesn't exist any more! Good-bye. 3919 mRecentTasks.remove(i); 3920 task.removedFromRecents(mTaskPersister); 3921 i--; 3922 N--; 3923 Slog.w(TAG, "Removing no longer valid recent: " + task); 3924 continue; 3925 } else { 3926 // Otherwise just not available for now. 3927 if (task.isAvailable) { 3928 if (DEBUG_RECENTS) Slog.d(TAG, "Making recent unavailable: " 3929 + task); 3930 } 3931 task.isAvailable = false; 3932 } 3933 } else { 3934 if (!ai.enabled || !ai.applicationInfo.enabled 3935 || (ai.applicationInfo.flags&ApplicationInfo.FLAG_INSTALLED) == 0) { 3936 if (task.isAvailable) { 3937 if (DEBUG_RECENTS) Slog.d(TAG, "Making recent unavailable: " 3938 + task + " (enabled=" + ai.enabled + "/" 3939 + ai.applicationInfo.enabled + " flags=" 3940 + Integer.toHexString(ai.applicationInfo.flags) + ")"); 3941 } 3942 task.isAvailable = false; 3943 } else { 3944 if (!task.isAvailable) { 3945 if (DEBUG_RECENTS) Slog.d(TAG, "Making recent available: " 3946 + task); 3947 } 3948 task.isAvailable = true; 3949 } 3950 } 3951 } 3952 } 3953 } 3954 3955 // Verify the affiliate chain for each task. 3956 for (int i = 0; i < N; ) { 3957 TaskRecord task = mRecentTasks.remove(i); 3958 if (mTmpRecents.contains(task)) { 3959 continue; 3960 } 3961 int affiliatedTaskId = task.mAffiliatedTaskId; 3962 while (true) { 3963 TaskRecord next = task.mNextAffiliate; 3964 if (next == null) { 3965 break; 3966 } 3967 if (next.mAffiliatedTaskId != affiliatedTaskId) { 3968 Slog.e(TAG, "Error in Recents: next.affiliatedTaskId=" + 3969 next.mAffiliatedTaskId + " affiliatedTaskId=" + affiliatedTaskId); 3970 task.setNextAffiliate(null); 3971 if (next.mPrevAffiliate == task) { 3972 next.setPrevAffiliate(null); 3973 } 3974 break; 3975 } 3976 if (next.mPrevAffiliate != task) { 3977 Slog.e(TAG, "Error in Recents chain prev.mNextAffiliate=" + 3978 next.mPrevAffiliate + " task=" + task); 3979 next.setPrevAffiliate(null); 3980 task.setNextAffiliate(null); 3981 break; 3982 } 3983 if (!mRecentTasks.contains(next)) { 3984 Slog.e(TAG, "Error in Recents: next=" + next + " not in mRecentTasks"); 3985 task.setNextAffiliate(null); 3986 // We know that next.mPrevAffiliate is always task, from above, so clear 3987 // its previous affiliate. 3988 next.setPrevAffiliate(null); 3989 break; 3990 } 3991 task = next; 3992 } 3993 // task is now the end of the list 3994 do { 3995 mRecentTasks.remove(task); 3996 mRecentTasks.add(i++, task); 3997 mTmpRecents.add(task); 3998 task.inRecents = true; 3999 } while ((task = task.mPrevAffiliate) != null); 4000 } 4001 mTmpRecents.clear(); 4002 // mRecentTasks is now in sorted, affiliated order. 4003 } 4004 4005 private final boolean moveAffiliatedTasksToFront(TaskRecord task, int taskIndex) { 4006 int N = mRecentTasks.size(); 4007 TaskRecord top = task; 4008 int topIndex = taskIndex; 4009 while (top.mNextAffiliate != null && topIndex > 0) { 4010 top = top.mNextAffiliate; 4011 topIndex--; 4012 } 4013 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: adding affilliates starting at " 4014 + topIndex + " from intial " + taskIndex); 4015 // Find the end of the chain, doing a sanity check along the way. 4016 boolean sane = top.mAffiliatedTaskId == task.mAffiliatedTaskId; 4017 int endIndex = topIndex; 4018 TaskRecord prev = top; 4019 while (endIndex < N) { 4020 TaskRecord cur = mRecentTasks.get(endIndex); 4021 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: looking at next chain @" 4022 + endIndex + " " + cur); 4023 if (cur == top) { 4024 // Verify start of the chain. 4025 if (cur.mNextAffiliate != null || cur.mNextAffiliateTaskId != -1) { 4026 Slog.wtf(TAG, "Bad chain @" + endIndex 4027 + ": first task has next affiliate: " + prev); 4028 sane = false; 4029 break; 4030 } 4031 } else { 4032 // Verify middle of the chain's next points back to the one before. 4033 if (cur.mNextAffiliate != prev 4034 || cur.mNextAffiliateTaskId != prev.taskId) { 4035 Slog.wtf(TAG, "Bad chain @" + endIndex 4036 + ": middle task " + cur + " @" + endIndex 4037 + " has bad next affiliate " 4038 + cur.mNextAffiliate + " id " + cur.mNextAffiliateTaskId 4039 + ", expected " + prev); 4040 sane = false; 4041 break; 4042 } 4043 } 4044 if (cur.mPrevAffiliateTaskId == -1) { 4045 // Chain ends here. 4046 if (cur.mPrevAffiliate != null) { 4047 Slog.wtf(TAG, "Bad chain @" + endIndex 4048 + ": last task " + cur + " has previous affiliate " 4049 + cur.mPrevAffiliate); 4050 sane = false; 4051 } 4052 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: end of chain @" + endIndex); 4053 break; 4054 } else { 4055 // Verify middle of the chain's prev points to a valid item. 4056 if (cur.mPrevAffiliate == null) { 4057 Slog.wtf(TAG, "Bad chain @" + endIndex 4058 + ": task " + cur + " has previous affiliate " 4059 + cur.mPrevAffiliate + " but should be id " 4060 + cur.mPrevAffiliate); 4061 sane = false; 4062 break; 4063 } 4064 } 4065 if (cur.mAffiliatedTaskId != task.mAffiliatedTaskId) { 4066 Slog.wtf(TAG, "Bad chain @" + endIndex 4067 + ": task " + cur + " has affiliated id " 4068 + cur.mAffiliatedTaskId + " but should be " 4069 + task.mAffiliatedTaskId); 4070 sane = false; 4071 break; 4072 } 4073 prev = cur; 4074 endIndex++; 4075 if (endIndex >= N) { 4076 Slog.wtf(TAG, "Bad chain ran off index " + endIndex 4077 + ": last task " + prev); 4078 sane = false; 4079 break; 4080 } 4081 } 4082 if (sane) { 4083 if (endIndex < taskIndex) { 4084 Slog.wtf(TAG, "Bad chain @" + endIndex 4085 + ": did not extend to task " + task + " @" + taskIndex); 4086 sane = false; 4087 } 4088 } 4089 if (sane) { 4090 // All looks good, we can just move all of the affiliated tasks 4091 // to the top. 4092 for (int i=topIndex; i<=endIndex; i++) { 4093 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: moving affiliated " + task 4094 + " from " + i + " to " + (i-topIndex)); 4095 TaskRecord cur = mRecentTasks.remove(i); 4096 mRecentTasks.add(i-topIndex, cur); 4097 } 4098 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: done moving tasks " + topIndex 4099 + " to " + endIndex); 4100 return true; 4101 } 4102 4103 // Whoops, couldn't do it. 4104 return false; 4105 } 4106 4107 final void addRecentTaskLocked(TaskRecord task) { 4108 final boolean isAffiliated = task.mAffiliatedTaskId != task.taskId 4109 || task.mNextAffiliateTaskId != -1 || task.mPrevAffiliateTaskId != -1; 4110 4111 int N = mRecentTasks.size(); 4112 // Quick case: check if the top-most recent task is the same. 4113 if (!isAffiliated && N > 0 && mRecentTasks.get(0) == task) { 4114 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: already at top: " + task); 4115 return; 4116 } 4117 // Another quick case: check if this is part of a set of affiliated 4118 // tasks that are at the top. 4119 if (isAffiliated && N > 0 && task.inRecents 4120 && task.mAffiliatedTaskId == mRecentTasks.get(0).mAffiliatedTaskId) { 4121 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: affiliated " + mRecentTasks.get(0) 4122 + " at top when adding " + task); 4123 return; 4124 } 4125 // Another quick case: never add voice sessions. 4126 if (task.voiceSession != null) { 4127 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: not adding voice interaction " + task); 4128 return; 4129 } 4130 4131 boolean needAffiliationFix = false; 4132 4133 // Slightly less quick case: the task is already in recents, so all we need 4134 // to do is move it. 4135 if (task.inRecents) { 4136 int taskIndex = mRecentTasks.indexOf(task); 4137 if (taskIndex >= 0) { 4138 if (!isAffiliated) { 4139 // Simple case: this is not an affiliated task, so we just move it to the front. 4140 mRecentTasks.remove(taskIndex); 4141 mRecentTasks.add(0, task); 4142 notifyTaskPersisterLocked(task, false); 4143 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: moving to top " + task 4144 + " from " + taskIndex); 4145 return; 4146 } else { 4147 // More complicated: need to keep all affiliated tasks together. 4148 if (moveAffiliatedTasksToFront(task, taskIndex)) { 4149 // All went well. 4150 return; 4151 } 4152 4153 // Uh oh... something bad in the affiliation chain, try to rebuild 4154 // everything and then go through our general path of adding a new task. 4155 needAffiliationFix = true; 4156 } 4157 } else { 4158 Slog.wtf(TAG, "Task with inRecent not in recents: " + task); 4159 needAffiliationFix = true; 4160 } 4161 } 4162 4163 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: trimming tasks for " + task); 4164 trimRecentsForTask(task, true); 4165 4166 N = mRecentTasks.size(); 4167 while (N >= ActivityManager.getMaxRecentTasksStatic()) { 4168 final TaskRecord tr = mRecentTasks.remove(N - 1); 4169 tr.removedFromRecents(mTaskPersister); 4170 N--; 4171 } 4172 task.inRecents = true; 4173 if (!isAffiliated || needAffiliationFix) { 4174 // If this is a simple non-affiliated task, or we had some failure trying to 4175 // handle it as part of an affilated task, then just place it at the top. 4176 mRecentTasks.add(0, task); 4177 } else if (isAffiliated) { 4178 // If this is a new affiliated task, then move all of the affiliated tasks 4179 // to the front and insert this new one. 4180 TaskRecord other = task.mNextAffiliate; 4181 if (other == null) { 4182 other = task.mPrevAffiliate; 4183 } 4184 if (other != null) { 4185 int otherIndex = mRecentTasks.indexOf(other); 4186 if (otherIndex >= 0) { 4187 // Insert new task at appropriate location. 4188 int taskIndex; 4189 if (other == task.mNextAffiliate) { 4190 // We found the index of our next affiliation, which is who is 4191 // before us in the list, so add after that point. 4192 taskIndex = otherIndex+1; 4193 } else { 4194 // We found the index of our previous affiliation, which is who is 4195 // after us in the list, so add at their position. 4196 taskIndex = otherIndex; 4197 } 4198 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: new affiliated task added at " 4199 + taskIndex + ": " + task); 4200 mRecentTasks.add(taskIndex, task); 4201 4202 // Now move everything to the front. 4203 if (moveAffiliatedTasksToFront(task, taskIndex)) { 4204 // All went well. 4205 return; 4206 } 4207 4208 // Uh oh... something bad in the affiliation chain, try to rebuild 4209 // everything and then go through our general path of adding a new task. 4210 needAffiliationFix = true; 4211 } else { 4212 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: couldn't find other affiliation " 4213 + other); 4214 needAffiliationFix = true; 4215 } 4216 } else { 4217 if (DEBUG_RECENTS) Slog.d(TAG, 4218 "addRecent: adding affiliated task without next/prev:" + task); 4219 needAffiliationFix = true; 4220 } 4221 } 4222 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: adding " + task); 4223 4224 if (needAffiliationFix) { 4225 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: regrouping affiliations"); 4226 cleanupRecentTasksLocked(task.userId); 4227 } 4228 } 4229 4230 /** 4231 * If needed, remove oldest existing entries in recents that are for the same kind 4232 * of task as the given one. 4233 */ 4234 int trimRecentsForTask(TaskRecord task, boolean doTrim) { 4235 int N = mRecentTasks.size(); 4236 final Intent intent = task.intent; 4237 final boolean document = intent != null && intent.isDocument(); 4238 4239 int maxRecents = task.maxRecents - 1; 4240 for (int i=0; i<N; i++) { 4241 final TaskRecord tr = mRecentTasks.get(i); 4242 if (task != tr) { 4243 if (task.userId != tr.userId) { 4244 continue; 4245 } 4246 if (i > MAX_RECENT_BITMAPS) { 4247 tr.freeLastThumbnail(); 4248 } 4249 final Intent trIntent = tr.intent; 4250 if ((task.affinity == null || !task.affinity.equals(tr.affinity)) && 4251 (intent == null || !intent.filterEquals(trIntent))) { 4252 continue; 4253 } 4254 final boolean trIsDocument = trIntent != null && trIntent.isDocument(); 4255 if (document && trIsDocument) { 4256 // These are the same document activity (not necessarily the same doc). 4257 if (maxRecents > 0) { 4258 --maxRecents; 4259 continue; 4260 } 4261 // Hit the maximum number of documents for this task. Fall through 4262 // and remove this document from recents. 4263 } else if (document || trIsDocument) { 4264 // Only one of these is a document. Not the droid we're looking for. 4265 continue; 4266 } 4267 } 4268 4269 if (!doTrim) { 4270 // If the caller is not actually asking for a trim, just tell them we reached 4271 // a point where the trim would happen. 4272 return i; 4273 } 4274 4275 // Either task and tr are the same or, their affinities match or their intents match 4276 // and neither of them is a document, or they are documents using the same activity 4277 // and their maxRecents has been reached. 4278 tr.disposeThumbnail(); 4279 mRecentTasks.remove(i); 4280 if (task != tr) { 4281 tr.removedFromRecents(mTaskPersister); 4282 } 4283 i--; 4284 N--; 4285 if (task.intent == null) { 4286 // If the new recent task we are adding is not fully 4287 // specified, then replace it with the existing recent task. 4288 task = tr; 4289 } 4290 notifyTaskPersisterLocked(tr, false); 4291 } 4292 4293 return -1; 4294 } 4295 4296 @Override 4297 public void reportActivityFullyDrawn(IBinder token) { 4298 synchronized (this) { 4299 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4300 if (r == null) { 4301 return; 4302 } 4303 r.reportFullyDrawnLocked(); 4304 } 4305 } 4306 4307 @Override 4308 public void setRequestedOrientation(IBinder token, int requestedOrientation) { 4309 synchronized (this) { 4310 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4311 if (r == null) { 4312 return; 4313 } 4314 final long origId = Binder.clearCallingIdentity(); 4315 mWindowManager.setAppOrientation(r.appToken, requestedOrientation); 4316 Configuration config = mWindowManager.updateOrientationFromAppTokens( 4317 mConfiguration, r.mayFreezeScreenLocked(r.app) ? r.appToken : null); 4318 if (config != null) { 4319 r.frozenBeforeDestroy = true; 4320 if (!updateConfigurationLocked(config, r, false, false)) { 4321 mStackSupervisor.resumeTopActivitiesLocked(); 4322 } 4323 } 4324 Binder.restoreCallingIdentity(origId); 4325 } 4326 } 4327 4328 @Override 4329 public int getRequestedOrientation(IBinder token) { 4330 synchronized (this) { 4331 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4332 if (r == null) { 4333 return ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED; 4334 } 4335 return mWindowManager.getAppOrientation(r.appToken); 4336 } 4337 } 4338 4339 /** 4340 * This is the internal entry point for handling Activity.finish(). 4341 * 4342 * @param token The Binder token referencing the Activity we want to finish. 4343 * @param resultCode Result code, if any, from this Activity. 4344 * @param resultData Result data (Intent), if any, from this Activity. 4345 * @param finishTask Whether to finish the task associated with this Activity. Only applies to 4346 * the root Activity in the task. 4347 * 4348 * @return Returns true if the activity successfully finished, or false if it is still running. 4349 */ 4350 @Override 4351 public final boolean finishActivity(IBinder token, int resultCode, Intent resultData, 4352 boolean finishTask) { 4353 // Refuse possible leaked file descriptors 4354 if (resultData != null && resultData.hasFileDescriptors() == true) { 4355 throw new IllegalArgumentException("File descriptors passed in Intent"); 4356 } 4357 4358 synchronized(this) { 4359 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4360 if (r == null) { 4361 return true; 4362 } 4363 // Keep track of the root activity of the task before we finish it 4364 TaskRecord tr = r.task; 4365 ActivityRecord rootR = tr.getRootActivity(); 4366 // Do not allow task to finish in Lock Task mode. 4367 if (tr == mStackSupervisor.mLockTaskModeTask) { 4368 if (rootR == r) { 4369 mStackSupervisor.showLockTaskToast(); 4370 return false; 4371 } 4372 } 4373 if (mController != null) { 4374 // Find the first activity that is not finishing. 4375 ActivityRecord next = r.task.stack.topRunningActivityLocked(token, 0); 4376 if (next != null) { 4377 // ask watcher if this is allowed 4378 boolean resumeOK = true; 4379 try { 4380 resumeOK = mController.activityResuming(next.packageName); 4381 } catch (RemoteException e) { 4382 mController = null; 4383 Watchdog.getInstance().setActivityController(null); 4384 } 4385 4386 if (!resumeOK) { 4387 return false; 4388 } 4389 } 4390 } 4391 final long origId = Binder.clearCallingIdentity(); 4392 try { 4393 boolean res; 4394 if (finishTask && r == rootR) { 4395 // If requested, remove the task that is associated to this activity only if it 4396 // was the root activity in the task. The result code and data is ignored because 4397 // we don't support returning them across task boundaries. 4398 res = removeTaskByIdLocked(tr.taskId, 0); 4399 } else { 4400 res = tr.stack.requestFinishActivityLocked(token, resultCode, 4401 resultData, "app-request", true); 4402 } 4403 return res; 4404 } finally { 4405 Binder.restoreCallingIdentity(origId); 4406 } 4407 } 4408 } 4409 4410 @Override 4411 public final void finishHeavyWeightApp() { 4412 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4413 != PackageManager.PERMISSION_GRANTED) { 4414 String msg = "Permission Denial: finishHeavyWeightApp() from pid=" 4415 + Binder.getCallingPid() 4416 + ", uid=" + Binder.getCallingUid() 4417 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4418 Slog.w(TAG, msg); 4419 throw new SecurityException(msg); 4420 } 4421 4422 synchronized(this) { 4423 if (mHeavyWeightProcess == null) { 4424 return; 4425 } 4426 4427 ArrayList<ActivityRecord> activities = new ArrayList<ActivityRecord>( 4428 mHeavyWeightProcess.activities); 4429 for (int i=0; i<activities.size(); i++) { 4430 ActivityRecord r = activities.get(i); 4431 if (!r.finishing) { 4432 r.task.stack.finishActivityLocked(r, Activity.RESULT_CANCELED, 4433 null, "finish-heavy", true); 4434 } 4435 } 4436 4437 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 4438 mHeavyWeightProcess.userId, 0)); 4439 mHeavyWeightProcess = null; 4440 } 4441 } 4442 4443 @Override 4444 public void crashApplication(int uid, int initialPid, String packageName, 4445 String message) { 4446 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4447 != PackageManager.PERMISSION_GRANTED) { 4448 String msg = "Permission Denial: crashApplication() from pid=" 4449 + Binder.getCallingPid() 4450 + ", uid=" + Binder.getCallingUid() 4451 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4452 Slog.w(TAG, msg); 4453 throw new SecurityException(msg); 4454 } 4455 4456 synchronized(this) { 4457 ProcessRecord proc = null; 4458 4459 // Figure out which process to kill. We don't trust that initialPid 4460 // still has any relation to current pids, so must scan through the 4461 // list. 4462 synchronized (mPidsSelfLocked) { 4463 for (int i=0; i<mPidsSelfLocked.size(); i++) { 4464 ProcessRecord p = mPidsSelfLocked.valueAt(i); 4465 if (p.uid != uid) { 4466 continue; 4467 } 4468 if (p.pid == initialPid) { 4469 proc = p; 4470 break; 4471 } 4472 if (p.pkgList.containsKey(packageName)) { 4473 proc = p; 4474 } 4475 } 4476 } 4477 4478 if (proc == null) { 4479 Slog.w(TAG, "crashApplication: nothing for uid=" + uid 4480 + " initialPid=" + initialPid 4481 + " packageName=" + packageName); 4482 return; 4483 } 4484 4485 if (proc.thread != null) { 4486 if (proc.pid == Process.myPid()) { 4487 Log.w(TAG, "crashApplication: trying to crash self!"); 4488 return; 4489 } 4490 long ident = Binder.clearCallingIdentity(); 4491 try { 4492 proc.thread.scheduleCrash(message); 4493 } catch (RemoteException e) { 4494 } 4495 Binder.restoreCallingIdentity(ident); 4496 } 4497 } 4498 } 4499 4500 @Override 4501 public final void finishSubActivity(IBinder token, String resultWho, 4502 int requestCode) { 4503 synchronized(this) { 4504 final long origId = Binder.clearCallingIdentity(); 4505 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4506 if (r != null) { 4507 r.task.stack.finishSubActivityLocked(r, resultWho, requestCode); 4508 } 4509 Binder.restoreCallingIdentity(origId); 4510 } 4511 } 4512 4513 @Override 4514 public boolean finishActivityAffinity(IBinder token) { 4515 synchronized(this) { 4516 final long origId = Binder.clearCallingIdentity(); 4517 try { 4518 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4519 4520 ActivityRecord rootR = r.task.getRootActivity(); 4521 // Do not allow task to finish in Lock Task mode. 4522 if (r.task == mStackSupervisor.mLockTaskModeTask) { 4523 if (rootR == r) { 4524 mStackSupervisor.showLockTaskToast(); 4525 return false; 4526 } 4527 } 4528 boolean res = false; 4529 if (r != null) { 4530 res = r.task.stack.finishActivityAffinityLocked(r); 4531 } 4532 return res; 4533 } finally { 4534 Binder.restoreCallingIdentity(origId); 4535 } 4536 } 4537 } 4538 4539 @Override 4540 public void finishVoiceTask(IVoiceInteractionSession session) { 4541 synchronized(this) { 4542 final long origId = Binder.clearCallingIdentity(); 4543 try { 4544 mStackSupervisor.finishVoiceTask(session); 4545 } finally { 4546 Binder.restoreCallingIdentity(origId); 4547 } 4548 } 4549 4550 } 4551 4552 @Override 4553 public boolean releaseActivityInstance(IBinder token) { 4554 synchronized(this) { 4555 final long origId = Binder.clearCallingIdentity(); 4556 try { 4557 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4558 if (r.task == null || r.task.stack == null) { 4559 return false; 4560 } 4561 return r.task.stack.safelyDestroyActivityLocked(r, "app-req"); 4562 } finally { 4563 Binder.restoreCallingIdentity(origId); 4564 } 4565 } 4566 } 4567 4568 @Override 4569 public void releaseSomeActivities(IApplicationThread appInt) { 4570 synchronized(this) { 4571 final long origId = Binder.clearCallingIdentity(); 4572 try { 4573 ProcessRecord app = getRecordForAppLocked(appInt); 4574 mStackSupervisor.releaseSomeActivitiesLocked(app, "low-mem"); 4575 } finally { 4576 Binder.restoreCallingIdentity(origId); 4577 } 4578 } 4579 } 4580 4581 @Override 4582 public boolean willActivityBeVisible(IBinder token) { 4583 synchronized(this) { 4584 ActivityStack stack = ActivityRecord.getStackLocked(token); 4585 if (stack != null) { 4586 return stack.willActivityBeVisibleLocked(token); 4587 } 4588 return false; 4589 } 4590 } 4591 4592 @Override 4593 public void overridePendingTransition(IBinder token, String packageName, 4594 int enterAnim, int exitAnim) { 4595 synchronized(this) { 4596 ActivityRecord self = ActivityRecord.isInStackLocked(token); 4597 if (self == null) { 4598 return; 4599 } 4600 4601 final long origId = Binder.clearCallingIdentity(); 4602 4603 if (self.state == ActivityState.RESUMED 4604 || self.state == ActivityState.PAUSING) { 4605 mWindowManager.overridePendingAppTransition(packageName, 4606 enterAnim, exitAnim, null); 4607 } 4608 4609 Binder.restoreCallingIdentity(origId); 4610 } 4611 } 4612 4613 /** 4614 * Main function for removing an existing process from the activity manager 4615 * as a result of that process going away. Clears out all connections 4616 * to the process. 4617 */ 4618 private final void handleAppDiedLocked(ProcessRecord app, 4619 boolean restarting, boolean allowRestart) { 4620 int pid = app.pid; 4621 cleanUpApplicationRecordLocked(app, restarting, allowRestart, -1); 4622 if (!restarting) { 4623 removeLruProcessLocked(app); 4624 if (pid > 0) { 4625 ProcessList.remove(pid); 4626 } 4627 } 4628 4629 if (mProfileProc == app) { 4630 clearProfilerLocked(); 4631 } 4632 4633 // Remove this application's activities from active lists. 4634 boolean hasVisibleActivities = mStackSupervisor.handleAppDiedLocked(app); 4635 4636 app.activities.clear(); 4637 4638 if (app.instrumentationClass != null) { 4639 Slog.w(TAG, "Crash of app " + app.processName 4640 + " running instrumentation " + app.instrumentationClass); 4641 Bundle info = new Bundle(); 4642 info.putString("shortMsg", "Process crashed."); 4643 finishInstrumentationLocked(app, Activity.RESULT_CANCELED, info); 4644 } 4645 4646 if (!restarting) { 4647 if (!mStackSupervisor.resumeTopActivitiesLocked()) { 4648 // If there was nothing to resume, and we are not already 4649 // restarting this process, but there is a visible activity that 4650 // is hosted by the process... then make sure all visible 4651 // activities are running, taking care of restarting this 4652 // process. 4653 if (hasVisibleActivities) { 4654 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 4655 } 4656 } 4657 } 4658 } 4659 4660 private final int getLRURecordIndexForAppLocked(IApplicationThread thread) { 4661 IBinder threadBinder = thread.asBinder(); 4662 // Find the application record. 4663 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4664 ProcessRecord rec = mLruProcesses.get(i); 4665 if (rec.thread != null && rec.thread.asBinder() == threadBinder) { 4666 return i; 4667 } 4668 } 4669 return -1; 4670 } 4671 4672 final ProcessRecord getRecordForAppLocked( 4673 IApplicationThread thread) { 4674 if (thread == null) { 4675 return null; 4676 } 4677 4678 int appIndex = getLRURecordIndexForAppLocked(thread); 4679 return appIndex >= 0 ? mLruProcesses.get(appIndex) : null; 4680 } 4681 4682 final void doLowMemReportIfNeededLocked(ProcessRecord dyingProc) { 4683 // If there are no longer any background processes running, 4684 // and the app that died was not running instrumentation, 4685 // then tell everyone we are now low on memory. 4686 boolean haveBg = false; 4687 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4688 ProcessRecord rec = mLruProcesses.get(i); 4689 if (rec.thread != null 4690 && rec.setProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 4691 haveBg = true; 4692 break; 4693 } 4694 } 4695 4696 if (!haveBg) { 4697 boolean doReport = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 4698 if (doReport) { 4699 long now = SystemClock.uptimeMillis(); 4700 if (now < (mLastMemUsageReportTime+5*60*1000)) { 4701 doReport = false; 4702 } else { 4703 mLastMemUsageReportTime = now; 4704 } 4705 } 4706 final ArrayList<ProcessMemInfo> memInfos 4707 = doReport ? new ArrayList<ProcessMemInfo>(mLruProcesses.size()) : null; 4708 EventLog.writeEvent(EventLogTags.AM_LOW_MEMORY, mLruProcesses.size()); 4709 long now = SystemClock.uptimeMillis(); 4710 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4711 ProcessRecord rec = mLruProcesses.get(i); 4712 if (rec == dyingProc || rec.thread == null) { 4713 continue; 4714 } 4715 if (doReport) { 4716 memInfos.add(new ProcessMemInfo(rec.processName, rec.pid, rec.setAdj, 4717 rec.setProcState, rec.adjType, rec.makeAdjReason())); 4718 } 4719 if ((rec.lastLowMemory+GC_MIN_INTERVAL) <= now) { 4720 // The low memory report is overriding any current 4721 // state for a GC request. Make sure to do 4722 // heavy/important/visible/foreground processes first. 4723 if (rec.setAdj <= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 4724 rec.lastRequestedGc = 0; 4725 } else { 4726 rec.lastRequestedGc = rec.lastLowMemory; 4727 } 4728 rec.reportLowMemory = true; 4729 rec.lastLowMemory = now; 4730 mProcessesToGc.remove(rec); 4731 addProcessToGcListLocked(rec); 4732 } 4733 } 4734 if (doReport) { 4735 Message msg = mHandler.obtainMessage(REPORT_MEM_USAGE_MSG, memInfos); 4736 mHandler.sendMessage(msg); 4737 } 4738 scheduleAppGcsLocked(); 4739 } 4740 } 4741 4742 final void appDiedLocked(ProcessRecord app) { 4743 appDiedLocked(app, app.pid, app.thread); 4744 } 4745 4746 final void appDiedLocked(ProcessRecord app, int pid, 4747 IApplicationThread thread) { 4748 4749 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 4750 synchronized (stats) { 4751 stats.noteProcessDiedLocked(app.info.uid, pid); 4752 } 4753 4754 Process.killProcessGroup(app.info.uid, pid); 4755 4756 // Clean up already done if the process has been re-started. 4757 if (app.pid == pid && app.thread != null && 4758 app.thread.asBinder() == thread.asBinder()) { 4759 boolean doLowMem = app.instrumentationClass == null; 4760 boolean doOomAdj = doLowMem; 4761 if (!app.killedByAm) { 4762 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4763 + ") has died."); 4764 mAllowLowerMemLevel = true; 4765 } else { 4766 // Note that we always want to do oom adj to update our state with the 4767 // new number of procs. 4768 mAllowLowerMemLevel = false; 4769 doLowMem = false; 4770 } 4771 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4772 if (DEBUG_CLEANUP) Slog.v( 4773 TAG, "Dying app: " + app + ", pid: " + pid 4774 + ", thread: " + thread.asBinder()); 4775 handleAppDiedLocked(app, false, true); 4776 4777 if (doOomAdj) { 4778 updateOomAdjLocked(); 4779 } 4780 if (doLowMem) { 4781 doLowMemReportIfNeededLocked(app); 4782 } 4783 } else if (app.pid != pid) { 4784 // A new process has already been started. 4785 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4786 + ") has died and restarted (pid " + app.pid + ")."); 4787 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4788 } else if (DEBUG_PROCESSES) { 4789 Slog.d(TAG, "Received spurious death notification for thread " 4790 + thread.asBinder()); 4791 } 4792 } 4793 4794 /** 4795 * If a stack trace dump file is configured, dump process stack traces. 4796 * @param clearTraces causes the dump file to be erased prior to the new 4797 * traces being written, if true; when false, the new traces will be 4798 * appended to any existing file content. 4799 * @param firstPids of dalvik VM processes to dump stack traces for first 4800 * @param lastPids of dalvik VM processes to dump stack traces for last 4801 * @param nativeProcs optional list of native process names to dump stack crawls 4802 * @return file containing stack traces, or null if no dump file is configured 4803 */ 4804 public static File dumpStackTraces(boolean clearTraces, ArrayList<Integer> firstPids, 4805 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4806 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4807 if (tracesPath == null || tracesPath.length() == 0) { 4808 return null; 4809 } 4810 4811 File tracesFile = new File(tracesPath); 4812 try { 4813 File tracesDir = tracesFile.getParentFile(); 4814 if (!tracesDir.exists()) { 4815 tracesFile.mkdirs(); 4816 if (!SELinux.restorecon(tracesDir)) { 4817 return null; 4818 } 4819 } 4820 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4821 4822 if (clearTraces && tracesFile.exists()) tracesFile.delete(); 4823 tracesFile.createNewFile(); 4824 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4825 } catch (IOException e) { 4826 Slog.w(TAG, "Unable to prepare ANR traces file: " + tracesPath, e); 4827 return null; 4828 } 4829 4830 dumpStackTraces(tracesPath, firstPids, processCpuTracker, lastPids, nativeProcs); 4831 return tracesFile; 4832 } 4833 4834 private static void dumpStackTraces(String tracesPath, ArrayList<Integer> firstPids, 4835 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4836 // Use a FileObserver to detect when traces finish writing. 4837 // The order of traces is considered important to maintain for legibility. 4838 FileObserver observer = new FileObserver(tracesPath, FileObserver.CLOSE_WRITE) { 4839 @Override 4840 public synchronized void onEvent(int event, String path) { notify(); } 4841 }; 4842 4843 try { 4844 observer.startWatching(); 4845 4846 // First collect all of the stacks of the most important pids. 4847 if (firstPids != null) { 4848 try { 4849 int num = firstPids.size(); 4850 for (int i = 0; i < num; i++) { 4851 synchronized (observer) { 4852 Process.sendSignal(firstPids.get(i), Process.SIGNAL_QUIT); 4853 observer.wait(200); // Wait for write-close, give up after 200msec 4854 } 4855 } 4856 } catch (InterruptedException e) { 4857 Log.wtf(TAG, e); 4858 } 4859 } 4860 4861 // Next collect the stacks of the native pids 4862 if (nativeProcs != null) { 4863 int[] pids = Process.getPidsForCommands(nativeProcs); 4864 if (pids != null) { 4865 for (int pid : pids) { 4866 Debug.dumpNativeBacktraceToFile(pid, tracesPath); 4867 } 4868 } 4869 } 4870 4871 // Lastly, measure CPU usage. 4872 if (processCpuTracker != null) { 4873 processCpuTracker.init(); 4874 System.gc(); 4875 processCpuTracker.update(); 4876 try { 4877 synchronized (processCpuTracker) { 4878 processCpuTracker.wait(500); // measure over 1/2 second. 4879 } 4880 } catch (InterruptedException e) { 4881 } 4882 processCpuTracker.update(); 4883 4884 // We'll take the stack crawls of just the top apps using CPU. 4885 final int N = processCpuTracker.countWorkingStats(); 4886 int numProcs = 0; 4887 for (int i=0; i<N && numProcs<5; i++) { 4888 ProcessCpuTracker.Stats stats = processCpuTracker.getWorkingStats(i); 4889 if (lastPids.indexOfKey(stats.pid) >= 0) { 4890 numProcs++; 4891 try { 4892 synchronized (observer) { 4893 Process.sendSignal(stats.pid, Process.SIGNAL_QUIT); 4894 observer.wait(200); // Wait for write-close, give up after 200msec 4895 } 4896 } catch (InterruptedException e) { 4897 Log.wtf(TAG, e); 4898 } 4899 4900 } 4901 } 4902 } 4903 } finally { 4904 observer.stopWatching(); 4905 } 4906 } 4907 4908 final void logAppTooSlow(ProcessRecord app, long startTime, String msg) { 4909 if (true || IS_USER_BUILD) { 4910 return; 4911 } 4912 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4913 if (tracesPath == null || tracesPath.length() == 0) { 4914 return; 4915 } 4916 4917 StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads(); 4918 StrictMode.allowThreadDiskWrites(); 4919 try { 4920 final File tracesFile = new File(tracesPath); 4921 final File tracesDir = tracesFile.getParentFile(); 4922 final File tracesTmp = new File(tracesDir, "__tmp__"); 4923 try { 4924 if (!tracesDir.exists()) { 4925 tracesFile.mkdirs(); 4926 if (!SELinux.restorecon(tracesDir.getPath())) { 4927 return; 4928 } 4929 } 4930 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4931 4932 if (tracesFile.exists()) { 4933 tracesTmp.delete(); 4934 tracesFile.renameTo(tracesTmp); 4935 } 4936 StringBuilder sb = new StringBuilder(); 4937 Time tobj = new Time(); 4938 tobj.set(System.currentTimeMillis()); 4939 sb.append(tobj.format("%Y-%m-%d %H:%M:%S")); 4940 sb.append(": "); 4941 TimeUtils.formatDuration(SystemClock.uptimeMillis()-startTime, sb); 4942 sb.append(" since "); 4943 sb.append(msg); 4944 FileOutputStream fos = new FileOutputStream(tracesFile); 4945 fos.write(sb.toString().getBytes()); 4946 if (app == null) { 4947 fos.write("\n*** No application process!".getBytes()); 4948 } 4949 fos.close(); 4950 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4951 } catch (IOException e) { 4952 Slog.w(TAG, "Unable to prepare slow app traces file: " + tracesPath, e); 4953 return; 4954 } 4955 4956 if (app != null) { 4957 ArrayList<Integer> firstPids = new ArrayList<Integer>(); 4958 firstPids.add(app.pid); 4959 dumpStackTraces(tracesPath, firstPids, null, null, null); 4960 } 4961 4962 File lastTracesFile = null; 4963 File curTracesFile = null; 4964 for (int i=9; i>=0; i--) { 4965 String name = String.format(Locale.US, "slow%02d.txt", i); 4966 curTracesFile = new File(tracesDir, name); 4967 if (curTracesFile.exists()) { 4968 if (lastTracesFile != null) { 4969 curTracesFile.renameTo(lastTracesFile); 4970 } else { 4971 curTracesFile.delete(); 4972 } 4973 } 4974 lastTracesFile = curTracesFile; 4975 } 4976 tracesFile.renameTo(curTracesFile); 4977 if (tracesTmp.exists()) { 4978 tracesTmp.renameTo(tracesFile); 4979 } 4980 } finally { 4981 StrictMode.setThreadPolicy(oldPolicy); 4982 } 4983 } 4984 4985 final void appNotResponding(ProcessRecord app, ActivityRecord activity, 4986 ActivityRecord parent, boolean aboveSystem, final String annotation) { 4987 ArrayList<Integer> firstPids = new ArrayList<Integer>(5); 4988 SparseArray<Boolean> lastPids = new SparseArray<Boolean>(20); 4989 4990 if (mController != null) { 4991 try { 4992 // 0 == continue, -1 = kill process immediately 4993 int res = mController.appEarlyNotResponding(app.processName, app.pid, annotation); 4994 if (res < 0 && app.pid != MY_PID) { 4995 app.kill("anr", true); 4996 } 4997 } catch (RemoteException e) { 4998 mController = null; 4999 Watchdog.getInstance().setActivityController(null); 5000 } 5001 } 5002 5003 long anrTime = SystemClock.uptimeMillis(); 5004 if (MONITOR_CPU_USAGE) { 5005 updateCpuStatsNow(); 5006 } 5007 5008 synchronized (this) { 5009 // PowerManager.reboot() can block for a long time, so ignore ANRs while shutting down. 5010 if (mShuttingDown) { 5011 Slog.i(TAG, "During shutdown skipping ANR: " + app + " " + annotation); 5012 return; 5013 } else if (app.notResponding) { 5014 Slog.i(TAG, "Skipping duplicate ANR: " + app + " " + annotation); 5015 return; 5016 } else if (app.crashing) { 5017 Slog.i(TAG, "Crashing app skipping ANR: " + app + " " + annotation); 5018 return; 5019 } 5020 5021 // In case we come through here for the same app before completing 5022 // this one, mark as anring now so we will bail out. 5023 app.notResponding = true; 5024 5025 // Log the ANR to the event log. 5026 EventLog.writeEvent(EventLogTags.AM_ANR, app.userId, app.pid, 5027 app.processName, app.info.flags, annotation); 5028 5029 // Dump thread traces as quickly as we can, starting with "interesting" processes. 5030 firstPids.add(app.pid); 5031 5032 int parentPid = app.pid; 5033 if (parent != null && parent.app != null && parent.app.pid > 0) parentPid = parent.app.pid; 5034 if (parentPid != app.pid) firstPids.add(parentPid); 5035 5036 if (MY_PID != app.pid && MY_PID != parentPid) firstPids.add(MY_PID); 5037 5038 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 5039 ProcessRecord r = mLruProcesses.get(i); 5040 if (r != null && r.thread != null) { 5041 int pid = r.pid; 5042 if (pid > 0 && pid != app.pid && pid != parentPid && pid != MY_PID) { 5043 if (r.persistent) { 5044 firstPids.add(pid); 5045 } else { 5046 lastPids.put(pid, Boolean.TRUE); 5047 } 5048 } 5049 } 5050 } 5051 } 5052 5053 // Log the ANR to the main log. 5054 StringBuilder info = new StringBuilder(); 5055 info.setLength(0); 5056 info.append("ANR in ").append(app.processName); 5057 if (activity != null && activity.shortComponentName != null) { 5058 info.append(" (").append(activity.shortComponentName).append(")"); 5059 } 5060 info.append("\n"); 5061 info.append("PID: ").append(app.pid).append("\n"); 5062 if (annotation != null) { 5063 info.append("Reason: ").append(annotation).append("\n"); 5064 } 5065 if (parent != null && parent != activity) { 5066 info.append("Parent: ").append(parent.shortComponentName).append("\n"); 5067 } 5068 5069 final ProcessCpuTracker processCpuTracker = new ProcessCpuTracker(true); 5070 5071 File tracesFile = dumpStackTraces(true, firstPids, processCpuTracker, lastPids, 5072 NATIVE_STACKS_OF_INTEREST); 5073 5074 String cpuInfo = null; 5075 if (MONITOR_CPU_USAGE) { 5076 updateCpuStatsNow(); 5077 synchronized (mProcessCpuThread) { 5078 cpuInfo = mProcessCpuTracker.printCurrentState(anrTime); 5079 } 5080 info.append(processCpuTracker.printCurrentLoad()); 5081 info.append(cpuInfo); 5082 } 5083 5084 info.append(processCpuTracker.printCurrentState(anrTime)); 5085 5086 Slog.e(TAG, info.toString()); 5087 if (tracesFile == null) { 5088 // There is no trace file, so dump (only) the alleged culprit's threads to the log 5089 Process.sendSignal(app.pid, Process.SIGNAL_QUIT); 5090 } 5091 5092 addErrorToDropBox("anr", app, app.processName, activity, parent, annotation, 5093 cpuInfo, tracesFile, null); 5094 5095 if (mController != null) { 5096 try { 5097 // 0 == show dialog, 1 = keep waiting, -1 = kill process immediately 5098 int res = mController.appNotResponding(app.processName, app.pid, info.toString()); 5099 if (res != 0) { 5100 if (res < 0 && app.pid != MY_PID) { 5101 app.kill("anr", true); 5102 } else { 5103 synchronized (this) { 5104 mServices.scheduleServiceTimeoutLocked(app); 5105 } 5106 } 5107 return; 5108 } 5109 } catch (RemoteException e) { 5110 mController = null; 5111 Watchdog.getInstance().setActivityController(null); 5112 } 5113 } 5114 5115 // Unless configured otherwise, swallow ANRs in background processes & kill the process. 5116 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 5117 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 5118 5119 synchronized (this) { 5120 if (!showBackground && !app.isInterestingToUserLocked() && app.pid != MY_PID) { 5121 app.kill("bg anr", true); 5122 return; 5123 } 5124 5125 // Set the app's notResponding state, and look up the errorReportReceiver 5126 makeAppNotRespondingLocked(app, 5127 activity != null ? activity.shortComponentName : null, 5128 annotation != null ? "ANR " + annotation : "ANR", 5129 info.toString()); 5130 5131 // Bring up the infamous App Not Responding dialog 5132 Message msg = Message.obtain(); 5133 HashMap<String, Object> map = new HashMap<String, Object>(); 5134 msg.what = SHOW_NOT_RESPONDING_MSG; 5135 msg.obj = map; 5136 msg.arg1 = aboveSystem ? 1 : 0; 5137 map.put("app", app); 5138 if (activity != null) { 5139 map.put("activity", activity); 5140 } 5141 5142 mHandler.sendMessage(msg); 5143 } 5144 } 5145 5146 final void showLaunchWarningLocked(final ActivityRecord cur, final ActivityRecord next) { 5147 if (!mLaunchWarningShown) { 5148 mLaunchWarningShown = true; 5149 mHandler.post(new Runnable() { 5150 @Override 5151 public void run() { 5152 synchronized (ActivityManagerService.this) { 5153 final Dialog d = new LaunchWarningWindow(mContext, cur, next); 5154 d.show(); 5155 mHandler.postDelayed(new Runnable() { 5156 @Override 5157 public void run() { 5158 synchronized (ActivityManagerService.this) { 5159 d.dismiss(); 5160 mLaunchWarningShown = false; 5161 } 5162 } 5163 }, 4000); 5164 } 5165 } 5166 }); 5167 } 5168 } 5169 5170 @Override 5171 public boolean clearApplicationUserData(final String packageName, 5172 final IPackageDataObserver observer, int userId) { 5173 enforceNotIsolatedCaller("clearApplicationUserData"); 5174 int uid = Binder.getCallingUid(); 5175 int pid = Binder.getCallingPid(); 5176 userId = handleIncomingUser(pid, uid, 5177 userId, false, ALLOW_FULL_ONLY, "clearApplicationUserData", null); 5178 long callingId = Binder.clearCallingIdentity(); 5179 try { 5180 IPackageManager pm = AppGlobals.getPackageManager(); 5181 int pkgUid = -1; 5182 synchronized(this) { 5183 try { 5184 pkgUid = pm.getPackageUid(packageName, userId); 5185 } catch (RemoteException e) { 5186 } 5187 if (pkgUid == -1) { 5188 Slog.w(TAG, "Invalid packageName: " + packageName); 5189 if (observer != null) { 5190 try { 5191 observer.onRemoveCompleted(packageName, false); 5192 } catch (RemoteException e) { 5193 Slog.i(TAG, "Observer no longer exists."); 5194 } 5195 } 5196 return false; 5197 } 5198 if (uid == pkgUid || checkComponentPermission( 5199 android.Manifest.permission.CLEAR_APP_USER_DATA, 5200 pid, uid, -1, true) 5201 == PackageManager.PERMISSION_GRANTED) { 5202 forceStopPackageLocked(packageName, pkgUid, "clear data"); 5203 } else { 5204 throw new SecurityException("PID " + pid + " does not have permission " 5205 + android.Manifest.permission.CLEAR_APP_USER_DATA + " to clear data" 5206 + " of package " + packageName); 5207 } 5208 5209 // Remove all tasks match the cleared application package and user 5210 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 5211 final TaskRecord tr = mRecentTasks.get(i); 5212 final String taskPackageName = 5213 tr.getBaseIntent().getComponent().getPackageName(); 5214 if (tr.userId != userId) continue; 5215 if (!taskPackageName.equals(packageName)) continue; 5216 removeTaskByIdLocked(tr.taskId, 0); 5217 } 5218 } 5219 5220 try { 5221 // Clear application user data 5222 pm.clearApplicationUserData(packageName, observer, userId); 5223 5224 synchronized(this) { 5225 // Remove all permissions granted from/to this package 5226 removeUriPermissionsForPackageLocked(packageName, userId, true); 5227 } 5228 5229 Intent intent = new Intent(Intent.ACTION_PACKAGE_DATA_CLEARED, 5230 Uri.fromParts("package", packageName, null)); 5231 intent.putExtra(Intent.EXTRA_UID, pkgUid); 5232 broadcastIntentInPackage("android", Process.SYSTEM_UID, intent, 5233 null, null, 0, null, null, null, false, false, userId); 5234 } catch (RemoteException e) { 5235 } 5236 } finally { 5237 Binder.restoreCallingIdentity(callingId); 5238 } 5239 return true; 5240 } 5241 5242 @Override 5243 public void killBackgroundProcesses(final String packageName, int userId) { 5244 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 5245 != PackageManager.PERMISSION_GRANTED && 5246 checkCallingPermission(android.Manifest.permission.RESTART_PACKAGES) 5247 != PackageManager.PERMISSION_GRANTED) { 5248 String msg = "Permission Denial: killBackgroundProcesses() from pid=" 5249 + Binder.getCallingPid() 5250 + ", uid=" + Binder.getCallingUid() 5251 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 5252 Slog.w(TAG, msg); 5253 throw new SecurityException(msg); 5254 } 5255 5256 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 5257 userId, true, ALLOW_FULL_ONLY, "killBackgroundProcesses", null); 5258 long callingId = Binder.clearCallingIdentity(); 5259 try { 5260 IPackageManager pm = AppGlobals.getPackageManager(); 5261 synchronized(this) { 5262 int appId = -1; 5263 try { 5264 appId = UserHandle.getAppId(pm.getPackageUid(packageName, 0)); 5265 } catch (RemoteException e) { 5266 } 5267 if (appId == -1) { 5268 Slog.w(TAG, "Invalid packageName: " + packageName); 5269 return; 5270 } 5271 killPackageProcessesLocked(packageName, appId, userId, 5272 ProcessList.SERVICE_ADJ, false, true, true, false, "kill background"); 5273 } 5274 } finally { 5275 Binder.restoreCallingIdentity(callingId); 5276 } 5277 } 5278 5279 @Override 5280 public void killAllBackgroundProcesses() { 5281 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 5282 != PackageManager.PERMISSION_GRANTED) { 5283 String msg = "Permission Denial: killAllBackgroundProcesses() from pid=" 5284 + Binder.getCallingPid() 5285 + ", uid=" + Binder.getCallingUid() 5286 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 5287 Slog.w(TAG, msg); 5288 throw new SecurityException(msg); 5289 } 5290 5291 long callingId = Binder.clearCallingIdentity(); 5292 try { 5293 synchronized(this) { 5294 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 5295 final int NP = mProcessNames.getMap().size(); 5296 for (int ip=0; ip<NP; ip++) { 5297 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 5298 final int NA = apps.size(); 5299 for (int ia=0; ia<NA; ia++) { 5300 ProcessRecord app = apps.valueAt(ia); 5301 if (app.persistent) { 5302 // we don't kill persistent processes 5303 continue; 5304 } 5305 if (app.removed) { 5306 procs.add(app); 5307 } else if (app.setAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 5308 app.removed = true; 5309 procs.add(app); 5310 } 5311 } 5312 } 5313 5314 int N = procs.size(); 5315 for (int i=0; i<N; i++) { 5316 removeProcessLocked(procs.get(i), false, true, "kill all background"); 5317 } 5318 mAllowLowerMemLevel = true; 5319 updateOomAdjLocked(); 5320 doLowMemReportIfNeededLocked(null); 5321 } 5322 } finally { 5323 Binder.restoreCallingIdentity(callingId); 5324 } 5325 } 5326 5327 @Override 5328 public void forceStopPackage(final String packageName, int userId) { 5329 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 5330 != PackageManager.PERMISSION_GRANTED) { 5331 String msg = "Permission Denial: forceStopPackage() from pid=" 5332 + Binder.getCallingPid() 5333 + ", uid=" + Binder.getCallingUid() 5334 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 5335 Slog.w(TAG, msg); 5336 throw new SecurityException(msg); 5337 } 5338 final int callingPid = Binder.getCallingPid(); 5339 userId = handleIncomingUser(callingPid, Binder.getCallingUid(), 5340 userId, true, ALLOW_FULL_ONLY, "forceStopPackage", null); 5341 long callingId = Binder.clearCallingIdentity(); 5342 try { 5343 IPackageManager pm = AppGlobals.getPackageManager(); 5344 synchronized(this) { 5345 int[] users = userId == UserHandle.USER_ALL 5346 ? getUsersLocked() : new int[] { userId }; 5347 for (int user : users) { 5348 int pkgUid = -1; 5349 try { 5350 pkgUid = pm.getPackageUid(packageName, user); 5351 } catch (RemoteException e) { 5352 } 5353 if (pkgUid == -1) { 5354 Slog.w(TAG, "Invalid packageName: " + packageName); 5355 continue; 5356 } 5357 try { 5358 pm.setPackageStoppedState(packageName, true, user); 5359 } catch (RemoteException e) { 5360 } catch (IllegalArgumentException e) { 5361 Slog.w(TAG, "Failed trying to unstop package " 5362 + packageName + ": " + e); 5363 } 5364 if (isUserRunningLocked(user, false)) { 5365 forceStopPackageLocked(packageName, pkgUid, "from pid " + callingPid); 5366 } 5367 } 5368 } 5369 } finally { 5370 Binder.restoreCallingIdentity(callingId); 5371 } 5372 } 5373 5374 @Override 5375 public void addPackageDependency(String packageName) { 5376 synchronized (this) { 5377 int callingPid = Binder.getCallingPid(); 5378 if (callingPid == Process.myPid()) { 5379 // Yeah, um, no. 5380 Slog.w(TAG, "Can't addPackageDependency on system process"); 5381 return; 5382 } 5383 ProcessRecord proc; 5384 synchronized (mPidsSelfLocked) { 5385 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 5386 } 5387 if (proc != null) { 5388 if (proc.pkgDeps == null) { 5389 proc.pkgDeps = new ArraySet<String>(1); 5390 } 5391 proc.pkgDeps.add(packageName); 5392 } 5393 } 5394 } 5395 5396 /* 5397 * The pkg name and app id have to be specified. 5398 */ 5399 @Override 5400 public void killApplicationWithAppId(String pkg, int appid, String reason) { 5401 if (pkg == null) { 5402 return; 5403 } 5404 // Make sure the uid is valid. 5405 if (appid < 0) { 5406 Slog.w(TAG, "Invalid appid specified for pkg : " + pkg); 5407 return; 5408 } 5409 int callerUid = Binder.getCallingUid(); 5410 // Only the system server can kill an application 5411 if (callerUid == Process.SYSTEM_UID) { 5412 // Post an aysnc message to kill the application 5413 Message msg = mHandler.obtainMessage(KILL_APPLICATION_MSG); 5414 msg.arg1 = appid; 5415 msg.arg2 = 0; 5416 Bundle bundle = new Bundle(); 5417 bundle.putString("pkg", pkg); 5418 bundle.putString("reason", reason); 5419 msg.obj = bundle; 5420 mHandler.sendMessage(msg); 5421 } else { 5422 throw new SecurityException(callerUid + " cannot kill pkg: " + 5423 pkg); 5424 } 5425 } 5426 5427 @Override 5428 public void closeSystemDialogs(String reason) { 5429 enforceNotIsolatedCaller("closeSystemDialogs"); 5430 5431 final int pid = Binder.getCallingPid(); 5432 final int uid = Binder.getCallingUid(); 5433 final long origId = Binder.clearCallingIdentity(); 5434 try { 5435 synchronized (this) { 5436 // Only allow this from foreground processes, so that background 5437 // applications can't abuse it to prevent system UI from being shown. 5438 if (uid >= Process.FIRST_APPLICATION_UID) { 5439 ProcessRecord proc; 5440 synchronized (mPidsSelfLocked) { 5441 proc = mPidsSelfLocked.get(pid); 5442 } 5443 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 5444 Slog.w(TAG, "Ignoring closeSystemDialogs " + reason 5445 + " from background process " + proc); 5446 return; 5447 } 5448 } 5449 closeSystemDialogsLocked(reason); 5450 } 5451 } finally { 5452 Binder.restoreCallingIdentity(origId); 5453 } 5454 } 5455 5456 void closeSystemDialogsLocked(String reason) { 5457 Intent intent = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS); 5458 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5459 | Intent.FLAG_RECEIVER_FOREGROUND); 5460 if (reason != null) { 5461 intent.putExtra("reason", reason); 5462 } 5463 mWindowManager.closeSystemDialogs(reason); 5464 5465 mStackSupervisor.closeSystemDialogsLocked(); 5466 5467 broadcastIntentLocked(null, null, intent, null, 5468 null, 0, null, null, null, AppOpsManager.OP_NONE, false, false, -1, 5469 Process.SYSTEM_UID, UserHandle.USER_ALL); 5470 } 5471 5472 @Override 5473 public Debug.MemoryInfo[] getProcessMemoryInfo(int[] pids) { 5474 enforceNotIsolatedCaller("getProcessMemoryInfo"); 5475 Debug.MemoryInfo[] infos = new Debug.MemoryInfo[pids.length]; 5476 for (int i=pids.length-1; i>=0; i--) { 5477 ProcessRecord proc; 5478 int oomAdj; 5479 synchronized (this) { 5480 synchronized (mPidsSelfLocked) { 5481 proc = mPidsSelfLocked.get(pids[i]); 5482 oomAdj = proc != null ? proc.setAdj : 0; 5483 } 5484 } 5485 infos[i] = new Debug.MemoryInfo(); 5486 Debug.getMemoryInfo(pids[i], infos[i]); 5487 if (proc != null) { 5488 synchronized (this) { 5489 if (proc.thread != null && proc.setAdj == oomAdj) { 5490 // Record this for posterity if the process has been stable. 5491 proc.baseProcessTracker.addPss(infos[i].getTotalPss(), 5492 infos[i].getTotalUss(), false, proc.pkgList); 5493 } 5494 } 5495 } 5496 } 5497 return infos; 5498 } 5499 5500 @Override 5501 public long[] getProcessPss(int[] pids) { 5502 enforceNotIsolatedCaller("getProcessPss"); 5503 long[] pss = new long[pids.length]; 5504 for (int i=pids.length-1; i>=0; i--) { 5505 ProcessRecord proc; 5506 int oomAdj; 5507 synchronized (this) { 5508 synchronized (mPidsSelfLocked) { 5509 proc = mPidsSelfLocked.get(pids[i]); 5510 oomAdj = proc != null ? proc.setAdj : 0; 5511 } 5512 } 5513 long[] tmpUss = new long[1]; 5514 pss[i] = Debug.getPss(pids[i], tmpUss); 5515 if (proc != null) { 5516 synchronized (this) { 5517 if (proc.thread != null && proc.setAdj == oomAdj) { 5518 // Record this for posterity if the process has been stable. 5519 proc.baseProcessTracker.addPss(pss[i], tmpUss[0], false, proc.pkgList); 5520 } 5521 } 5522 } 5523 } 5524 return pss; 5525 } 5526 5527 @Override 5528 public void killApplicationProcess(String processName, int uid) { 5529 if (processName == null) { 5530 return; 5531 } 5532 5533 int callerUid = Binder.getCallingUid(); 5534 // Only the system server can kill an application 5535 if (callerUid == Process.SYSTEM_UID) { 5536 synchronized (this) { 5537 ProcessRecord app = getProcessRecordLocked(processName, uid, true); 5538 if (app != null && app.thread != null) { 5539 try { 5540 app.thread.scheduleSuicide(); 5541 } catch (RemoteException e) { 5542 // If the other end already died, then our work here is done. 5543 } 5544 } else { 5545 Slog.w(TAG, "Process/uid not found attempting kill of " 5546 + processName + " / " + uid); 5547 } 5548 } 5549 } else { 5550 throw new SecurityException(callerUid + " cannot kill app process: " + 5551 processName); 5552 } 5553 } 5554 5555 private void forceStopPackageLocked(final String packageName, int uid, String reason) { 5556 forceStopPackageLocked(packageName, UserHandle.getAppId(uid), false, 5557 false, true, false, false, UserHandle.getUserId(uid), reason); 5558 Intent intent = new Intent(Intent.ACTION_PACKAGE_RESTARTED, 5559 Uri.fromParts("package", packageName, null)); 5560 if (!mProcessesReady) { 5561 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5562 | Intent.FLAG_RECEIVER_FOREGROUND); 5563 } 5564 intent.putExtra(Intent.EXTRA_UID, uid); 5565 intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(uid)); 5566 broadcastIntentLocked(null, null, intent, 5567 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 5568 false, false, 5569 MY_PID, Process.SYSTEM_UID, UserHandle.getUserId(uid)); 5570 } 5571 5572 private void forceStopUserLocked(int userId, String reason) { 5573 forceStopPackageLocked(null, -1, false, false, true, false, false, userId, reason); 5574 Intent intent = new Intent(Intent.ACTION_USER_STOPPED); 5575 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5576 | Intent.FLAG_RECEIVER_FOREGROUND); 5577 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 5578 broadcastIntentLocked(null, null, intent, 5579 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 5580 false, false, 5581 MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 5582 } 5583 5584 private final boolean killPackageProcessesLocked(String packageName, int appId, 5585 int userId, int minOomAdj, boolean callerWillRestart, boolean allowRestart, 5586 boolean doit, boolean evenPersistent, String reason) { 5587 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 5588 5589 // Remove all processes this package may have touched: all with the 5590 // same UID (except for the system or root user), and all whose name 5591 // matches the package name. 5592 final int NP = mProcessNames.getMap().size(); 5593 for (int ip=0; ip<NP; ip++) { 5594 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 5595 final int NA = apps.size(); 5596 for (int ia=0; ia<NA; ia++) { 5597 ProcessRecord app = apps.valueAt(ia); 5598 if (app.persistent && !evenPersistent) { 5599 // we don't kill persistent processes 5600 continue; 5601 } 5602 if (app.removed) { 5603 if (doit) { 5604 procs.add(app); 5605 } 5606 continue; 5607 } 5608 5609 // Skip process if it doesn't meet our oom adj requirement. 5610 if (app.setAdj < minOomAdj) { 5611 continue; 5612 } 5613 5614 // If no package is specified, we call all processes under the 5615 // give user id. 5616 if (packageName == null) { 5617 if (app.userId != userId) { 5618 continue; 5619 } 5620 if (appId >= 0 && UserHandle.getAppId(app.uid) != appId) { 5621 continue; 5622 } 5623 // Package has been specified, we want to hit all processes 5624 // that match it. We need to qualify this by the processes 5625 // that are running under the specified app and user ID. 5626 } else { 5627 final boolean isDep = app.pkgDeps != null 5628 && app.pkgDeps.contains(packageName); 5629 if (!isDep && UserHandle.getAppId(app.uid) != appId) { 5630 continue; 5631 } 5632 if (userId != UserHandle.USER_ALL && app.userId != userId) { 5633 continue; 5634 } 5635 if (!app.pkgList.containsKey(packageName) && !isDep) { 5636 continue; 5637 } 5638 } 5639 5640 // Process has passed all conditions, kill it! 5641 if (!doit) { 5642 return true; 5643 } 5644 app.removed = true; 5645 procs.add(app); 5646 } 5647 } 5648 5649 int N = procs.size(); 5650 for (int i=0; i<N; i++) { 5651 removeProcessLocked(procs.get(i), callerWillRestart, allowRestart, reason); 5652 } 5653 updateOomAdjLocked(); 5654 return N > 0; 5655 } 5656 5657 private final boolean forceStopPackageLocked(String name, int appId, 5658 boolean callerWillRestart, boolean purgeCache, boolean doit, 5659 boolean evenPersistent, boolean uninstalling, int userId, String reason) { 5660 int i; 5661 int N; 5662 5663 if (userId == UserHandle.USER_ALL && name == null) { 5664 Slog.w(TAG, "Can't force stop all processes of all users, that is insane!"); 5665 } 5666 5667 if (appId < 0 && name != null) { 5668 try { 5669 appId = UserHandle.getAppId( 5670 AppGlobals.getPackageManager().getPackageUid(name, 0)); 5671 } catch (RemoteException e) { 5672 } 5673 } 5674 5675 if (doit) { 5676 if (name != null) { 5677 Slog.i(TAG, "Force stopping " + name + " appid=" + appId 5678 + " user=" + userId + ": " + reason); 5679 } else { 5680 Slog.i(TAG, "Force stopping u" + userId + ": " + reason); 5681 } 5682 5683 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 5684 for (int ip=pmap.size()-1; ip>=0; ip--) { 5685 SparseArray<Long> ba = pmap.valueAt(ip); 5686 for (i=ba.size()-1; i>=0; i--) { 5687 boolean remove = false; 5688 final int entUid = ba.keyAt(i); 5689 if (name != null) { 5690 if (userId == UserHandle.USER_ALL) { 5691 if (UserHandle.getAppId(entUid) == appId) { 5692 remove = true; 5693 } 5694 } else { 5695 if (entUid == UserHandle.getUid(userId, appId)) { 5696 remove = true; 5697 } 5698 } 5699 } else if (UserHandle.getUserId(entUid) == userId) { 5700 remove = true; 5701 } 5702 if (remove) { 5703 ba.removeAt(i); 5704 } 5705 } 5706 if (ba.size() == 0) { 5707 pmap.removeAt(ip); 5708 } 5709 } 5710 } 5711 5712 boolean didSomething = killPackageProcessesLocked(name, appId, userId, 5713 -100, callerWillRestart, true, doit, evenPersistent, 5714 name == null ? ("stop user " + userId) : ("stop " + name)); 5715 5716 if (mStackSupervisor.forceStopPackageLocked(name, doit, evenPersistent, userId)) { 5717 if (!doit) { 5718 return true; 5719 } 5720 didSomething = true; 5721 } 5722 5723 if (mServices.forceStopLocked(name, userId, evenPersistent, doit)) { 5724 if (!doit) { 5725 return true; 5726 } 5727 didSomething = true; 5728 } 5729 5730 if (name == null) { 5731 // Remove all sticky broadcasts from this user. 5732 mStickyBroadcasts.remove(userId); 5733 } 5734 5735 ArrayList<ContentProviderRecord> providers = new ArrayList<ContentProviderRecord>(); 5736 if (mProviderMap.collectForceStopProviders(name, appId, doit, evenPersistent, 5737 userId, providers)) { 5738 if (!doit) { 5739 return true; 5740 } 5741 didSomething = true; 5742 } 5743 N = providers.size(); 5744 for (i=0; i<N; i++) { 5745 removeDyingProviderLocked(null, providers.get(i), true); 5746 } 5747 5748 // Remove transient permissions granted from/to this package/user 5749 removeUriPermissionsForPackageLocked(name, userId, false); 5750 5751 if (name == null || uninstalling) { 5752 // Remove pending intents. For now we only do this when force 5753 // stopping users, because we have some problems when doing this 5754 // for packages -- app widgets are not currently cleaned up for 5755 // such packages, so they can be left with bad pending intents. 5756 if (mIntentSenderRecords.size() > 0) { 5757 Iterator<WeakReference<PendingIntentRecord>> it 5758 = mIntentSenderRecords.values().iterator(); 5759 while (it.hasNext()) { 5760 WeakReference<PendingIntentRecord> wpir = it.next(); 5761 if (wpir == null) { 5762 it.remove(); 5763 continue; 5764 } 5765 PendingIntentRecord pir = wpir.get(); 5766 if (pir == null) { 5767 it.remove(); 5768 continue; 5769 } 5770 if (name == null) { 5771 // Stopping user, remove all objects for the user. 5772 if (pir.key.userId != userId) { 5773 // Not the same user, skip it. 5774 continue; 5775 } 5776 } else { 5777 if (UserHandle.getAppId(pir.uid) != appId) { 5778 // Different app id, skip it. 5779 continue; 5780 } 5781 if (userId != UserHandle.USER_ALL && pir.key.userId != userId) { 5782 // Different user, skip it. 5783 continue; 5784 } 5785 if (!pir.key.packageName.equals(name)) { 5786 // Different package, skip it. 5787 continue; 5788 } 5789 } 5790 if (!doit) { 5791 return true; 5792 } 5793 didSomething = true; 5794 it.remove(); 5795 pir.canceled = true; 5796 if (pir.key.activity != null) { 5797 pir.key.activity.pendingResults.remove(pir.ref); 5798 } 5799 } 5800 } 5801 } 5802 5803 if (doit) { 5804 if (purgeCache && name != null) { 5805 AttributeCache ac = AttributeCache.instance(); 5806 if (ac != null) { 5807 ac.removePackage(name); 5808 } 5809 } 5810 if (mBooted) { 5811 mStackSupervisor.resumeTopActivitiesLocked(); 5812 mStackSupervisor.scheduleIdleLocked(); 5813 } 5814 } 5815 5816 return didSomething; 5817 } 5818 5819 private final boolean removeProcessLocked(ProcessRecord app, 5820 boolean callerWillRestart, boolean allowRestart, String reason) { 5821 final String name = app.processName; 5822 final int uid = app.uid; 5823 if (DEBUG_PROCESSES) Slog.d( 5824 TAG, "Force removing proc " + app.toShortString() + " (" + name 5825 + "/" + uid + ")"); 5826 5827 mProcessNames.remove(name, uid); 5828 mIsolatedProcesses.remove(app.uid); 5829 if (mHeavyWeightProcess == app) { 5830 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5831 mHeavyWeightProcess.userId, 0)); 5832 mHeavyWeightProcess = null; 5833 } 5834 boolean needRestart = false; 5835 if (app.pid > 0 && app.pid != MY_PID) { 5836 int pid = app.pid; 5837 synchronized (mPidsSelfLocked) { 5838 mPidsSelfLocked.remove(pid); 5839 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5840 } 5841 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 5842 if (app.isolated) { 5843 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5844 } 5845 app.kill(reason, true); 5846 handleAppDiedLocked(app, true, allowRestart); 5847 removeLruProcessLocked(app); 5848 5849 if (app.persistent && !app.isolated) { 5850 if (!callerWillRestart) { 5851 addAppLocked(app.info, false, null /* ABI override */); 5852 } else { 5853 needRestart = true; 5854 } 5855 } 5856 } else { 5857 mRemovedProcesses.add(app); 5858 } 5859 5860 return needRestart; 5861 } 5862 5863 private final void processStartTimedOutLocked(ProcessRecord app) { 5864 final int pid = app.pid; 5865 boolean gone = false; 5866 synchronized (mPidsSelfLocked) { 5867 ProcessRecord knownApp = mPidsSelfLocked.get(pid); 5868 if (knownApp != null && knownApp.thread == null) { 5869 mPidsSelfLocked.remove(pid); 5870 gone = true; 5871 } 5872 } 5873 5874 if (gone) { 5875 Slog.w(TAG, "Process " + app + " failed to attach"); 5876 EventLog.writeEvent(EventLogTags.AM_PROCESS_START_TIMEOUT, app.userId, 5877 pid, app.uid, app.processName); 5878 mProcessNames.remove(app.processName, app.uid); 5879 mIsolatedProcesses.remove(app.uid); 5880 if (mHeavyWeightProcess == app) { 5881 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5882 mHeavyWeightProcess.userId, 0)); 5883 mHeavyWeightProcess = null; 5884 } 5885 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 5886 if (app.isolated) { 5887 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5888 } 5889 // Take care of any launching providers waiting for this process. 5890 checkAppInLaunchingProvidersLocked(app, true); 5891 // Take care of any services that are waiting for the process. 5892 mServices.processStartTimedOutLocked(app); 5893 app.kill("start timeout", true); 5894 if (mBackupTarget != null && mBackupTarget.app.pid == pid) { 5895 Slog.w(TAG, "Unattached app died before backup, skipping"); 5896 try { 5897 IBackupManager bm = IBackupManager.Stub.asInterface( 5898 ServiceManager.getService(Context.BACKUP_SERVICE)); 5899 bm.agentDisconnected(app.info.packageName); 5900 } catch (RemoteException e) { 5901 // Can't happen; the backup manager is local 5902 } 5903 } 5904 if (isPendingBroadcastProcessLocked(pid)) { 5905 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 5906 skipPendingBroadcastLocked(pid); 5907 } 5908 } else { 5909 Slog.w(TAG, "Spurious process start timeout - pid not known for " + app); 5910 } 5911 } 5912 5913 private final boolean attachApplicationLocked(IApplicationThread thread, 5914 int pid) { 5915 5916 // Find the application record that is being attached... either via 5917 // the pid if we are running in multiple processes, or just pull the 5918 // next app record if we are emulating process with anonymous threads. 5919 ProcessRecord app; 5920 if (pid != MY_PID && pid >= 0) { 5921 synchronized (mPidsSelfLocked) { 5922 app = mPidsSelfLocked.get(pid); 5923 } 5924 } else { 5925 app = null; 5926 } 5927 5928 if (app == null) { 5929 Slog.w(TAG, "No pending application record for pid " + pid 5930 + " (IApplicationThread " + thread + "); dropping process"); 5931 EventLog.writeEvent(EventLogTags.AM_DROP_PROCESS, pid); 5932 if (pid > 0 && pid != MY_PID) { 5933 Process.killProcessQuiet(pid); 5934 //TODO: Process.killProcessGroup(app.info.uid, pid); 5935 } else { 5936 try { 5937 thread.scheduleExit(); 5938 } catch (Exception e) { 5939 // Ignore exceptions. 5940 } 5941 } 5942 return false; 5943 } 5944 5945 // If this application record is still attached to a previous 5946 // process, clean it up now. 5947 if (app.thread != null) { 5948 handleAppDiedLocked(app, true, true); 5949 } 5950 5951 // Tell the process all about itself. 5952 5953 if (localLOGV) Slog.v( 5954 TAG, "Binding process pid " + pid + " to record " + app); 5955 5956 final String processName = app.processName; 5957 try { 5958 AppDeathRecipient adr = new AppDeathRecipient( 5959 app, pid, thread); 5960 thread.asBinder().linkToDeath(adr, 0); 5961 app.deathRecipient = adr; 5962 } catch (RemoteException e) { 5963 app.resetPackageList(mProcessStats); 5964 startProcessLocked(app, "link fail", processName); 5965 return false; 5966 } 5967 5968 EventLog.writeEvent(EventLogTags.AM_PROC_BOUND, app.userId, app.pid, app.processName); 5969 5970 app.makeActive(thread, mProcessStats); 5971 app.curAdj = app.setAdj = -100; 5972 app.curSchedGroup = app.setSchedGroup = Process.THREAD_GROUP_DEFAULT; 5973 app.forcingToForeground = null; 5974 updateProcessForegroundLocked(app, false, false); 5975 app.hasShownUi = false; 5976 app.debugging = false; 5977 app.cached = false; 5978 5979 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5980 5981 boolean normalMode = mProcessesReady || isAllowedWhileBooting(app.info); 5982 List<ProviderInfo> providers = normalMode ? generateApplicationProvidersLocked(app) : null; 5983 5984 if (!normalMode) { 5985 Slog.i(TAG, "Launching preboot mode app: " + app); 5986 } 5987 5988 if (localLOGV) Slog.v( 5989 TAG, "New app record " + app 5990 + " thread=" + thread.asBinder() + " pid=" + pid); 5991 try { 5992 int testMode = IApplicationThread.DEBUG_OFF; 5993 if (mDebugApp != null && mDebugApp.equals(processName)) { 5994 testMode = mWaitForDebugger 5995 ? IApplicationThread.DEBUG_WAIT 5996 : IApplicationThread.DEBUG_ON; 5997 app.debugging = true; 5998 if (mDebugTransient) { 5999 mDebugApp = mOrigDebugApp; 6000 mWaitForDebugger = mOrigWaitForDebugger; 6001 } 6002 } 6003 String profileFile = app.instrumentationProfileFile; 6004 ParcelFileDescriptor profileFd = null; 6005 int samplingInterval = 0; 6006 boolean profileAutoStop = false; 6007 if (mProfileApp != null && mProfileApp.equals(processName)) { 6008 mProfileProc = app; 6009 profileFile = mProfileFile; 6010 profileFd = mProfileFd; 6011 samplingInterval = mSamplingInterval; 6012 profileAutoStop = mAutoStopProfiler; 6013 } 6014 boolean enableOpenGlTrace = false; 6015 if (mOpenGlTraceApp != null && mOpenGlTraceApp.equals(processName)) { 6016 enableOpenGlTrace = true; 6017 mOpenGlTraceApp = null; 6018 } 6019 6020 // If the app is being launched for restore or full backup, set it up specially 6021 boolean isRestrictedBackupMode = false; 6022 if (mBackupTarget != null && mBackupAppName.equals(processName)) { 6023 isRestrictedBackupMode = (mBackupTarget.backupMode == BackupRecord.RESTORE) 6024 || (mBackupTarget.backupMode == BackupRecord.RESTORE_FULL) 6025 || (mBackupTarget.backupMode == BackupRecord.BACKUP_FULL); 6026 } 6027 6028 ensurePackageDexOpt(app.instrumentationInfo != null 6029 ? app.instrumentationInfo.packageName 6030 : app.info.packageName); 6031 if (app.instrumentationClass != null) { 6032 ensurePackageDexOpt(app.instrumentationClass.getPackageName()); 6033 } 6034 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Binding proc " 6035 + processName + " with config " + mConfiguration); 6036 ApplicationInfo appInfo = app.instrumentationInfo != null 6037 ? app.instrumentationInfo : app.info; 6038 app.compat = compatibilityInfoForPackageLocked(appInfo); 6039 if (profileFd != null) { 6040 profileFd = profileFd.dup(); 6041 } 6042 ProfilerInfo profilerInfo = profileFile == null ? null 6043 : new ProfilerInfo(profileFile, profileFd, samplingInterval, profileAutoStop); 6044 thread.bindApplication(processName, appInfo, providers, app.instrumentationClass, 6045 profilerInfo, app.instrumentationArguments, app.instrumentationWatcher, 6046 app.instrumentationUiAutomationConnection, testMode, enableOpenGlTrace, 6047 isRestrictedBackupMode || !normalMode, app.persistent, 6048 new Configuration(mConfiguration), app.compat, getCommonServicesLocked(), 6049 mCoreSettingsObserver.getCoreSettingsLocked()); 6050 updateLruProcessLocked(app, false, null); 6051 app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis(); 6052 } catch (Exception e) { 6053 // todo: Yikes! What should we do? For now we will try to 6054 // start another process, but that could easily get us in 6055 // an infinite loop of restarting processes... 6056 Slog.w(TAG, "Exception thrown during bind!", e); 6057 6058 app.resetPackageList(mProcessStats); 6059 app.unlinkDeathRecipient(); 6060 startProcessLocked(app, "bind fail", processName); 6061 return false; 6062 } 6063 6064 // Remove this record from the list of starting applications. 6065 mPersistentStartingProcesses.remove(app); 6066 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 6067 "Attach application locked removing on hold: " + app); 6068 mProcessesOnHold.remove(app); 6069 6070 boolean badApp = false; 6071 boolean didSomething = false; 6072 6073 // See if the top visible activity is waiting to run in this process... 6074 if (normalMode) { 6075 try { 6076 if (mStackSupervisor.attachApplicationLocked(app)) { 6077 didSomething = true; 6078 } 6079 } catch (Exception e) { 6080 badApp = true; 6081 } 6082 } 6083 6084 // Find any services that should be running in this process... 6085 if (!badApp) { 6086 try { 6087 didSomething |= mServices.attachApplicationLocked(app, processName); 6088 } catch (Exception e) { 6089 badApp = true; 6090 } 6091 } 6092 6093 // Check if a next-broadcast receiver is in this process... 6094 if (!badApp && isPendingBroadcastProcessLocked(pid)) { 6095 try { 6096 didSomething |= sendPendingBroadcastsLocked(app); 6097 } catch (Exception e) { 6098 // If the app died trying to launch the receiver we declare it 'bad' 6099 badApp = true; 6100 } 6101 } 6102 6103 // Check whether the next backup agent is in this process... 6104 if (!badApp && mBackupTarget != null && mBackupTarget.appInfo.uid == app.uid) { 6105 if (DEBUG_BACKUP) Slog.v(TAG, "New app is backup target, launching agent for " + app); 6106 ensurePackageDexOpt(mBackupTarget.appInfo.packageName); 6107 try { 6108 thread.scheduleCreateBackupAgent(mBackupTarget.appInfo, 6109 compatibilityInfoForPackageLocked(mBackupTarget.appInfo), 6110 mBackupTarget.backupMode); 6111 } catch (Exception e) { 6112 Slog.w(TAG, "Exception scheduling backup agent creation: "); 6113 e.printStackTrace(); 6114 } 6115 } 6116 6117 if (badApp) { 6118 // todo: Also need to kill application to deal with all 6119 // kinds of exceptions. 6120 handleAppDiedLocked(app, false, true); 6121 return false; 6122 } 6123 6124 if (!didSomething) { 6125 updateOomAdjLocked(); 6126 } 6127 6128 return true; 6129 } 6130 6131 @Override 6132 public final void attachApplication(IApplicationThread thread) { 6133 synchronized (this) { 6134 int callingPid = Binder.getCallingPid(); 6135 final long origId = Binder.clearCallingIdentity(); 6136 attachApplicationLocked(thread, callingPid); 6137 Binder.restoreCallingIdentity(origId); 6138 } 6139 } 6140 6141 @Override 6142 public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) { 6143 final long origId = Binder.clearCallingIdentity(); 6144 synchronized (this) { 6145 ActivityStack stack = ActivityRecord.getStackLocked(token); 6146 if (stack != null) { 6147 ActivityRecord r = 6148 mStackSupervisor.activityIdleInternalLocked(token, false, config); 6149 if (stopProfiling) { 6150 if ((mProfileProc == r.app) && (mProfileFd != null)) { 6151 try { 6152 mProfileFd.close(); 6153 } catch (IOException e) { 6154 } 6155 clearProfilerLocked(); 6156 } 6157 } 6158 } 6159 } 6160 Binder.restoreCallingIdentity(origId); 6161 } 6162 6163 void postEnableScreenAfterBootLocked() { 6164 mHandler.sendEmptyMessage(ENABLE_SCREEN_AFTER_BOOT_MSG); 6165 } 6166 6167 void enableScreenAfterBoot() { 6168 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN, 6169 SystemClock.uptimeMillis()); 6170 mWindowManager.enableScreenAfterBoot(); 6171 6172 synchronized (this) { 6173 updateEventDispatchingLocked(); 6174 } 6175 } 6176 6177 @Override 6178 public void showBootMessage(final CharSequence msg, final boolean always) { 6179 enforceNotIsolatedCaller("showBootMessage"); 6180 mWindowManager.showBootMessage(msg, always); 6181 } 6182 6183 @Override 6184 public void keyguardWaitingForActivityDrawn() { 6185 enforceNotIsolatedCaller("keyguardWaitingForActivityDrawn"); 6186 final long token = Binder.clearCallingIdentity(); 6187 try { 6188 synchronized (this) { 6189 if (DEBUG_LOCKSCREEN) logLockScreen(""); 6190 mWindowManager.keyguardWaitingForActivityDrawn(); 6191 } 6192 } finally { 6193 Binder.restoreCallingIdentity(token); 6194 } 6195 } 6196 6197 final void finishBooting() { 6198 // Register receivers to handle package update events 6199 mPackageMonitor.register(mContext, Looper.getMainLooper(), false); 6200 6201 // Let system services know. 6202 mSystemServiceManager.startBootPhase(SystemService.PHASE_BOOT_COMPLETED); 6203 6204 synchronized (this) { 6205 // Ensure that any processes we had put on hold are now started 6206 // up. 6207 final int NP = mProcessesOnHold.size(); 6208 if (NP > 0) { 6209 ArrayList<ProcessRecord> procs = 6210 new ArrayList<ProcessRecord>(mProcessesOnHold); 6211 for (int ip=0; ip<NP; ip++) { 6212 if (DEBUG_PROCESSES) Slog.v(TAG, "Starting process on hold: " 6213 + procs.get(ip)); 6214 startProcessLocked(procs.get(ip), "on-hold", null); 6215 } 6216 } 6217 6218 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 6219 // Start looking for apps that are abusing wake locks. 6220 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 6221 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 6222 // Tell anyone interested that we are done booting! 6223 SystemProperties.set("sys.boot_completed", "1"); 6224 SystemProperties.set("dev.bootcomplete", "1"); 6225 for (int i=0; i<mStartedUsers.size(); i++) { 6226 UserStartedState uss = mStartedUsers.valueAt(i); 6227 if (uss.mState == UserStartedState.STATE_BOOTING) { 6228 uss.mState = UserStartedState.STATE_RUNNING; 6229 final int userId = mStartedUsers.keyAt(i); 6230 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 6231 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 6232 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 6233 broadcastIntentLocked(null, null, intent, null, 6234 new IIntentReceiver.Stub() { 6235 @Override 6236 public void performReceive(Intent intent, int resultCode, 6237 String data, Bundle extras, boolean ordered, 6238 boolean sticky, int sendingUser) { 6239 synchronized (ActivityManagerService.this) { 6240 requestPssAllProcsLocked(SystemClock.uptimeMillis(), 6241 true, false); 6242 } 6243 } 6244 }, 6245 0, null, null, 6246 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, 6247 AppOpsManager.OP_NONE, true, false, MY_PID, Process.SYSTEM_UID, 6248 userId); 6249 } 6250 } 6251 scheduleStartProfilesLocked(); 6252 } 6253 } 6254 } 6255 6256 final void ensureBootCompleted() { 6257 boolean booting; 6258 boolean enableScreen; 6259 synchronized (this) { 6260 booting = mBooting; 6261 mBooting = false; 6262 enableScreen = !mBooted; 6263 mBooted = true; 6264 } 6265 6266 if (booting) { 6267 finishBooting(); 6268 } 6269 6270 if (enableScreen) { 6271 enableScreenAfterBoot(); 6272 } 6273 } 6274 6275 @Override 6276 public final void activityResumed(IBinder token) { 6277 final long origId = Binder.clearCallingIdentity(); 6278 synchronized(this) { 6279 ActivityStack stack = ActivityRecord.getStackLocked(token); 6280 if (stack != null) { 6281 ActivityRecord.activityResumedLocked(token); 6282 } 6283 } 6284 Binder.restoreCallingIdentity(origId); 6285 } 6286 6287 @Override 6288 public final void activityPaused(IBinder token) { 6289 final long origId = Binder.clearCallingIdentity(); 6290 synchronized(this) { 6291 ActivityStack stack = ActivityRecord.getStackLocked(token); 6292 if (stack != null) { 6293 stack.activityPausedLocked(token, false); 6294 } 6295 } 6296 Binder.restoreCallingIdentity(origId); 6297 } 6298 6299 @Override 6300 public final void activityStopped(IBinder token, Bundle icicle, 6301 PersistableBundle persistentState, CharSequence description) { 6302 if (localLOGV) Slog.v(TAG, "Activity stopped: token=" + token); 6303 6304 // Refuse possible leaked file descriptors 6305 if (icicle != null && icicle.hasFileDescriptors()) { 6306 throw new IllegalArgumentException("File descriptors passed in Bundle"); 6307 } 6308 6309 final long origId = Binder.clearCallingIdentity(); 6310 6311 synchronized (this) { 6312 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6313 if (r != null) { 6314 r.task.stack.activityStoppedLocked(r, icicle, persistentState, description); 6315 } 6316 } 6317 6318 trimApplications(); 6319 6320 Binder.restoreCallingIdentity(origId); 6321 } 6322 6323 @Override 6324 public final void activityDestroyed(IBinder token) { 6325 if (DEBUG_SWITCH) Slog.v(TAG, "ACTIVITY DESTROYED: " + token); 6326 synchronized (this) { 6327 ActivityStack stack = ActivityRecord.getStackLocked(token); 6328 if (stack != null) { 6329 stack.activityDestroyedLocked(token); 6330 } 6331 } 6332 } 6333 6334 @Override 6335 public final void backgroundResourcesReleased(IBinder token) { 6336 final long origId = Binder.clearCallingIdentity(); 6337 try { 6338 synchronized (this) { 6339 ActivityStack stack = ActivityRecord.getStackLocked(token); 6340 if (stack != null) { 6341 stack.backgroundResourcesReleased(token); 6342 } 6343 } 6344 } finally { 6345 Binder.restoreCallingIdentity(origId); 6346 } 6347 } 6348 6349 @Override 6350 public final void notifyLaunchTaskBehindComplete(IBinder token) { 6351 mStackSupervisor.scheduleLaunchTaskBehindComplete(token); 6352 } 6353 6354 @Override 6355 public final void notifyEnterAnimationComplete(IBinder token) { 6356 mHandler.sendMessage(mHandler.obtainMessage(ENTER_ANIMATION_COMPLETE_MSG, token)); 6357 } 6358 6359 @Override 6360 public String getCallingPackage(IBinder token) { 6361 synchronized (this) { 6362 ActivityRecord r = getCallingRecordLocked(token); 6363 return r != null ? r.info.packageName : null; 6364 } 6365 } 6366 6367 @Override 6368 public ComponentName getCallingActivity(IBinder token) { 6369 synchronized (this) { 6370 ActivityRecord r = getCallingRecordLocked(token); 6371 return r != null ? r.intent.getComponent() : null; 6372 } 6373 } 6374 6375 private ActivityRecord getCallingRecordLocked(IBinder token) { 6376 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6377 if (r == null) { 6378 return null; 6379 } 6380 return r.resultTo; 6381 } 6382 6383 @Override 6384 public ComponentName getActivityClassForToken(IBinder token) { 6385 synchronized(this) { 6386 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6387 if (r == null) { 6388 return null; 6389 } 6390 return r.intent.getComponent(); 6391 } 6392 } 6393 6394 @Override 6395 public String getPackageForToken(IBinder token) { 6396 synchronized(this) { 6397 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6398 if (r == null) { 6399 return null; 6400 } 6401 return r.packageName; 6402 } 6403 } 6404 6405 @Override 6406 public IIntentSender getIntentSender(int type, 6407 String packageName, IBinder token, String resultWho, 6408 int requestCode, Intent[] intents, String[] resolvedTypes, 6409 int flags, Bundle options, int userId) { 6410 enforceNotIsolatedCaller("getIntentSender"); 6411 // Refuse possible leaked file descriptors 6412 if (intents != null) { 6413 if (intents.length < 1) { 6414 throw new IllegalArgumentException("Intents array length must be >= 1"); 6415 } 6416 for (int i=0; i<intents.length; i++) { 6417 Intent intent = intents[i]; 6418 if (intent != null) { 6419 if (intent.hasFileDescriptors()) { 6420 throw new IllegalArgumentException("File descriptors passed in Intent"); 6421 } 6422 if (type == ActivityManager.INTENT_SENDER_BROADCAST && 6423 (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 6424 throw new IllegalArgumentException( 6425 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 6426 } 6427 intents[i] = new Intent(intent); 6428 } 6429 } 6430 if (resolvedTypes != null && resolvedTypes.length != intents.length) { 6431 throw new IllegalArgumentException( 6432 "Intent array length does not match resolvedTypes length"); 6433 } 6434 } 6435 if (options != null) { 6436 if (options.hasFileDescriptors()) { 6437 throw new IllegalArgumentException("File descriptors passed in options"); 6438 } 6439 } 6440 6441 synchronized(this) { 6442 int callingUid = Binder.getCallingUid(); 6443 int origUserId = userId; 6444 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 6445 type == ActivityManager.INTENT_SENDER_BROADCAST, 6446 ALLOW_NON_FULL, "getIntentSender", null); 6447 if (origUserId == UserHandle.USER_CURRENT) { 6448 // We don't want to evaluate this until the pending intent is 6449 // actually executed. However, we do want to always do the 6450 // security checking for it above. 6451 userId = UserHandle.USER_CURRENT; 6452 } 6453 try { 6454 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 6455 int uid = AppGlobals.getPackageManager() 6456 .getPackageUid(packageName, UserHandle.getUserId(callingUid)); 6457 if (!UserHandle.isSameApp(callingUid, uid)) { 6458 String msg = "Permission Denial: getIntentSender() from pid=" 6459 + Binder.getCallingPid() 6460 + ", uid=" + Binder.getCallingUid() 6461 + ", (need uid=" + uid + ")" 6462 + " is not allowed to send as package " + packageName; 6463 Slog.w(TAG, msg); 6464 throw new SecurityException(msg); 6465 } 6466 } 6467 6468 return getIntentSenderLocked(type, packageName, callingUid, userId, 6469 token, resultWho, requestCode, intents, resolvedTypes, flags, options); 6470 6471 } catch (RemoteException e) { 6472 throw new SecurityException(e); 6473 } 6474 } 6475 } 6476 6477 IIntentSender getIntentSenderLocked(int type, String packageName, 6478 int callingUid, int userId, IBinder token, String resultWho, 6479 int requestCode, Intent[] intents, String[] resolvedTypes, int flags, 6480 Bundle options) { 6481 if (DEBUG_MU) 6482 Slog.v(TAG_MU, "getIntentSenderLocked(): uid=" + callingUid); 6483 ActivityRecord activity = null; 6484 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 6485 activity = ActivityRecord.isInStackLocked(token); 6486 if (activity == null) { 6487 return null; 6488 } 6489 if (activity.finishing) { 6490 return null; 6491 } 6492 } 6493 6494 final boolean noCreate = (flags&PendingIntent.FLAG_NO_CREATE) != 0; 6495 final boolean cancelCurrent = (flags&PendingIntent.FLAG_CANCEL_CURRENT) != 0; 6496 final boolean updateCurrent = (flags&PendingIntent.FLAG_UPDATE_CURRENT) != 0; 6497 flags &= ~(PendingIntent.FLAG_NO_CREATE|PendingIntent.FLAG_CANCEL_CURRENT 6498 |PendingIntent.FLAG_UPDATE_CURRENT); 6499 6500 PendingIntentRecord.Key key = new PendingIntentRecord.Key( 6501 type, packageName, activity, resultWho, 6502 requestCode, intents, resolvedTypes, flags, options, userId); 6503 WeakReference<PendingIntentRecord> ref; 6504 ref = mIntentSenderRecords.get(key); 6505 PendingIntentRecord rec = ref != null ? ref.get() : null; 6506 if (rec != null) { 6507 if (!cancelCurrent) { 6508 if (updateCurrent) { 6509 if (rec.key.requestIntent != null) { 6510 rec.key.requestIntent.replaceExtras(intents != null ? 6511 intents[intents.length - 1] : null); 6512 } 6513 if (intents != null) { 6514 intents[intents.length-1] = rec.key.requestIntent; 6515 rec.key.allIntents = intents; 6516 rec.key.allResolvedTypes = resolvedTypes; 6517 } else { 6518 rec.key.allIntents = null; 6519 rec.key.allResolvedTypes = null; 6520 } 6521 } 6522 return rec; 6523 } 6524 rec.canceled = true; 6525 mIntentSenderRecords.remove(key); 6526 } 6527 if (noCreate) { 6528 return rec; 6529 } 6530 rec = new PendingIntentRecord(this, key, callingUid); 6531 mIntentSenderRecords.put(key, rec.ref); 6532 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 6533 if (activity.pendingResults == null) { 6534 activity.pendingResults 6535 = new HashSet<WeakReference<PendingIntentRecord>>(); 6536 } 6537 activity.pendingResults.add(rec.ref); 6538 } 6539 return rec; 6540 } 6541 6542 @Override 6543 public void cancelIntentSender(IIntentSender sender) { 6544 if (!(sender instanceof PendingIntentRecord)) { 6545 return; 6546 } 6547 synchronized(this) { 6548 PendingIntentRecord rec = (PendingIntentRecord)sender; 6549 try { 6550 int uid = AppGlobals.getPackageManager() 6551 .getPackageUid(rec.key.packageName, UserHandle.getCallingUserId()); 6552 if (!UserHandle.isSameApp(uid, Binder.getCallingUid())) { 6553 String msg = "Permission Denial: cancelIntentSender() from pid=" 6554 + Binder.getCallingPid() 6555 + ", uid=" + Binder.getCallingUid() 6556 + " is not allowed to cancel packges " 6557 + rec.key.packageName; 6558 Slog.w(TAG, msg); 6559 throw new SecurityException(msg); 6560 } 6561 } catch (RemoteException e) { 6562 throw new SecurityException(e); 6563 } 6564 cancelIntentSenderLocked(rec, true); 6565 } 6566 } 6567 6568 void cancelIntentSenderLocked(PendingIntentRecord rec, boolean cleanActivity) { 6569 rec.canceled = true; 6570 mIntentSenderRecords.remove(rec.key); 6571 if (cleanActivity && rec.key.activity != null) { 6572 rec.key.activity.pendingResults.remove(rec.ref); 6573 } 6574 } 6575 6576 @Override 6577 public String getPackageForIntentSender(IIntentSender pendingResult) { 6578 if (!(pendingResult instanceof PendingIntentRecord)) { 6579 return null; 6580 } 6581 try { 6582 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6583 return res.key.packageName; 6584 } catch (ClassCastException e) { 6585 } 6586 return null; 6587 } 6588 6589 @Override 6590 public int getUidForIntentSender(IIntentSender sender) { 6591 if (sender instanceof PendingIntentRecord) { 6592 try { 6593 PendingIntentRecord res = (PendingIntentRecord)sender; 6594 return res.uid; 6595 } catch (ClassCastException e) { 6596 } 6597 } 6598 return -1; 6599 } 6600 6601 @Override 6602 public boolean isIntentSenderTargetedToPackage(IIntentSender pendingResult) { 6603 if (!(pendingResult instanceof PendingIntentRecord)) { 6604 return false; 6605 } 6606 try { 6607 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6608 if (res.key.allIntents == null) { 6609 return false; 6610 } 6611 for (int i=0; i<res.key.allIntents.length; i++) { 6612 Intent intent = res.key.allIntents[i]; 6613 if (intent.getPackage() != null && intent.getComponent() != null) { 6614 return false; 6615 } 6616 } 6617 return true; 6618 } catch (ClassCastException e) { 6619 } 6620 return false; 6621 } 6622 6623 @Override 6624 public boolean isIntentSenderAnActivity(IIntentSender pendingResult) { 6625 if (!(pendingResult instanceof PendingIntentRecord)) { 6626 return false; 6627 } 6628 try { 6629 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6630 if (res.key.type == ActivityManager.INTENT_SENDER_ACTIVITY) { 6631 return true; 6632 } 6633 return false; 6634 } catch (ClassCastException e) { 6635 } 6636 return false; 6637 } 6638 6639 @Override 6640 public Intent getIntentForIntentSender(IIntentSender pendingResult) { 6641 if (!(pendingResult instanceof PendingIntentRecord)) { 6642 return null; 6643 } 6644 try { 6645 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6646 return res.key.requestIntent != null ? new Intent(res.key.requestIntent) : null; 6647 } catch (ClassCastException e) { 6648 } 6649 return null; 6650 } 6651 6652 @Override 6653 public String getTagForIntentSender(IIntentSender pendingResult, String prefix) { 6654 if (!(pendingResult instanceof PendingIntentRecord)) { 6655 return null; 6656 } 6657 try { 6658 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6659 Intent intent = res.key.requestIntent; 6660 if (intent != null) { 6661 if (res.lastTag != null && res.lastTagPrefix == prefix && (res.lastTagPrefix == null 6662 || res.lastTagPrefix.equals(prefix))) { 6663 return res.lastTag; 6664 } 6665 res.lastTagPrefix = prefix; 6666 StringBuilder sb = new StringBuilder(128); 6667 if (prefix != null) { 6668 sb.append(prefix); 6669 } 6670 if (intent.getAction() != null) { 6671 sb.append(intent.getAction()); 6672 } else if (intent.getComponent() != null) { 6673 intent.getComponent().appendShortString(sb); 6674 } else { 6675 sb.append("?"); 6676 } 6677 return res.lastTag = sb.toString(); 6678 } 6679 } catch (ClassCastException e) { 6680 } 6681 return null; 6682 } 6683 6684 @Override 6685 public void setProcessLimit(int max) { 6686 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 6687 "setProcessLimit()"); 6688 synchronized (this) { 6689 mProcessLimit = max < 0 ? ProcessList.MAX_CACHED_APPS : max; 6690 mProcessLimitOverride = max; 6691 } 6692 trimApplications(); 6693 } 6694 6695 @Override 6696 public int getProcessLimit() { 6697 synchronized (this) { 6698 return mProcessLimitOverride; 6699 } 6700 } 6701 6702 void foregroundTokenDied(ForegroundToken token) { 6703 synchronized (ActivityManagerService.this) { 6704 synchronized (mPidsSelfLocked) { 6705 ForegroundToken cur 6706 = mForegroundProcesses.get(token.pid); 6707 if (cur != token) { 6708 return; 6709 } 6710 mForegroundProcesses.remove(token.pid); 6711 ProcessRecord pr = mPidsSelfLocked.get(token.pid); 6712 if (pr == null) { 6713 return; 6714 } 6715 pr.forcingToForeground = null; 6716 updateProcessForegroundLocked(pr, false, false); 6717 } 6718 updateOomAdjLocked(); 6719 } 6720 } 6721 6722 @Override 6723 public void setProcessForeground(IBinder token, int pid, boolean isForeground) { 6724 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 6725 "setProcessForeground()"); 6726 synchronized(this) { 6727 boolean changed = false; 6728 6729 synchronized (mPidsSelfLocked) { 6730 ProcessRecord pr = mPidsSelfLocked.get(pid); 6731 if (pr == null && isForeground) { 6732 Slog.w(TAG, "setProcessForeground called on unknown pid: " + pid); 6733 return; 6734 } 6735 ForegroundToken oldToken = mForegroundProcesses.get(pid); 6736 if (oldToken != null) { 6737 oldToken.token.unlinkToDeath(oldToken, 0); 6738 mForegroundProcesses.remove(pid); 6739 if (pr != null) { 6740 pr.forcingToForeground = null; 6741 } 6742 changed = true; 6743 } 6744 if (isForeground && token != null) { 6745 ForegroundToken newToken = new ForegroundToken() { 6746 @Override 6747 public void binderDied() { 6748 foregroundTokenDied(this); 6749 } 6750 }; 6751 newToken.pid = pid; 6752 newToken.token = token; 6753 try { 6754 token.linkToDeath(newToken, 0); 6755 mForegroundProcesses.put(pid, newToken); 6756 pr.forcingToForeground = token; 6757 changed = true; 6758 } catch (RemoteException e) { 6759 // If the process died while doing this, we will later 6760 // do the cleanup with the process death link. 6761 } 6762 } 6763 } 6764 6765 if (changed) { 6766 updateOomAdjLocked(); 6767 } 6768 } 6769 } 6770 6771 // ========================================================= 6772 // PERMISSIONS 6773 // ========================================================= 6774 6775 static class PermissionController extends IPermissionController.Stub { 6776 ActivityManagerService mActivityManagerService; 6777 PermissionController(ActivityManagerService activityManagerService) { 6778 mActivityManagerService = activityManagerService; 6779 } 6780 6781 @Override 6782 public boolean checkPermission(String permission, int pid, int uid) { 6783 return mActivityManagerService.checkPermission(permission, pid, 6784 uid) == PackageManager.PERMISSION_GRANTED; 6785 } 6786 } 6787 6788 class IntentFirewallInterface implements IntentFirewall.AMSInterface { 6789 @Override 6790 public int checkComponentPermission(String permission, int pid, int uid, 6791 int owningUid, boolean exported) { 6792 return ActivityManagerService.this.checkComponentPermission(permission, pid, uid, 6793 owningUid, exported); 6794 } 6795 6796 @Override 6797 public Object getAMSLock() { 6798 return ActivityManagerService.this; 6799 } 6800 } 6801 6802 /** 6803 * This can be called with or without the global lock held. 6804 */ 6805 int checkComponentPermission(String permission, int pid, int uid, 6806 int owningUid, boolean exported) { 6807 // We might be performing an operation on behalf of an indirect binder 6808 // invocation, e.g. via {@link #openContentUri}. Check and adjust the 6809 // client identity accordingly before proceeding. 6810 Identity tlsIdentity = sCallerIdentity.get(); 6811 if (tlsIdentity != null) { 6812 Slog.d(TAG, "checkComponentPermission() adjusting {pid,uid} to {" 6813 + tlsIdentity.pid + "," + tlsIdentity.uid + "}"); 6814 uid = tlsIdentity.uid; 6815 pid = tlsIdentity.pid; 6816 } 6817 6818 if (pid == MY_PID) { 6819 return PackageManager.PERMISSION_GRANTED; 6820 } 6821 6822 return ActivityManager.checkComponentPermission(permission, uid, 6823 owningUid, exported); 6824 } 6825 6826 /** 6827 * As the only public entry point for permissions checking, this method 6828 * can enforce the semantic that requesting a check on a null global 6829 * permission is automatically denied. (Internally a null permission 6830 * string is used when calling {@link #checkComponentPermission} in cases 6831 * when only uid-based security is needed.) 6832 * 6833 * This can be called with or without the global lock held. 6834 */ 6835 @Override 6836 public int checkPermission(String permission, int pid, int uid) { 6837 if (permission == null) { 6838 return PackageManager.PERMISSION_DENIED; 6839 } 6840 return checkComponentPermission(permission, pid, UserHandle.getAppId(uid), -1, true); 6841 } 6842 6843 /** 6844 * Binder IPC calls go through the public entry point. 6845 * This can be called with or without the global lock held. 6846 */ 6847 int checkCallingPermission(String permission) { 6848 return checkPermission(permission, 6849 Binder.getCallingPid(), 6850 UserHandle.getAppId(Binder.getCallingUid())); 6851 } 6852 6853 /** 6854 * This can be called with or without the global lock held. 6855 */ 6856 void enforceCallingPermission(String permission, String func) { 6857 if (checkCallingPermission(permission) 6858 == PackageManager.PERMISSION_GRANTED) { 6859 return; 6860 } 6861 6862 String msg = "Permission Denial: " + func + " from pid=" 6863 + Binder.getCallingPid() 6864 + ", uid=" + Binder.getCallingUid() 6865 + " requires " + permission; 6866 Slog.w(TAG, msg); 6867 throw new SecurityException(msg); 6868 } 6869 6870 /** 6871 * Determine if UID is holding permissions required to access {@link Uri} in 6872 * the given {@link ProviderInfo}. Final permission checking is always done 6873 * in {@link ContentProvider}. 6874 */ 6875 private final boolean checkHoldingPermissionsLocked( 6876 IPackageManager pm, ProviderInfo pi, GrantUri grantUri, int uid, final int modeFlags) { 6877 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6878 "checkHoldingPermissionsLocked: uri=" + grantUri + " uid=" + uid); 6879 if (UserHandle.getUserId(uid) != grantUri.sourceUserId) { 6880 if (ActivityManager.checkComponentPermission(INTERACT_ACROSS_USERS, uid, -1, true) 6881 != PERMISSION_GRANTED) { 6882 return false; 6883 } 6884 } 6885 return checkHoldingPermissionsInternalLocked(pm, pi, grantUri, uid, modeFlags, true); 6886 } 6887 6888 private final boolean checkHoldingPermissionsInternalLocked(IPackageManager pm, ProviderInfo pi, 6889 GrantUri grantUri, int uid, final int modeFlags, boolean considerUidPermissions) { 6890 if (pi.applicationInfo.uid == uid) { 6891 return true; 6892 } else if (!pi.exported) { 6893 return false; 6894 } 6895 6896 boolean readMet = (modeFlags & Intent.FLAG_GRANT_READ_URI_PERMISSION) == 0; 6897 boolean writeMet = (modeFlags & Intent.FLAG_GRANT_WRITE_URI_PERMISSION) == 0; 6898 try { 6899 // check if target holds top-level <provider> permissions 6900 if (!readMet && pi.readPermission != null && considerUidPermissions 6901 && (pm.checkUidPermission(pi.readPermission, uid) == PERMISSION_GRANTED)) { 6902 readMet = true; 6903 } 6904 if (!writeMet && pi.writePermission != null && considerUidPermissions 6905 && (pm.checkUidPermission(pi.writePermission, uid) == PERMISSION_GRANTED)) { 6906 writeMet = true; 6907 } 6908 6909 // track if unprotected read/write is allowed; any denied 6910 // <path-permission> below removes this ability 6911 boolean allowDefaultRead = pi.readPermission == null; 6912 boolean allowDefaultWrite = pi.writePermission == null; 6913 6914 // check if target holds any <path-permission> that match uri 6915 final PathPermission[] pps = pi.pathPermissions; 6916 if (pps != null) { 6917 final String path = grantUri.uri.getPath(); 6918 int i = pps.length; 6919 while (i > 0 && (!readMet || !writeMet)) { 6920 i--; 6921 PathPermission pp = pps[i]; 6922 if (pp.match(path)) { 6923 if (!readMet) { 6924 final String pprperm = pp.getReadPermission(); 6925 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking read perm for " 6926 + pprperm + " for " + pp.getPath() 6927 + ": match=" + pp.match(path) 6928 + " check=" + pm.checkUidPermission(pprperm, uid)); 6929 if (pprperm != null) { 6930 if (considerUidPermissions && pm.checkUidPermission(pprperm, uid) 6931 == PERMISSION_GRANTED) { 6932 readMet = true; 6933 } else { 6934 allowDefaultRead = false; 6935 } 6936 } 6937 } 6938 if (!writeMet) { 6939 final String ppwperm = pp.getWritePermission(); 6940 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking write perm " 6941 + ppwperm + " for " + pp.getPath() 6942 + ": match=" + pp.match(path) 6943 + " check=" + pm.checkUidPermission(ppwperm, uid)); 6944 if (ppwperm != null) { 6945 if (considerUidPermissions && pm.checkUidPermission(ppwperm, uid) 6946 == PERMISSION_GRANTED) { 6947 writeMet = true; 6948 } else { 6949 allowDefaultWrite = false; 6950 } 6951 } 6952 } 6953 } 6954 } 6955 } 6956 6957 // grant unprotected <provider> read/write, if not blocked by 6958 // <path-permission> above 6959 if (allowDefaultRead) readMet = true; 6960 if (allowDefaultWrite) writeMet = true; 6961 6962 } catch (RemoteException e) { 6963 return false; 6964 } 6965 6966 return readMet && writeMet; 6967 } 6968 6969 private ProviderInfo getProviderInfoLocked(String authority, int userHandle) { 6970 ProviderInfo pi = null; 6971 ContentProviderRecord cpr = mProviderMap.getProviderByName(authority, userHandle); 6972 if (cpr != null) { 6973 pi = cpr.info; 6974 } else { 6975 try { 6976 pi = AppGlobals.getPackageManager().resolveContentProvider( 6977 authority, PackageManager.GET_URI_PERMISSION_PATTERNS, userHandle); 6978 } catch (RemoteException ex) { 6979 } 6980 } 6981 return pi; 6982 } 6983 6984 private UriPermission findUriPermissionLocked(int targetUid, GrantUri grantUri) { 6985 final ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6986 if (targetUris != null) { 6987 return targetUris.get(grantUri); 6988 } 6989 return null; 6990 } 6991 6992 private UriPermission findOrCreateUriPermissionLocked(String sourcePkg, 6993 String targetPkg, int targetUid, GrantUri grantUri) { 6994 ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6995 if (targetUris == null) { 6996 targetUris = Maps.newArrayMap(); 6997 mGrantedUriPermissions.put(targetUid, targetUris); 6998 } 6999 7000 UriPermission perm = targetUris.get(grantUri); 7001 if (perm == null) { 7002 perm = new UriPermission(sourcePkg, targetPkg, targetUid, grantUri); 7003 targetUris.put(grantUri, perm); 7004 } 7005 7006 return perm; 7007 } 7008 7009 private final boolean checkUriPermissionLocked(GrantUri grantUri, int uid, 7010 final int modeFlags) { 7011 final boolean persistable = (modeFlags & Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION) != 0; 7012 final int minStrength = persistable ? UriPermission.STRENGTH_PERSISTABLE 7013 : UriPermission.STRENGTH_OWNED; 7014 7015 // Root gets to do everything. 7016 if (uid == 0) { 7017 return true; 7018 } 7019 7020 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 7021 if (perms == null) return false; 7022 7023 // First look for exact match 7024 final UriPermission exactPerm = perms.get(grantUri); 7025 if (exactPerm != null && exactPerm.getStrength(modeFlags) >= minStrength) { 7026 return true; 7027 } 7028 7029 // No exact match, look for prefixes 7030 final int N = perms.size(); 7031 for (int i = 0; i < N; i++) { 7032 final UriPermission perm = perms.valueAt(i); 7033 if (perm.uri.prefix && grantUri.uri.isPathPrefixMatch(perm.uri.uri) 7034 && perm.getStrength(modeFlags) >= minStrength) { 7035 return true; 7036 } 7037 } 7038 7039 return false; 7040 } 7041 7042 /** 7043 * @param uri This uri must NOT contain an embedded userId. 7044 * @param userId The userId in which the uri is to be resolved. 7045 */ 7046 @Override 7047 public int checkUriPermission(Uri uri, int pid, int uid, 7048 final int modeFlags, int userId) { 7049 enforceNotIsolatedCaller("checkUriPermission"); 7050 7051 // Another redirected-binder-call permissions check as in 7052 // {@link checkComponentPermission}. 7053 Identity tlsIdentity = sCallerIdentity.get(); 7054 if (tlsIdentity != null) { 7055 uid = tlsIdentity.uid; 7056 pid = tlsIdentity.pid; 7057 } 7058 7059 // Our own process gets to do everything. 7060 if (pid == MY_PID) { 7061 return PackageManager.PERMISSION_GRANTED; 7062 } 7063 synchronized (this) { 7064 return checkUriPermissionLocked(new GrantUri(userId, uri, false), uid, modeFlags) 7065 ? PackageManager.PERMISSION_GRANTED 7066 : PackageManager.PERMISSION_DENIED; 7067 } 7068 } 7069 7070 /** 7071 * Check if the targetPkg can be granted permission to access uri by 7072 * the callingUid using the given modeFlags. Throws a security exception 7073 * if callingUid is not allowed to do this. Returns the uid of the target 7074 * if the URI permission grant should be performed; returns -1 if it is not 7075 * needed (for example targetPkg already has permission to access the URI). 7076 * If you already know the uid of the target, you can supply it in 7077 * lastTargetUid else set that to -1. 7078 */ 7079 int checkGrantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 7080 final int modeFlags, int lastTargetUid) { 7081 if (!Intent.isAccessUriMode(modeFlags)) { 7082 return -1; 7083 } 7084 7085 if (targetPkg != null) { 7086 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7087 "Checking grant " + targetPkg + " permission to " + grantUri); 7088 } 7089 7090 final IPackageManager pm = AppGlobals.getPackageManager(); 7091 7092 // If this is not a content: uri, we can't do anything with it. 7093 if (!ContentResolver.SCHEME_CONTENT.equals(grantUri.uri.getScheme())) { 7094 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7095 "Can't grant URI permission for non-content URI: " + grantUri); 7096 return -1; 7097 } 7098 7099 final String authority = grantUri.uri.getAuthority(); 7100 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 7101 if (pi == null) { 7102 Slog.w(TAG, "No content provider found for permission check: " + 7103 grantUri.uri.toSafeString()); 7104 return -1; 7105 } 7106 7107 int targetUid = lastTargetUid; 7108 if (targetUid < 0 && targetPkg != null) { 7109 try { 7110 targetUid = pm.getPackageUid(targetPkg, UserHandle.getUserId(callingUid)); 7111 if (targetUid < 0) { 7112 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7113 "Can't grant URI permission no uid for: " + targetPkg); 7114 return -1; 7115 } 7116 } catch (RemoteException ex) { 7117 return -1; 7118 } 7119 } 7120 7121 if (targetUid >= 0) { 7122 // First... does the target actually need this permission? 7123 if (checkHoldingPermissionsLocked(pm, pi, grantUri, targetUid, modeFlags)) { 7124 // No need to grant the target this permission. 7125 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7126 "Target " + targetPkg + " already has full permission to " + grantUri); 7127 return -1; 7128 } 7129 } else { 7130 // First... there is no target package, so can anyone access it? 7131 boolean allowed = pi.exported; 7132 if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) { 7133 if (pi.readPermission != null) { 7134 allowed = false; 7135 } 7136 } 7137 if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) { 7138 if (pi.writePermission != null) { 7139 allowed = false; 7140 } 7141 } 7142 if (allowed) { 7143 return -1; 7144 } 7145 } 7146 7147 /* There is a special cross user grant if: 7148 * - The target is on another user. 7149 * - Apps on the current user can access the uri without any uid permissions. 7150 * In this case, we grant a uri permission, even if the ContentProvider does not normally 7151 * grant uri permissions. 7152 */ 7153 boolean specialCrossUserGrant = UserHandle.getUserId(targetUid) != grantUri.sourceUserId 7154 && checkHoldingPermissionsInternalLocked(pm, pi, grantUri, callingUid, 7155 modeFlags, false /*without considering the uid permissions*/); 7156 7157 // Second... is the provider allowing granting of URI permissions? 7158 if (!specialCrossUserGrant) { 7159 if (!pi.grantUriPermissions) { 7160 throw new SecurityException("Provider " + pi.packageName 7161 + "/" + pi.name 7162 + " does not allow granting of Uri permissions (uri " 7163 + grantUri + ")"); 7164 } 7165 if (pi.uriPermissionPatterns != null) { 7166 final int N = pi.uriPermissionPatterns.length; 7167 boolean allowed = false; 7168 for (int i=0; i<N; i++) { 7169 if (pi.uriPermissionPatterns[i] != null 7170 && pi.uriPermissionPatterns[i].match(grantUri.uri.getPath())) { 7171 allowed = true; 7172 break; 7173 } 7174 } 7175 if (!allowed) { 7176 throw new SecurityException("Provider " + pi.packageName 7177 + "/" + pi.name 7178 + " does not allow granting of permission to path of Uri " 7179 + grantUri); 7180 } 7181 } 7182 } 7183 7184 // Third... does the caller itself have permission to access 7185 // this uri? 7186 if (UserHandle.getAppId(callingUid) != Process.SYSTEM_UID) { 7187 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 7188 // Require they hold a strong enough Uri permission 7189 if (!checkUriPermissionLocked(grantUri, callingUid, modeFlags)) { 7190 throw new SecurityException("Uid " + callingUid 7191 + " does not have permission to uri " + grantUri); 7192 } 7193 } 7194 } 7195 return targetUid; 7196 } 7197 7198 /** 7199 * @param uri This uri must NOT contain an embedded userId. 7200 * @param userId The userId in which the uri is to be resolved. 7201 */ 7202 @Override 7203 public int checkGrantUriPermission(int callingUid, String targetPkg, Uri uri, 7204 final int modeFlags, int userId) { 7205 enforceNotIsolatedCaller("checkGrantUriPermission"); 7206 synchronized(this) { 7207 return checkGrantUriPermissionLocked(callingUid, targetPkg, 7208 new GrantUri(userId, uri, false), modeFlags, -1); 7209 } 7210 } 7211 7212 void grantUriPermissionUncheckedLocked(int targetUid, String targetPkg, GrantUri grantUri, 7213 final int modeFlags, UriPermissionOwner owner) { 7214 if (!Intent.isAccessUriMode(modeFlags)) { 7215 return; 7216 } 7217 7218 // So here we are: the caller has the assumed permission 7219 // to the uri, and the target doesn't. Let's now give this to 7220 // the target. 7221 7222 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7223 "Granting " + targetPkg + "/" + targetUid + " permission to " + grantUri); 7224 7225 final String authority = grantUri.uri.getAuthority(); 7226 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 7227 if (pi == null) { 7228 Slog.w(TAG, "No content provider found for grant: " + grantUri.toSafeString()); 7229 return; 7230 } 7231 7232 if ((modeFlags & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0) { 7233 grantUri.prefix = true; 7234 } 7235 final UriPermission perm = findOrCreateUriPermissionLocked( 7236 pi.packageName, targetPkg, targetUid, grantUri); 7237 perm.grantModes(modeFlags, owner); 7238 } 7239 7240 void grantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 7241 final int modeFlags, UriPermissionOwner owner, int targetUserId) { 7242 if (targetPkg == null) { 7243 throw new NullPointerException("targetPkg"); 7244 } 7245 int targetUid; 7246 final IPackageManager pm = AppGlobals.getPackageManager(); 7247 try { 7248 targetUid = pm.getPackageUid(targetPkg, targetUserId); 7249 } catch (RemoteException ex) { 7250 return; 7251 } 7252 7253 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, modeFlags, 7254 targetUid); 7255 if (targetUid < 0) { 7256 return; 7257 } 7258 7259 grantUriPermissionUncheckedLocked(targetUid, targetPkg, grantUri, modeFlags, 7260 owner); 7261 } 7262 7263 static class NeededUriGrants extends ArrayList<GrantUri> { 7264 final String targetPkg; 7265 final int targetUid; 7266 final int flags; 7267 7268 NeededUriGrants(String targetPkg, int targetUid, int flags) { 7269 this.targetPkg = targetPkg; 7270 this.targetUid = targetUid; 7271 this.flags = flags; 7272 } 7273 } 7274 7275 /** 7276 * Like checkGrantUriPermissionLocked, but takes an Intent. 7277 */ 7278 NeededUriGrants checkGrantUriPermissionFromIntentLocked(int callingUid, 7279 String targetPkg, Intent intent, int mode, NeededUriGrants needed, int targetUserId) { 7280 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7281 "Checking URI perm to data=" + (intent != null ? intent.getData() : null) 7282 + " clip=" + (intent != null ? intent.getClipData() : null) 7283 + " from " + intent + "; flags=0x" 7284 + Integer.toHexString(intent != null ? intent.getFlags() : 0)); 7285 7286 if (targetPkg == null) { 7287 throw new NullPointerException("targetPkg"); 7288 } 7289 7290 if (intent == null) { 7291 return null; 7292 } 7293 Uri data = intent.getData(); 7294 ClipData clip = intent.getClipData(); 7295 if (data == null && clip == null) { 7296 return null; 7297 } 7298 // Default userId for uris in the intent (if they don't specify it themselves) 7299 int contentUserHint = intent.getContentUserHint(); 7300 if (contentUserHint == UserHandle.USER_CURRENT) { 7301 contentUserHint = UserHandle.getUserId(callingUid); 7302 } 7303 final IPackageManager pm = AppGlobals.getPackageManager(); 7304 int targetUid; 7305 if (needed != null) { 7306 targetUid = needed.targetUid; 7307 } else { 7308 try { 7309 targetUid = pm.getPackageUid(targetPkg, targetUserId); 7310 } catch (RemoteException ex) { 7311 return null; 7312 } 7313 if (targetUid < 0) { 7314 if (DEBUG_URI_PERMISSION) { 7315 Slog.v(TAG, "Can't grant URI permission no uid for: " + targetPkg 7316 + " on user " + targetUserId); 7317 } 7318 return null; 7319 } 7320 } 7321 if (data != null) { 7322 GrantUri grantUri = GrantUri.resolve(contentUserHint, data); 7323 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 7324 targetUid); 7325 if (targetUid > 0) { 7326 if (needed == null) { 7327 needed = new NeededUriGrants(targetPkg, targetUid, mode); 7328 } 7329 needed.add(grantUri); 7330 } 7331 } 7332 if (clip != null) { 7333 for (int i=0; i<clip.getItemCount(); i++) { 7334 Uri uri = clip.getItemAt(i).getUri(); 7335 if (uri != null) { 7336 GrantUri grantUri = GrantUri.resolve(contentUserHint, uri); 7337 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 7338 targetUid); 7339 if (targetUid > 0) { 7340 if (needed == null) { 7341 needed = new NeededUriGrants(targetPkg, targetUid, mode); 7342 } 7343 needed.add(grantUri); 7344 } 7345 } else { 7346 Intent clipIntent = clip.getItemAt(i).getIntent(); 7347 if (clipIntent != null) { 7348 NeededUriGrants newNeeded = checkGrantUriPermissionFromIntentLocked( 7349 callingUid, targetPkg, clipIntent, mode, needed, targetUserId); 7350 if (newNeeded != null) { 7351 needed = newNeeded; 7352 } 7353 } 7354 } 7355 } 7356 } 7357 7358 return needed; 7359 } 7360 7361 /** 7362 * Like grantUriPermissionUncheckedLocked, but takes an Intent. 7363 */ 7364 void grantUriPermissionUncheckedFromIntentLocked(NeededUriGrants needed, 7365 UriPermissionOwner owner) { 7366 if (needed != null) { 7367 for (int i=0; i<needed.size(); i++) { 7368 GrantUri grantUri = needed.get(i); 7369 grantUriPermissionUncheckedLocked(needed.targetUid, needed.targetPkg, 7370 grantUri, needed.flags, owner); 7371 } 7372 } 7373 } 7374 7375 void grantUriPermissionFromIntentLocked(int callingUid, 7376 String targetPkg, Intent intent, UriPermissionOwner owner, int targetUserId) { 7377 NeededUriGrants needed = checkGrantUriPermissionFromIntentLocked(callingUid, targetPkg, 7378 intent, intent != null ? intent.getFlags() : 0, null, targetUserId); 7379 if (needed == null) { 7380 return; 7381 } 7382 7383 grantUriPermissionUncheckedFromIntentLocked(needed, owner); 7384 } 7385 7386 /** 7387 * @param uri This uri must NOT contain an embedded userId. 7388 * @param userId The userId in which the uri is to be resolved. 7389 */ 7390 @Override 7391 public void grantUriPermission(IApplicationThread caller, String targetPkg, Uri uri, 7392 final int modeFlags, int userId) { 7393 enforceNotIsolatedCaller("grantUriPermission"); 7394 GrantUri grantUri = new GrantUri(userId, uri, false); 7395 synchronized(this) { 7396 final ProcessRecord r = getRecordForAppLocked(caller); 7397 if (r == null) { 7398 throw new SecurityException("Unable to find app for caller " 7399 + caller 7400 + " when granting permission to uri " + grantUri); 7401 } 7402 if (targetPkg == null) { 7403 throw new IllegalArgumentException("null target"); 7404 } 7405 if (grantUri == null) { 7406 throw new IllegalArgumentException("null uri"); 7407 } 7408 7409 Preconditions.checkFlagsArgument(modeFlags, Intent.FLAG_GRANT_READ_URI_PERMISSION 7410 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION 7411 | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION 7412 | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION); 7413 7414 grantUriPermissionLocked(r.uid, targetPkg, grantUri, modeFlags, null, 7415 UserHandle.getUserId(r.uid)); 7416 } 7417 } 7418 7419 void removeUriPermissionIfNeededLocked(UriPermission perm) { 7420 if (perm.modeFlags == 0) { 7421 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 7422 perm.targetUid); 7423 if (perms != null) { 7424 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7425 "Removing " + perm.targetUid + " permission to " + perm.uri); 7426 7427 perms.remove(perm.uri); 7428 if (perms.isEmpty()) { 7429 mGrantedUriPermissions.remove(perm.targetUid); 7430 } 7431 } 7432 } 7433 } 7434 7435 private void revokeUriPermissionLocked(int callingUid, GrantUri grantUri, final int modeFlags) { 7436 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Revoking all granted permissions to " + grantUri); 7437 7438 final IPackageManager pm = AppGlobals.getPackageManager(); 7439 final String authority = grantUri.uri.getAuthority(); 7440 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 7441 if (pi == null) { 7442 Slog.w(TAG, "No content provider found for permission revoke: " 7443 + grantUri.toSafeString()); 7444 return; 7445 } 7446 7447 // Does the caller have this permission on the URI? 7448 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 7449 // Right now, if you are not the original owner of the permission, 7450 // you are not allowed to revoke it. 7451 //if (!checkUriPermissionLocked(uri, callingUid, modeFlags)) { 7452 throw new SecurityException("Uid " + callingUid 7453 + " does not have permission to uri " + grantUri); 7454 //} 7455 } 7456 7457 boolean persistChanged = false; 7458 7459 // Go through all of the permissions and remove any that match. 7460 int N = mGrantedUriPermissions.size(); 7461 for (int i = 0; i < N; i++) { 7462 final int targetUid = mGrantedUriPermissions.keyAt(i); 7463 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 7464 7465 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 7466 final UriPermission perm = it.next(); 7467 if (perm.uri.sourceUserId == grantUri.sourceUserId 7468 && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) { 7469 if (DEBUG_URI_PERMISSION) 7470 Slog.v(TAG, 7471 "Revoking " + perm.targetUid + " permission to " + perm.uri); 7472 persistChanged |= perm.revokeModes( 7473 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 7474 if (perm.modeFlags == 0) { 7475 it.remove(); 7476 } 7477 } 7478 } 7479 7480 if (perms.isEmpty()) { 7481 mGrantedUriPermissions.remove(targetUid); 7482 N--; 7483 i--; 7484 } 7485 } 7486 7487 if (persistChanged) { 7488 schedulePersistUriGrants(); 7489 } 7490 } 7491 7492 /** 7493 * @param uri This uri must NOT contain an embedded userId. 7494 * @param userId The userId in which the uri is to be resolved. 7495 */ 7496 @Override 7497 public void revokeUriPermission(IApplicationThread caller, Uri uri, final int modeFlags, 7498 int userId) { 7499 enforceNotIsolatedCaller("revokeUriPermission"); 7500 synchronized(this) { 7501 final ProcessRecord r = getRecordForAppLocked(caller); 7502 if (r == null) { 7503 throw new SecurityException("Unable to find app for caller " 7504 + caller 7505 + " when revoking permission to uri " + uri); 7506 } 7507 if (uri == null) { 7508 Slog.w(TAG, "revokeUriPermission: null uri"); 7509 return; 7510 } 7511 7512 if (!Intent.isAccessUriMode(modeFlags)) { 7513 return; 7514 } 7515 7516 final IPackageManager pm = AppGlobals.getPackageManager(); 7517 final String authority = uri.getAuthority(); 7518 final ProviderInfo pi = getProviderInfoLocked(authority, userId); 7519 if (pi == null) { 7520 Slog.w(TAG, "No content provider found for permission revoke: " 7521 + uri.toSafeString()); 7522 return; 7523 } 7524 7525 revokeUriPermissionLocked(r.uid, new GrantUri(userId, uri, false), modeFlags); 7526 } 7527 } 7528 7529 /** 7530 * Remove any {@link UriPermission} granted <em>from</em> or <em>to</em> the 7531 * given package. 7532 * 7533 * @param packageName Package name to match, or {@code null} to apply to all 7534 * packages. 7535 * @param userHandle User to match, or {@link UserHandle#USER_ALL} to apply 7536 * to all users. 7537 * @param persistable If persistable grants should be removed. 7538 */ 7539 private void removeUriPermissionsForPackageLocked( 7540 String packageName, int userHandle, boolean persistable) { 7541 if (userHandle == UserHandle.USER_ALL && packageName == null) { 7542 throw new IllegalArgumentException("Must narrow by either package or user"); 7543 } 7544 7545 boolean persistChanged = false; 7546 7547 int N = mGrantedUriPermissions.size(); 7548 for (int i = 0; i < N; i++) { 7549 final int targetUid = mGrantedUriPermissions.keyAt(i); 7550 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 7551 7552 // Only inspect grants matching user 7553 if (userHandle == UserHandle.USER_ALL 7554 || userHandle == UserHandle.getUserId(targetUid)) { 7555 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 7556 final UriPermission perm = it.next(); 7557 7558 // Only inspect grants matching package 7559 if (packageName == null || perm.sourcePkg.equals(packageName) 7560 || perm.targetPkg.equals(packageName)) { 7561 persistChanged |= perm.revokeModes( 7562 persistable ? ~0 : ~Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 7563 7564 // Only remove when no modes remain; any persisted grants 7565 // will keep this alive. 7566 if (perm.modeFlags == 0) { 7567 it.remove(); 7568 } 7569 } 7570 } 7571 7572 if (perms.isEmpty()) { 7573 mGrantedUriPermissions.remove(targetUid); 7574 N--; 7575 i--; 7576 } 7577 } 7578 } 7579 7580 if (persistChanged) { 7581 schedulePersistUriGrants(); 7582 } 7583 } 7584 7585 @Override 7586 public IBinder newUriPermissionOwner(String name) { 7587 enforceNotIsolatedCaller("newUriPermissionOwner"); 7588 synchronized(this) { 7589 UriPermissionOwner owner = new UriPermissionOwner(this, name); 7590 return owner.getExternalTokenLocked(); 7591 } 7592 } 7593 7594 /** 7595 * @param uri This uri must NOT contain an embedded userId. 7596 * @param sourceUserId The userId in which the uri is to be resolved. 7597 * @param targetUserId The userId of the app that receives the grant. 7598 */ 7599 @Override 7600 public void grantUriPermissionFromOwner(IBinder token, int fromUid, String targetPkg, Uri uri, 7601 final int modeFlags, int sourceUserId, int targetUserId) { 7602 targetUserId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 7603 targetUserId, false, ALLOW_FULL_ONLY, "grantUriPermissionFromOwner", null); 7604 synchronized(this) { 7605 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 7606 if (owner == null) { 7607 throw new IllegalArgumentException("Unknown owner: " + token); 7608 } 7609 if (fromUid != Binder.getCallingUid()) { 7610 if (Binder.getCallingUid() != Process.myUid()) { 7611 // Only system code can grant URI permissions on behalf 7612 // of other users. 7613 throw new SecurityException("nice try"); 7614 } 7615 } 7616 if (targetPkg == null) { 7617 throw new IllegalArgumentException("null target"); 7618 } 7619 if (uri == null) { 7620 throw new IllegalArgumentException("null uri"); 7621 } 7622 7623 grantUriPermissionLocked(fromUid, targetPkg, new GrantUri(sourceUserId, uri, false), 7624 modeFlags, owner, targetUserId); 7625 } 7626 } 7627 7628 /** 7629 * @param uri This uri must NOT contain an embedded userId. 7630 * @param userId The userId in which the uri is to be resolved. 7631 */ 7632 @Override 7633 public void revokeUriPermissionFromOwner(IBinder token, Uri uri, int mode, int userId) { 7634 synchronized(this) { 7635 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 7636 if (owner == null) { 7637 throw new IllegalArgumentException("Unknown owner: " + token); 7638 } 7639 7640 if (uri == null) { 7641 owner.removeUriPermissionsLocked(mode); 7642 } else { 7643 owner.removeUriPermissionLocked(new GrantUri(userId, uri, false), mode); 7644 } 7645 } 7646 } 7647 7648 private void schedulePersistUriGrants() { 7649 if (!mHandler.hasMessages(PERSIST_URI_GRANTS_MSG)) { 7650 mHandler.sendMessageDelayed(mHandler.obtainMessage(PERSIST_URI_GRANTS_MSG), 7651 10 * DateUtils.SECOND_IN_MILLIS); 7652 } 7653 } 7654 7655 private void writeGrantedUriPermissions() { 7656 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "writeGrantedUriPermissions()"); 7657 7658 // Snapshot permissions so we can persist without lock 7659 ArrayList<UriPermission.Snapshot> persist = Lists.newArrayList(); 7660 synchronized (this) { 7661 final int size = mGrantedUriPermissions.size(); 7662 for (int i = 0; i < size; i++) { 7663 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 7664 for (UriPermission perm : perms.values()) { 7665 if (perm.persistedModeFlags != 0) { 7666 persist.add(perm.snapshot()); 7667 } 7668 } 7669 } 7670 } 7671 7672 FileOutputStream fos = null; 7673 try { 7674 fos = mGrantFile.startWrite(); 7675 7676 XmlSerializer out = new FastXmlSerializer(); 7677 out.setOutput(fos, "utf-8"); 7678 out.startDocument(null, true); 7679 out.startTag(null, TAG_URI_GRANTS); 7680 for (UriPermission.Snapshot perm : persist) { 7681 out.startTag(null, TAG_URI_GRANT); 7682 writeIntAttribute(out, ATTR_SOURCE_USER_ID, perm.uri.sourceUserId); 7683 writeIntAttribute(out, ATTR_TARGET_USER_ID, perm.targetUserId); 7684 out.attribute(null, ATTR_SOURCE_PKG, perm.sourcePkg); 7685 out.attribute(null, ATTR_TARGET_PKG, perm.targetPkg); 7686 out.attribute(null, ATTR_URI, String.valueOf(perm.uri.uri)); 7687 writeBooleanAttribute(out, ATTR_PREFIX, perm.uri.prefix); 7688 writeIntAttribute(out, ATTR_MODE_FLAGS, perm.persistedModeFlags); 7689 writeLongAttribute(out, ATTR_CREATED_TIME, perm.persistedCreateTime); 7690 out.endTag(null, TAG_URI_GRANT); 7691 } 7692 out.endTag(null, TAG_URI_GRANTS); 7693 out.endDocument(); 7694 7695 mGrantFile.finishWrite(fos); 7696 } catch (IOException e) { 7697 if (fos != null) { 7698 mGrantFile.failWrite(fos); 7699 } 7700 } 7701 } 7702 7703 private void readGrantedUriPermissionsLocked() { 7704 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "readGrantedUriPermissions()"); 7705 7706 final long now = System.currentTimeMillis(); 7707 7708 FileInputStream fis = null; 7709 try { 7710 fis = mGrantFile.openRead(); 7711 final XmlPullParser in = Xml.newPullParser(); 7712 in.setInput(fis, null); 7713 7714 int type; 7715 while ((type = in.next()) != END_DOCUMENT) { 7716 final String tag = in.getName(); 7717 if (type == START_TAG) { 7718 if (TAG_URI_GRANT.equals(tag)) { 7719 final int sourceUserId; 7720 final int targetUserId; 7721 final int userHandle = readIntAttribute(in, 7722 ATTR_USER_HANDLE, UserHandle.USER_NULL); 7723 if (userHandle != UserHandle.USER_NULL) { 7724 // For backwards compatibility. 7725 sourceUserId = userHandle; 7726 targetUserId = userHandle; 7727 } else { 7728 sourceUserId = readIntAttribute(in, ATTR_SOURCE_USER_ID); 7729 targetUserId = readIntAttribute(in, ATTR_TARGET_USER_ID); 7730 } 7731 final String sourcePkg = in.getAttributeValue(null, ATTR_SOURCE_PKG); 7732 final String targetPkg = in.getAttributeValue(null, ATTR_TARGET_PKG); 7733 final Uri uri = Uri.parse(in.getAttributeValue(null, ATTR_URI)); 7734 final boolean prefix = readBooleanAttribute(in, ATTR_PREFIX); 7735 final int modeFlags = readIntAttribute(in, ATTR_MODE_FLAGS); 7736 final long createdTime = readLongAttribute(in, ATTR_CREATED_TIME, now); 7737 7738 // Sanity check that provider still belongs to source package 7739 final ProviderInfo pi = getProviderInfoLocked( 7740 uri.getAuthority(), sourceUserId); 7741 if (pi != null && sourcePkg.equals(pi.packageName)) { 7742 int targetUid = -1; 7743 try { 7744 targetUid = AppGlobals.getPackageManager() 7745 .getPackageUid(targetPkg, targetUserId); 7746 } catch (RemoteException e) { 7747 } 7748 if (targetUid != -1) { 7749 final UriPermission perm = findOrCreateUriPermissionLocked( 7750 sourcePkg, targetPkg, targetUid, 7751 new GrantUri(sourceUserId, uri, prefix)); 7752 perm.initPersistedModes(modeFlags, createdTime); 7753 } 7754 } else { 7755 Slog.w(TAG, "Persisted grant for " + uri + " had source " + sourcePkg 7756 + " but instead found " + pi); 7757 } 7758 } 7759 } 7760 } 7761 } catch (FileNotFoundException e) { 7762 // Missing grants is okay 7763 } catch (IOException e) { 7764 Log.wtf(TAG, "Failed reading Uri grants", e); 7765 } catch (XmlPullParserException e) { 7766 Log.wtf(TAG, "Failed reading Uri grants", e); 7767 } finally { 7768 IoUtils.closeQuietly(fis); 7769 } 7770 } 7771 7772 /** 7773 * @param uri This uri must NOT contain an embedded userId. 7774 * @param userId The userId in which the uri is to be resolved. 7775 */ 7776 @Override 7777 public void takePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 7778 enforceNotIsolatedCaller("takePersistableUriPermission"); 7779 7780 Preconditions.checkFlagsArgument(modeFlags, 7781 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 7782 7783 synchronized (this) { 7784 final int callingUid = Binder.getCallingUid(); 7785 boolean persistChanged = false; 7786 GrantUri grantUri = new GrantUri(userId, uri, false); 7787 7788 UriPermission exactPerm = findUriPermissionLocked(callingUid, 7789 new GrantUri(userId, uri, false)); 7790 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 7791 new GrantUri(userId, uri, true)); 7792 7793 final boolean exactValid = (exactPerm != null) 7794 && ((modeFlags & exactPerm.persistableModeFlags) == modeFlags); 7795 final boolean prefixValid = (prefixPerm != null) 7796 && ((modeFlags & prefixPerm.persistableModeFlags) == modeFlags); 7797 7798 if (!(exactValid || prefixValid)) { 7799 throw new SecurityException("No persistable permission grants found for UID " 7800 + callingUid + " and Uri " + grantUri.toSafeString()); 7801 } 7802 7803 if (exactValid) { 7804 persistChanged |= exactPerm.takePersistableModes(modeFlags); 7805 } 7806 if (prefixValid) { 7807 persistChanged |= prefixPerm.takePersistableModes(modeFlags); 7808 } 7809 7810 persistChanged |= maybePrunePersistedUriGrantsLocked(callingUid); 7811 7812 if (persistChanged) { 7813 schedulePersistUriGrants(); 7814 } 7815 } 7816 } 7817 7818 /** 7819 * @param uri This uri must NOT contain an embedded userId. 7820 * @param userId The userId in which the uri is to be resolved. 7821 */ 7822 @Override 7823 public void releasePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 7824 enforceNotIsolatedCaller("releasePersistableUriPermission"); 7825 7826 Preconditions.checkFlagsArgument(modeFlags, 7827 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 7828 7829 synchronized (this) { 7830 final int callingUid = Binder.getCallingUid(); 7831 boolean persistChanged = false; 7832 7833 UriPermission exactPerm = findUriPermissionLocked(callingUid, 7834 new GrantUri(userId, uri, false)); 7835 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 7836 new GrantUri(userId, uri, true)); 7837 if (exactPerm == null && prefixPerm == null) { 7838 throw new SecurityException("No permission grants found for UID " + callingUid 7839 + " and Uri " + uri.toSafeString()); 7840 } 7841 7842 if (exactPerm != null) { 7843 persistChanged |= exactPerm.releasePersistableModes(modeFlags); 7844 removeUriPermissionIfNeededLocked(exactPerm); 7845 } 7846 if (prefixPerm != null) { 7847 persistChanged |= prefixPerm.releasePersistableModes(modeFlags); 7848 removeUriPermissionIfNeededLocked(prefixPerm); 7849 } 7850 7851 if (persistChanged) { 7852 schedulePersistUriGrants(); 7853 } 7854 } 7855 } 7856 7857 /** 7858 * Prune any older {@link UriPermission} for the given UID until outstanding 7859 * persisted grants are below {@link #MAX_PERSISTED_URI_GRANTS}. 7860 * 7861 * @return if any mutations occured that require persisting. 7862 */ 7863 private boolean maybePrunePersistedUriGrantsLocked(int uid) { 7864 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 7865 if (perms == null) return false; 7866 if (perms.size() < MAX_PERSISTED_URI_GRANTS) return false; 7867 7868 final ArrayList<UriPermission> persisted = Lists.newArrayList(); 7869 for (UriPermission perm : perms.values()) { 7870 if (perm.persistedModeFlags != 0) { 7871 persisted.add(perm); 7872 } 7873 } 7874 7875 final int trimCount = persisted.size() - MAX_PERSISTED_URI_GRANTS; 7876 if (trimCount <= 0) return false; 7877 7878 Collections.sort(persisted, new UriPermission.PersistedTimeComparator()); 7879 for (int i = 0; i < trimCount; i++) { 7880 final UriPermission perm = persisted.get(i); 7881 7882 if (DEBUG_URI_PERMISSION) { 7883 Slog.v(TAG, "Trimming grant created at " + perm.persistedCreateTime); 7884 } 7885 7886 perm.releasePersistableModes(~0); 7887 removeUriPermissionIfNeededLocked(perm); 7888 } 7889 7890 return true; 7891 } 7892 7893 @Override 7894 public ParceledListSlice<android.content.UriPermission> getPersistedUriPermissions( 7895 String packageName, boolean incoming) { 7896 enforceNotIsolatedCaller("getPersistedUriPermissions"); 7897 Preconditions.checkNotNull(packageName, "packageName"); 7898 7899 final int callingUid = Binder.getCallingUid(); 7900 final IPackageManager pm = AppGlobals.getPackageManager(); 7901 try { 7902 final int packageUid = pm.getPackageUid(packageName, UserHandle.getUserId(callingUid)); 7903 if (packageUid != callingUid) { 7904 throw new SecurityException( 7905 "Package " + packageName + " does not belong to calling UID " + callingUid); 7906 } 7907 } catch (RemoteException e) { 7908 throw new SecurityException("Failed to verify package name ownership"); 7909 } 7910 7911 final ArrayList<android.content.UriPermission> result = Lists.newArrayList(); 7912 synchronized (this) { 7913 if (incoming) { 7914 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 7915 callingUid); 7916 if (perms == null) { 7917 Slog.w(TAG, "No permission grants found for " + packageName); 7918 } else { 7919 for (UriPermission perm : perms.values()) { 7920 if (packageName.equals(perm.targetPkg) && perm.persistedModeFlags != 0) { 7921 result.add(perm.buildPersistedPublicApiObject()); 7922 } 7923 } 7924 } 7925 } else { 7926 final int size = mGrantedUriPermissions.size(); 7927 for (int i = 0; i < size; i++) { 7928 final ArrayMap<GrantUri, UriPermission> perms = 7929 mGrantedUriPermissions.valueAt(i); 7930 for (UriPermission perm : perms.values()) { 7931 if (packageName.equals(perm.sourcePkg) && perm.persistedModeFlags != 0) { 7932 result.add(perm.buildPersistedPublicApiObject()); 7933 } 7934 } 7935 } 7936 } 7937 } 7938 return new ParceledListSlice<android.content.UriPermission>(result); 7939 } 7940 7941 @Override 7942 public void showWaitingForDebugger(IApplicationThread who, boolean waiting) { 7943 synchronized (this) { 7944 ProcessRecord app = 7945 who != null ? getRecordForAppLocked(who) : null; 7946 if (app == null) return; 7947 7948 Message msg = Message.obtain(); 7949 msg.what = WAIT_FOR_DEBUGGER_MSG; 7950 msg.obj = app; 7951 msg.arg1 = waiting ? 1 : 0; 7952 mHandler.sendMessage(msg); 7953 } 7954 } 7955 7956 @Override 7957 public void getMemoryInfo(ActivityManager.MemoryInfo outInfo) { 7958 final long homeAppMem = mProcessList.getMemLevel(ProcessList.HOME_APP_ADJ); 7959 final long cachedAppMem = mProcessList.getMemLevel(ProcessList.CACHED_APP_MIN_ADJ); 7960 outInfo.availMem = Process.getFreeMemory(); 7961 outInfo.totalMem = Process.getTotalMemory(); 7962 outInfo.threshold = homeAppMem; 7963 outInfo.lowMemory = outInfo.availMem < (homeAppMem + ((cachedAppMem-homeAppMem)/2)); 7964 outInfo.hiddenAppThreshold = cachedAppMem; 7965 outInfo.secondaryServerThreshold = mProcessList.getMemLevel( 7966 ProcessList.SERVICE_ADJ); 7967 outInfo.visibleAppThreshold = mProcessList.getMemLevel( 7968 ProcessList.VISIBLE_APP_ADJ); 7969 outInfo.foregroundAppThreshold = mProcessList.getMemLevel( 7970 ProcessList.FOREGROUND_APP_ADJ); 7971 } 7972 7973 // ========================================================= 7974 // TASK MANAGEMENT 7975 // ========================================================= 7976 7977 @Override 7978 public List<IAppTask> getAppTasks(String callingPackage) { 7979 int callingUid = Binder.getCallingUid(); 7980 long ident = Binder.clearCallingIdentity(); 7981 7982 synchronized(this) { 7983 ArrayList<IAppTask> list = new ArrayList<IAppTask>(); 7984 try { 7985 if (localLOGV) Slog.v(TAG, "getAppTasks"); 7986 7987 final int N = mRecentTasks.size(); 7988 for (int i = 0; i < N; i++) { 7989 TaskRecord tr = mRecentTasks.get(i); 7990 // Skip tasks that do not match the caller. We don't need to verify 7991 // callingPackage, because we are also limiting to callingUid and know 7992 // that will limit to the correct security sandbox. 7993 if (tr.effectiveUid != callingUid) { 7994 continue; 7995 } 7996 Intent intent = tr.getBaseIntent(); 7997 if (intent == null || 7998 !callingPackage.equals(intent.getComponent().getPackageName())) { 7999 continue; 8000 } 8001 ActivityManager.RecentTaskInfo taskInfo = 8002 createRecentTaskInfoFromTaskRecord(tr); 8003 AppTaskImpl taskImpl = new AppTaskImpl(taskInfo.persistentId, callingUid); 8004 list.add(taskImpl); 8005 } 8006 } finally { 8007 Binder.restoreCallingIdentity(ident); 8008 } 8009 return list; 8010 } 8011 } 8012 8013 @Override 8014 public List<RunningTaskInfo> getTasks(int maxNum, int flags) { 8015 final int callingUid = Binder.getCallingUid(); 8016 ArrayList<RunningTaskInfo> list = new ArrayList<RunningTaskInfo>(); 8017 8018 synchronized(this) { 8019 if (localLOGV) Slog.v( 8020 TAG, "getTasks: max=" + maxNum + ", flags=" + flags); 8021 8022 final boolean allowed = checkCallingPermission( 8023 android.Manifest.permission.GET_TASKS) 8024 == PackageManager.PERMISSION_GRANTED; 8025 if (!allowed) { 8026 Slog.w(TAG, "getTasks: caller " + callingUid 8027 + " does not hold GET_TASKS; limiting output"); 8028 } 8029 8030 // TODO: Improve with MRU list from all ActivityStacks. 8031 mStackSupervisor.getTasksLocked(maxNum, list, callingUid, allowed); 8032 } 8033 8034 return list; 8035 } 8036 8037 TaskRecord getMostRecentTask() { 8038 return mRecentTasks.get(0); 8039 } 8040 8041 /** 8042 * Creates a new RecentTaskInfo from a TaskRecord. 8043 */ 8044 private ActivityManager.RecentTaskInfo createRecentTaskInfoFromTaskRecord(TaskRecord tr) { 8045 // Update the task description to reflect any changes in the task stack 8046 tr.updateTaskDescription(); 8047 8048 // Compose the recent task info 8049 ActivityManager.RecentTaskInfo rti = new ActivityManager.RecentTaskInfo(); 8050 rti.id = tr.getTopActivity() == null ? -1 : tr.taskId; 8051 rti.persistentId = tr.taskId; 8052 rti.baseIntent = new Intent(tr.getBaseIntent()); 8053 rti.origActivity = tr.origActivity; 8054 rti.description = tr.lastDescription; 8055 rti.stackId = tr.stack != null ? tr.stack.mStackId : -1; 8056 rti.userId = tr.userId; 8057 rti.taskDescription = new ActivityManager.TaskDescription(tr.lastTaskDescription); 8058 rti.firstActiveTime = tr.firstActiveTime; 8059 rti.lastActiveTime = tr.lastActiveTime; 8060 rti.affiliatedTaskId = tr.mAffiliatedTaskId; 8061 rti.affiliatedTaskColor = tr.mAffiliatedTaskColor; 8062 return rti; 8063 } 8064 8065 @Override 8066 public List<ActivityManager.RecentTaskInfo> getRecentTasks(int maxNum, int flags, int userId) { 8067 final int callingUid = Binder.getCallingUid(); 8068 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 8069 false, ALLOW_FULL_ONLY, "getRecentTasks", null); 8070 8071 final boolean includeProfiles = (flags & ActivityManager.RECENT_INCLUDE_PROFILES) != 0; 8072 final boolean withExcluded = (flags&ActivityManager.RECENT_WITH_EXCLUDED) != 0; 8073 synchronized (this) { 8074 final boolean allowed = checkCallingPermission(android.Manifest.permission.GET_TASKS) 8075 == PackageManager.PERMISSION_GRANTED; 8076 if (!allowed) { 8077 Slog.w(TAG, "getRecentTasks: caller " + callingUid 8078 + " does not hold GET_TASKS; limiting output"); 8079 } 8080 final boolean detailed = checkCallingPermission( 8081 android.Manifest.permission.GET_DETAILED_TASKS) 8082 == PackageManager.PERMISSION_GRANTED; 8083 8084 final int N = mRecentTasks.size(); 8085 ArrayList<ActivityManager.RecentTaskInfo> res 8086 = new ArrayList<ActivityManager.RecentTaskInfo>( 8087 maxNum < N ? maxNum : N); 8088 8089 final Set<Integer> includedUsers; 8090 if (includeProfiles) { 8091 includedUsers = getProfileIdsLocked(userId); 8092 } else { 8093 includedUsers = new HashSet<Integer>(); 8094 } 8095 includedUsers.add(Integer.valueOf(userId)); 8096 8097 for (int i=0; i<N && maxNum > 0; i++) { 8098 TaskRecord tr = mRecentTasks.get(i); 8099 // Only add calling user or related users recent tasks 8100 if (!includedUsers.contains(Integer.valueOf(tr.userId))) { 8101 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, not user: " + tr); 8102 continue; 8103 } 8104 8105 // Return the entry if desired by the caller. We always return 8106 // the first entry, because callers always expect this to be the 8107 // foreground app. We may filter others if the caller has 8108 // not supplied RECENT_WITH_EXCLUDED and there is some reason 8109 // we should exclude the entry. 8110 8111 if (i == 0 8112 || withExcluded 8113 || (tr.intent == null) 8114 || ((tr.intent.getFlags() & Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS) 8115 == 0)) { 8116 if (!allowed) { 8117 // If the caller doesn't have the GET_TASKS permission, then only 8118 // allow them to see a small subset of tasks -- their own and home. 8119 if (!tr.isHomeTask() && tr.effectiveUid != callingUid) { 8120 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, not allowed: " + tr); 8121 continue; 8122 } 8123 } 8124 if ((flags & ActivityManager.RECENT_IGNORE_HOME_STACK_TASKS) != 0) { 8125 if (tr.stack != null && tr.stack.isHomeStack()) { 8126 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, home stack task: " + tr); 8127 continue; 8128 } 8129 } 8130 if (tr.autoRemoveRecents && tr.getTopActivity() == null) { 8131 // Don't include auto remove tasks that are finished or finishing. 8132 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, auto-remove without activity: " 8133 + tr); 8134 continue; 8135 } 8136 if ((flags&ActivityManager.RECENT_IGNORE_UNAVAILABLE) != 0 8137 && !tr.isAvailable) { 8138 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, unavail real act: " + tr); 8139 continue; 8140 } 8141 8142 ActivityManager.RecentTaskInfo rti = createRecentTaskInfoFromTaskRecord(tr); 8143 if (!detailed) { 8144 rti.baseIntent.replaceExtras((Bundle)null); 8145 } 8146 8147 res.add(rti); 8148 maxNum--; 8149 } 8150 } 8151 return res; 8152 } 8153 } 8154 8155 private TaskRecord recentTaskForIdLocked(int id) { 8156 final int N = mRecentTasks.size(); 8157 for (int i=0; i<N; i++) { 8158 TaskRecord tr = mRecentTasks.get(i); 8159 if (tr.taskId == id) { 8160 return tr; 8161 } 8162 } 8163 return null; 8164 } 8165 8166 @Override 8167 public ActivityManager.TaskThumbnail getTaskThumbnail(int id) { 8168 synchronized (this) { 8169 enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER, 8170 "getTaskThumbnail()"); 8171 TaskRecord tr = recentTaskForIdLocked(id); 8172 if (tr != null) { 8173 return tr.getTaskThumbnailLocked(); 8174 } 8175 } 8176 return null; 8177 } 8178 8179 @Override 8180 public int addAppTask(IBinder activityToken, Intent intent, 8181 ActivityManager.TaskDescription description, Bitmap thumbnail) throws RemoteException { 8182 final int callingUid = Binder.getCallingUid(); 8183 final long callingIdent = Binder.clearCallingIdentity(); 8184 8185 try { 8186 synchronized (this) { 8187 ActivityRecord r = ActivityRecord.isInStackLocked(activityToken); 8188 if (r == null) { 8189 throw new IllegalArgumentException("Activity does not exist; token=" 8190 + activityToken); 8191 } 8192 ComponentName comp = intent.getComponent(); 8193 if (comp == null) { 8194 throw new IllegalArgumentException("Intent " + intent 8195 + " must specify explicit component"); 8196 } 8197 if (thumbnail.getWidth() != mThumbnailWidth 8198 || thumbnail.getHeight() != mThumbnailHeight) { 8199 throw new IllegalArgumentException("Bad thumbnail size: got " 8200 + thumbnail.getWidth() + "x" + thumbnail.getHeight() + ", require " 8201 + mThumbnailWidth + "x" + mThumbnailHeight); 8202 } 8203 if (intent.getSelector() != null) { 8204 intent.setSelector(null); 8205 } 8206 if (intent.getSourceBounds() != null) { 8207 intent.setSourceBounds(null); 8208 } 8209 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_DOCUMENT) != 0) { 8210 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS) == 0) { 8211 // The caller has added this as an auto-remove task... that makes no 8212 // sense, so turn off auto-remove. 8213 intent.addFlags(Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS); 8214 } 8215 } else if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_TASK) != 0) { 8216 // Must be a new task. 8217 intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 8218 } 8219 if (!comp.equals(mLastAddedTaskComponent) || callingUid != mLastAddedTaskUid) { 8220 mLastAddedTaskActivity = null; 8221 } 8222 ActivityInfo ainfo = mLastAddedTaskActivity; 8223 if (ainfo == null) { 8224 ainfo = mLastAddedTaskActivity = AppGlobals.getPackageManager().getActivityInfo( 8225 comp, 0, UserHandle.getUserId(callingUid)); 8226 if (ainfo.applicationInfo.uid != callingUid) { 8227 throw new SecurityException( 8228 "Can't add task for another application: target uid=" 8229 + ainfo.applicationInfo.uid + ", calling uid=" + callingUid); 8230 } 8231 } 8232 8233 TaskRecord task = new TaskRecord(this, mStackSupervisor.getNextTaskId(), ainfo, 8234 intent, description); 8235 8236 int trimIdx = trimRecentsForTask(task, false); 8237 if (trimIdx >= 0) { 8238 // If this would have caused a trim, then we'll abort because that 8239 // means it would be added at the end of the list but then just removed. 8240 return -1; 8241 } 8242 8243 final int N = mRecentTasks.size(); 8244 if (N >= (ActivityManager.getMaxRecentTasksStatic()-1)) { 8245 final TaskRecord tr = mRecentTasks.remove(N - 1); 8246 tr.removedFromRecents(mTaskPersister); 8247 } 8248 8249 task.inRecents = true; 8250 mRecentTasks.add(task); 8251 r.task.stack.addTask(task, false, false); 8252 8253 task.setLastThumbnail(thumbnail); 8254 task.freeLastThumbnail(); 8255 8256 return task.taskId; 8257 } 8258 } finally { 8259 Binder.restoreCallingIdentity(callingIdent); 8260 } 8261 } 8262 8263 @Override 8264 public Point getAppTaskThumbnailSize() { 8265 synchronized (this) { 8266 return new Point(mThumbnailWidth, mThumbnailHeight); 8267 } 8268 } 8269 8270 @Override 8271 public void setTaskDescription(IBinder token, ActivityManager.TaskDescription td) { 8272 synchronized (this) { 8273 ActivityRecord r = ActivityRecord.isInStackLocked(token); 8274 if (r != null) { 8275 r.taskDescription = td; 8276 r.task.updateTaskDescription(); 8277 } 8278 } 8279 } 8280 8281 private void cleanUpRemovedTaskLocked(TaskRecord tr, int flags) { 8282 mRecentTasks.remove(tr); 8283 tr.removedFromRecents(mTaskPersister); 8284 final boolean killProcesses = (flags&ActivityManager.REMOVE_TASK_KILL_PROCESS) != 0; 8285 Intent baseIntent = new Intent( 8286 tr.intent != null ? tr.intent : tr.affinityIntent); 8287 ComponentName component = baseIntent.getComponent(); 8288 if (component == null) { 8289 Slog.w(TAG, "Now component for base intent of task: " + tr); 8290 return; 8291 } 8292 8293 // Find any running services associated with this app. 8294 mServices.cleanUpRemovedTaskLocked(tr, component, baseIntent); 8295 8296 if (killProcesses) { 8297 // Find any running processes associated with this app. 8298 final String pkg = component.getPackageName(); 8299 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 8300 ArrayMap<String, SparseArray<ProcessRecord>> pmap = mProcessNames.getMap(); 8301 for (int i=0; i<pmap.size(); i++) { 8302 SparseArray<ProcessRecord> uids = pmap.valueAt(i); 8303 for (int j=0; j<uids.size(); j++) { 8304 ProcessRecord proc = uids.valueAt(j); 8305 if (proc.userId != tr.userId) { 8306 continue; 8307 } 8308 if (!proc.pkgList.containsKey(pkg)) { 8309 continue; 8310 } 8311 procs.add(proc); 8312 } 8313 } 8314 8315 // Kill the running processes. 8316 for (int i=0; i<procs.size(); i++) { 8317 ProcessRecord pr = procs.get(i); 8318 if (pr == mHomeProcess) { 8319 // Don't kill the home process along with tasks from the same package. 8320 continue; 8321 } 8322 if (pr.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 8323 pr.kill("remove task", true); 8324 } else { 8325 pr.waitingToKill = "remove task"; 8326 } 8327 } 8328 } 8329 } 8330 8331 /** 8332 * Removes the task with the specified task id. 8333 * 8334 * @param taskId Identifier of the task to be removed. 8335 * @param flags Additional operational flags. May be 0 or 8336 * {@link ActivityManager#REMOVE_TASK_KILL_PROCESS}. 8337 * @return Returns true if the given task was found and removed. 8338 */ 8339 private boolean removeTaskByIdLocked(int taskId, int flags) { 8340 TaskRecord tr = recentTaskForIdLocked(taskId); 8341 if (tr != null) { 8342 tr.removeTaskActivitiesLocked(); 8343 cleanUpRemovedTaskLocked(tr, flags); 8344 if (tr.isPersistable) { 8345 notifyTaskPersisterLocked(null, true); 8346 } 8347 return true; 8348 } 8349 return false; 8350 } 8351 8352 @Override 8353 public boolean removeTask(int taskId, int flags) { 8354 synchronized (this) { 8355 enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, 8356 "removeTask()"); 8357 long ident = Binder.clearCallingIdentity(); 8358 try { 8359 return removeTaskByIdLocked(taskId, flags); 8360 } finally { 8361 Binder.restoreCallingIdentity(ident); 8362 } 8363 } 8364 } 8365 8366 /** 8367 * TODO: Add mController hook 8368 */ 8369 @Override 8370 public void moveTaskToFront(int taskId, int flags, Bundle options) { 8371 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 8372 "moveTaskToFront()"); 8373 8374 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToFront: moving taskId=" + taskId); 8375 synchronized(this) { 8376 moveTaskToFrontLocked(taskId, flags, options); 8377 } 8378 } 8379 8380 void moveTaskToFrontLocked(int taskId, int flags, Bundle options) { 8381 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 8382 Binder.getCallingUid(), "Task to front")) { 8383 ActivityOptions.abort(options); 8384 return; 8385 } 8386 final long origId = Binder.clearCallingIdentity(); 8387 try { 8388 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 8389 if (task == null) { 8390 return; 8391 } 8392 if (mStackSupervisor.isLockTaskModeViolation(task)) { 8393 mStackSupervisor.showLockTaskToast(); 8394 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode"); 8395 return; 8396 } 8397 final ActivityRecord prev = mStackSupervisor.topRunningActivityLocked(); 8398 if (prev != null && prev.isRecentsActivity()) { 8399 task.setTaskToReturnTo(ActivityRecord.RECENTS_ACTIVITY_TYPE); 8400 } 8401 mStackSupervisor.findTaskToMoveToFrontLocked(task, flags, options); 8402 } finally { 8403 Binder.restoreCallingIdentity(origId); 8404 } 8405 ActivityOptions.abort(options); 8406 } 8407 8408 @Override 8409 public void moveTaskToBack(int taskId) { 8410 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 8411 "moveTaskToBack()"); 8412 8413 synchronized(this) { 8414 TaskRecord tr = recentTaskForIdLocked(taskId); 8415 if (tr != null) { 8416 if (tr == mStackSupervisor.mLockTaskModeTask) { 8417 mStackSupervisor.showLockTaskToast(); 8418 return; 8419 } 8420 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToBack: moving task=" + tr); 8421 ActivityStack stack = tr.stack; 8422 if (stack.mResumedActivity != null && stack.mResumedActivity.task == tr) { 8423 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 8424 Binder.getCallingUid(), "Task to back")) { 8425 return; 8426 } 8427 } 8428 final long origId = Binder.clearCallingIdentity(); 8429 try { 8430 stack.moveTaskToBackLocked(taskId, null); 8431 } finally { 8432 Binder.restoreCallingIdentity(origId); 8433 } 8434 } 8435 } 8436 } 8437 8438 /** 8439 * Moves an activity, and all of the other activities within the same task, to the bottom 8440 * of the history stack. The activity's order within the task is unchanged. 8441 * 8442 * @param token A reference to the activity we wish to move 8443 * @param nonRoot If false then this only works if the activity is the root 8444 * of a task; if true it will work for any activity in a task. 8445 * @return Returns true if the move completed, false if not. 8446 */ 8447 @Override 8448 public boolean moveActivityTaskToBack(IBinder token, boolean nonRoot) { 8449 enforceNotIsolatedCaller("moveActivityTaskToBack"); 8450 synchronized(this) { 8451 final long origId = Binder.clearCallingIdentity(); 8452 try { 8453 int taskId = ActivityRecord.getTaskForActivityLocked(token, !nonRoot); 8454 if (taskId >= 0) { 8455 if ((mStackSupervisor.mLockTaskModeTask != null) 8456 && (mStackSupervisor.mLockTaskModeTask.taskId == taskId)) { 8457 mStackSupervisor.showLockTaskToast(); 8458 return false; 8459 } 8460 return ActivityRecord.getStackLocked(token).moveTaskToBackLocked(taskId, null); 8461 } 8462 } finally { 8463 Binder.restoreCallingIdentity(origId); 8464 } 8465 } 8466 return false; 8467 } 8468 8469 @Override 8470 public void moveTaskBackwards(int task) { 8471 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 8472 "moveTaskBackwards()"); 8473 8474 synchronized(this) { 8475 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 8476 Binder.getCallingUid(), "Task backwards")) { 8477 return; 8478 } 8479 final long origId = Binder.clearCallingIdentity(); 8480 moveTaskBackwardsLocked(task); 8481 Binder.restoreCallingIdentity(origId); 8482 } 8483 } 8484 8485 private final void moveTaskBackwardsLocked(int task) { 8486 Slog.e(TAG, "moveTaskBackwards not yet implemented!"); 8487 } 8488 8489 @Override 8490 public IBinder getHomeActivityToken() throws RemoteException { 8491 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8492 "getHomeActivityToken()"); 8493 synchronized (this) { 8494 return mStackSupervisor.getHomeActivityToken(); 8495 } 8496 } 8497 8498 @Override 8499 public IActivityContainer createActivityContainer(IBinder parentActivityToken, 8500 IActivityContainerCallback callback) throws RemoteException { 8501 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8502 "createActivityContainer()"); 8503 synchronized (this) { 8504 if (parentActivityToken == null) { 8505 throw new IllegalArgumentException("parent token must not be null"); 8506 } 8507 ActivityRecord r = ActivityRecord.forToken(parentActivityToken); 8508 if (r == null) { 8509 return null; 8510 } 8511 if (callback == null) { 8512 throw new IllegalArgumentException("callback must not be null"); 8513 } 8514 return mStackSupervisor.createActivityContainer(r, callback); 8515 } 8516 } 8517 8518 @Override 8519 public void deleteActivityContainer(IActivityContainer container) throws RemoteException { 8520 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8521 "deleteActivityContainer()"); 8522 synchronized (this) { 8523 mStackSupervisor.deleteActivityContainer(container); 8524 } 8525 } 8526 8527 @Override 8528 public IActivityContainer getEnclosingActivityContainer(IBinder activityToken) 8529 throws RemoteException { 8530 synchronized (this) { 8531 ActivityStack stack = ActivityRecord.getStackLocked(activityToken); 8532 if (stack != null) { 8533 return stack.mActivityContainer; 8534 } 8535 return null; 8536 } 8537 } 8538 8539 @Override 8540 public void moveTaskToStack(int taskId, int stackId, boolean toTop) { 8541 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8542 "moveTaskToStack()"); 8543 if (stackId == HOME_STACK_ID) { 8544 Slog.e(TAG, "moveTaskToStack: Attempt to move task " + taskId + " to home stack", 8545 new RuntimeException("here").fillInStackTrace()); 8546 } 8547 synchronized (this) { 8548 long ident = Binder.clearCallingIdentity(); 8549 try { 8550 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToStack: moving task=" + taskId + " to stackId=" 8551 + stackId + " toTop=" + toTop); 8552 mStackSupervisor.moveTaskToStack(taskId, stackId, toTop); 8553 } finally { 8554 Binder.restoreCallingIdentity(ident); 8555 } 8556 } 8557 } 8558 8559 @Override 8560 public void resizeStack(int stackBoxId, Rect bounds) { 8561 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8562 "resizeStackBox()"); 8563 long ident = Binder.clearCallingIdentity(); 8564 try { 8565 mWindowManager.resizeStack(stackBoxId, bounds); 8566 } finally { 8567 Binder.restoreCallingIdentity(ident); 8568 } 8569 } 8570 8571 @Override 8572 public List<StackInfo> getAllStackInfos() { 8573 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8574 "getAllStackInfos()"); 8575 long ident = Binder.clearCallingIdentity(); 8576 try { 8577 synchronized (this) { 8578 return mStackSupervisor.getAllStackInfosLocked(); 8579 } 8580 } finally { 8581 Binder.restoreCallingIdentity(ident); 8582 } 8583 } 8584 8585 @Override 8586 public StackInfo getStackInfo(int stackId) { 8587 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8588 "getStackInfo()"); 8589 long ident = Binder.clearCallingIdentity(); 8590 try { 8591 synchronized (this) { 8592 return mStackSupervisor.getStackInfoLocked(stackId); 8593 } 8594 } finally { 8595 Binder.restoreCallingIdentity(ident); 8596 } 8597 } 8598 8599 @Override 8600 public boolean isInHomeStack(int taskId) { 8601 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8602 "getStackInfo()"); 8603 long ident = Binder.clearCallingIdentity(); 8604 try { 8605 synchronized (this) { 8606 TaskRecord tr = recentTaskForIdLocked(taskId); 8607 return tr != null && tr.stack != null && tr.stack.isHomeStack(); 8608 } 8609 } finally { 8610 Binder.restoreCallingIdentity(ident); 8611 } 8612 } 8613 8614 @Override 8615 public int getTaskForActivity(IBinder token, boolean onlyRoot) { 8616 synchronized(this) { 8617 return ActivityRecord.getTaskForActivityLocked(token, onlyRoot); 8618 } 8619 } 8620 8621 private boolean isLockTaskAuthorized(String pkg) { 8622 final DevicePolicyManager dpm = (DevicePolicyManager) 8623 mContext.getSystemService(Context.DEVICE_POLICY_SERVICE); 8624 try { 8625 int uid = mContext.getPackageManager().getPackageUid(pkg, 8626 Binder.getCallingUserHandle().getIdentifier()); 8627 return (uid == Binder.getCallingUid()) && dpm != null && dpm.isLockTaskPermitted(pkg); 8628 } catch (NameNotFoundException e) { 8629 return false; 8630 } 8631 } 8632 8633 void startLockTaskMode(TaskRecord task) { 8634 final String pkg; 8635 synchronized (this) { 8636 pkg = task.intent.getComponent().getPackageName(); 8637 } 8638 boolean isSystemInitiated = Binder.getCallingUid() == Process.SYSTEM_UID; 8639 if (!isSystemInitiated && !isLockTaskAuthorized(pkg)) { 8640 final TaskRecord taskRecord = task; 8641 mHandler.post(new Runnable() { 8642 @Override 8643 public void run() { 8644 mLockToAppRequest.showLockTaskPrompt(taskRecord); 8645 } 8646 }); 8647 return; 8648 } 8649 long ident = Binder.clearCallingIdentity(); 8650 try { 8651 synchronized (this) { 8652 // Since we lost lock on task, make sure it is still there. 8653 task = mStackSupervisor.anyTaskForIdLocked(task.taskId); 8654 if (task != null) { 8655 if (!isSystemInitiated 8656 && ((mFocusedActivity == null) || (task != mFocusedActivity.task))) { 8657 throw new IllegalArgumentException("Invalid task, not in foreground"); 8658 } 8659 mStackSupervisor.setLockTaskModeLocked(task, !isSystemInitiated); 8660 } 8661 } 8662 } finally { 8663 Binder.restoreCallingIdentity(ident); 8664 } 8665 } 8666 8667 @Override 8668 public void startLockTaskMode(int taskId) { 8669 final TaskRecord task; 8670 long ident = Binder.clearCallingIdentity(); 8671 try { 8672 synchronized (this) { 8673 task = mStackSupervisor.anyTaskForIdLocked(taskId); 8674 } 8675 } finally { 8676 Binder.restoreCallingIdentity(ident); 8677 } 8678 if (task != null) { 8679 startLockTaskMode(task); 8680 } 8681 } 8682 8683 @Override 8684 public void startLockTaskMode(IBinder token) { 8685 final TaskRecord task; 8686 long ident = Binder.clearCallingIdentity(); 8687 try { 8688 synchronized (this) { 8689 final ActivityRecord r = ActivityRecord.forToken(token); 8690 if (r == null) { 8691 return; 8692 } 8693 task = r.task; 8694 } 8695 } finally { 8696 Binder.restoreCallingIdentity(ident); 8697 } 8698 if (task != null) { 8699 startLockTaskMode(task); 8700 } 8701 } 8702 8703 @Override 8704 public void startLockTaskModeOnCurrent() throws RemoteException { 8705 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8706 "startLockTaskModeOnCurrent"); 8707 ActivityRecord r = null; 8708 synchronized (this) { 8709 r = mStackSupervisor.topRunningActivityLocked(); 8710 } 8711 startLockTaskMode(r.task); 8712 } 8713 8714 @Override 8715 public void stopLockTaskMode() { 8716 // Verify that the user matches the package of the intent for the TaskRecord 8717 // we are locked to or systtem. This will ensure the same caller for startLockTaskMode 8718 // and stopLockTaskMode. 8719 final int callingUid = Binder.getCallingUid(); 8720 if (callingUid != Process.SYSTEM_UID) { 8721 try { 8722 String pkg = 8723 mStackSupervisor.mLockTaskModeTask.intent.getComponent().getPackageName(); 8724 int uid = mContext.getPackageManager().getPackageUid(pkg, 8725 Binder.getCallingUserHandle().getIdentifier()); 8726 if (uid != callingUid) { 8727 throw new SecurityException("Invalid uid, expected " + uid); 8728 } 8729 } catch (NameNotFoundException e) { 8730 Log.d(TAG, "stopLockTaskMode " + e); 8731 return; 8732 } 8733 } 8734 long ident = Binder.clearCallingIdentity(); 8735 try { 8736 Log.d(TAG, "stopLockTaskMode"); 8737 // Stop lock task 8738 synchronized (this) { 8739 mStackSupervisor.setLockTaskModeLocked(null, false); 8740 } 8741 } finally { 8742 Binder.restoreCallingIdentity(ident); 8743 } 8744 } 8745 8746 @Override 8747 public void stopLockTaskModeOnCurrent() throws RemoteException { 8748 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8749 "stopLockTaskModeOnCurrent"); 8750 long ident = Binder.clearCallingIdentity(); 8751 try { 8752 stopLockTaskMode(); 8753 } finally { 8754 Binder.restoreCallingIdentity(ident); 8755 } 8756 } 8757 8758 @Override 8759 public boolean isInLockTaskMode() { 8760 synchronized (this) { 8761 return mStackSupervisor.isInLockTaskMode(); 8762 } 8763 } 8764 8765 // ========================================================= 8766 // CONTENT PROVIDERS 8767 // ========================================================= 8768 8769 private final List<ProviderInfo> generateApplicationProvidersLocked(ProcessRecord app) { 8770 List<ProviderInfo> providers = null; 8771 try { 8772 providers = AppGlobals.getPackageManager(). 8773 queryContentProviders(app.processName, app.uid, 8774 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS); 8775 } catch (RemoteException ex) { 8776 } 8777 if (DEBUG_MU) 8778 Slog.v(TAG_MU, "generateApplicationProvidersLocked, app.info.uid = " + app.uid); 8779 int userId = app.userId; 8780 if (providers != null) { 8781 int N = providers.size(); 8782 app.pubProviders.ensureCapacity(N + app.pubProviders.size()); 8783 for (int i=0; i<N; i++) { 8784 ProviderInfo cpi = 8785 (ProviderInfo)providers.get(i); 8786 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo, 8787 cpi.name, cpi.flags); 8788 if (singleton && UserHandle.getUserId(app.uid) != 0) { 8789 // This is a singleton provider, but a user besides the 8790 // default user is asking to initialize a process it runs 8791 // in... well, no, it doesn't actually run in this process, 8792 // it runs in the process of the default user. Get rid of it. 8793 providers.remove(i); 8794 N--; 8795 i--; 8796 continue; 8797 } 8798 8799 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 8800 ContentProviderRecord cpr = mProviderMap.getProviderByClass(comp, userId); 8801 if (cpr == null) { 8802 cpr = new ContentProviderRecord(this, cpi, app.info, comp, singleton); 8803 mProviderMap.putProviderByClass(comp, cpr); 8804 } 8805 if (DEBUG_MU) 8806 Slog.v(TAG_MU, "generateApplicationProvidersLocked, cpi.uid = " + cpr.uid); 8807 app.pubProviders.put(cpi.name, cpr); 8808 if (!cpi.multiprocess || !"android".equals(cpi.packageName)) { 8809 // Don't add this if it is a platform component that is marked 8810 // to run in multiple processes, because this is actually 8811 // part of the framework so doesn't make sense to track as a 8812 // separate apk in the process. 8813 app.addPackage(cpi.applicationInfo.packageName, cpi.applicationInfo.versionCode, 8814 mProcessStats); 8815 } 8816 ensurePackageDexOpt(cpi.applicationInfo.packageName); 8817 } 8818 } 8819 return providers; 8820 } 8821 8822 /** 8823 * Check if {@link ProcessRecord} has a possible chance at accessing the 8824 * given {@link ProviderInfo}. Final permission checking is always done 8825 * in {@link ContentProvider}. 8826 */ 8827 private final String checkContentProviderPermissionLocked( 8828 ProviderInfo cpi, ProcessRecord r, int userId, boolean checkUser) { 8829 final int callingPid = (r != null) ? r.pid : Binder.getCallingPid(); 8830 final int callingUid = (r != null) ? r.uid : Binder.getCallingUid(); 8831 boolean checkedGrants = false; 8832 if (checkUser) { 8833 // Looking for cross-user grants before enforcing the typical cross-users permissions 8834 int tmpTargetUserId = unsafeConvertIncomingUser(userId); 8835 if (tmpTargetUserId != UserHandle.getUserId(callingUid)) { 8836 if (checkAuthorityGrants(callingUid, cpi, tmpTargetUserId, checkUser)) { 8837 return null; 8838 } 8839 checkedGrants = true; 8840 } 8841 userId = handleIncomingUser(callingPid, callingUid, userId, 8842 false, ALLOW_NON_FULL, 8843 "checkContentProviderPermissionLocked " + cpi.authority, null); 8844 if (userId != tmpTargetUserId) { 8845 // When we actually went to determine the final targer user ID, this ended 8846 // up different than our initial check for the authority. This is because 8847 // they had asked for USER_CURRENT_OR_SELF and we ended up switching to 8848 // SELF. So we need to re-check the grants again. 8849 checkedGrants = false; 8850 } 8851 } 8852 if (checkComponentPermission(cpi.readPermission, callingPid, callingUid, 8853 cpi.applicationInfo.uid, cpi.exported) 8854 == PackageManager.PERMISSION_GRANTED) { 8855 return null; 8856 } 8857 if (checkComponentPermission(cpi.writePermission, callingPid, callingUid, 8858 cpi.applicationInfo.uid, cpi.exported) 8859 == PackageManager.PERMISSION_GRANTED) { 8860 return null; 8861 } 8862 8863 PathPermission[] pps = cpi.pathPermissions; 8864 if (pps != null) { 8865 int i = pps.length; 8866 while (i > 0) { 8867 i--; 8868 PathPermission pp = pps[i]; 8869 String pprperm = pp.getReadPermission(); 8870 if (pprperm != null && checkComponentPermission(pprperm, callingPid, callingUid, 8871 cpi.applicationInfo.uid, cpi.exported) 8872 == PackageManager.PERMISSION_GRANTED) { 8873 return null; 8874 } 8875 String ppwperm = pp.getWritePermission(); 8876 if (ppwperm != null && checkComponentPermission(ppwperm, callingPid, callingUid, 8877 cpi.applicationInfo.uid, cpi.exported) 8878 == PackageManager.PERMISSION_GRANTED) { 8879 return null; 8880 } 8881 } 8882 } 8883 if (!checkedGrants && checkAuthorityGrants(callingUid, cpi, userId, checkUser)) { 8884 return null; 8885 } 8886 8887 String msg; 8888 if (!cpi.exported) { 8889 msg = "Permission Denial: opening provider " + cpi.name 8890 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 8891 + ", uid=" + callingUid + ") that is not exported from uid " 8892 + cpi.applicationInfo.uid; 8893 } else { 8894 msg = "Permission Denial: opening provider " + cpi.name 8895 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 8896 + ", uid=" + callingUid + ") requires " 8897 + cpi.readPermission + " or " + cpi.writePermission; 8898 } 8899 Slog.w(TAG, msg); 8900 return msg; 8901 } 8902 8903 /** 8904 * Returns if the ContentProvider has granted a uri to callingUid 8905 */ 8906 boolean checkAuthorityGrants(int callingUid, ProviderInfo cpi, int userId, boolean checkUser) { 8907 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 8908 if (perms != null) { 8909 for (int i=perms.size()-1; i>=0; i--) { 8910 GrantUri grantUri = perms.keyAt(i); 8911 if (grantUri.sourceUserId == userId || !checkUser) { 8912 if (matchesProvider(grantUri.uri, cpi)) { 8913 return true; 8914 } 8915 } 8916 } 8917 } 8918 return false; 8919 } 8920 8921 /** 8922 * Returns true if the uri authority is one of the authorities specified in the provider. 8923 */ 8924 boolean matchesProvider(Uri uri, ProviderInfo cpi) { 8925 String uriAuth = uri.getAuthority(); 8926 String cpiAuth = cpi.authority; 8927 if (cpiAuth.indexOf(';') == -1) { 8928 return cpiAuth.equals(uriAuth); 8929 } 8930 String[] cpiAuths = cpiAuth.split(";"); 8931 int length = cpiAuths.length; 8932 for (int i = 0; i < length; i++) { 8933 if (cpiAuths[i].equals(uriAuth)) return true; 8934 } 8935 return false; 8936 } 8937 8938 ContentProviderConnection incProviderCountLocked(ProcessRecord r, 8939 final ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 8940 if (r != null) { 8941 for (int i=0; i<r.conProviders.size(); i++) { 8942 ContentProviderConnection conn = r.conProviders.get(i); 8943 if (conn.provider == cpr) { 8944 if (DEBUG_PROVIDER) Slog.v(TAG, 8945 "Adding provider requested by " 8946 + r.processName + " from process " 8947 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 8948 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 8949 if (stable) { 8950 conn.stableCount++; 8951 conn.numStableIncs++; 8952 } else { 8953 conn.unstableCount++; 8954 conn.numUnstableIncs++; 8955 } 8956 return conn; 8957 } 8958 } 8959 ContentProviderConnection conn = new ContentProviderConnection(cpr, r); 8960 if (stable) { 8961 conn.stableCount = 1; 8962 conn.numStableIncs = 1; 8963 } else { 8964 conn.unstableCount = 1; 8965 conn.numUnstableIncs = 1; 8966 } 8967 cpr.connections.add(conn); 8968 r.conProviders.add(conn); 8969 return conn; 8970 } 8971 cpr.addExternalProcessHandleLocked(externalProcessToken); 8972 return null; 8973 } 8974 8975 boolean decProviderCountLocked(ContentProviderConnection conn, 8976 ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 8977 if (conn != null) { 8978 cpr = conn.provider; 8979 if (DEBUG_PROVIDER) Slog.v(TAG, 8980 "Removing provider requested by " 8981 + conn.client.processName + " from process " 8982 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 8983 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 8984 if (stable) { 8985 conn.stableCount--; 8986 } else { 8987 conn.unstableCount--; 8988 } 8989 if (conn.stableCount == 0 && conn.unstableCount == 0) { 8990 cpr.connections.remove(conn); 8991 conn.client.conProviders.remove(conn); 8992 return true; 8993 } 8994 return false; 8995 } 8996 cpr.removeExternalProcessHandleLocked(externalProcessToken); 8997 return false; 8998 } 8999 9000 private void checkTime(long startTime, String where) { 9001 long now = SystemClock.elapsedRealtime(); 9002 if ((now-startTime) > 1000) { 9003 // If we are taking more than a second, log about it. 9004 Slog.w(TAG, "Slow operation: " + (now-startTime) + "ms so far, now at " + where); 9005 } 9006 } 9007 9008 private final ContentProviderHolder getContentProviderImpl(IApplicationThread caller, 9009 String name, IBinder token, boolean stable, int userId) { 9010 ContentProviderRecord cpr; 9011 ContentProviderConnection conn = null; 9012 ProviderInfo cpi = null; 9013 9014 synchronized(this) { 9015 long startTime = SystemClock.elapsedRealtime(); 9016 9017 ProcessRecord r = null; 9018 if (caller != null) { 9019 r = getRecordForAppLocked(caller); 9020 if (r == null) { 9021 throw new SecurityException( 9022 "Unable to find app for caller " + caller 9023 + " (pid=" + Binder.getCallingPid() 9024 + ") when getting content provider " + name); 9025 } 9026 } 9027 9028 boolean checkCrossUser = true; 9029 9030 checkTime(startTime, "getContentProviderImpl: getProviderByName"); 9031 9032 // First check if this content provider has been published... 9033 cpr = mProviderMap.getProviderByName(name, userId); 9034 // If that didn't work, check if it exists for user 0 and then 9035 // verify that it's a singleton provider before using it. 9036 if (cpr == null && userId != UserHandle.USER_OWNER) { 9037 cpr = mProviderMap.getProviderByName(name, UserHandle.USER_OWNER); 9038 if (cpr != null) { 9039 cpi = cpr.info; 9040 if (isSingleton(cpi.processName, cpi.applicationInfo, 9041 cpi.name, cpi.flags) 9042 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid)) { 9043 userId = UserHandle.USER_OWNER; 9044 checkCrossUser = false; 9045 } else { 9046 cpr = null; 9047 cpi = null; 9048 } 9049 } 9050 } 9051 9052 boolean providerRunning = cpr != null; 9053 if (providerRunning) { 9054 cpi = cpr.info; 9055 String msg; 9056 checkTime(startTime, "getContentProviderImpl: before checkContentProviderPermission"); 9057 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, checkCrossUser)) 9058 != null) { 9059 throw new SecurityException(msg); 9060 } 9061 checkTime(startTime, "getContentProviderImpl: after checkContentProviderPermission"); 9062 9063 if (r != null && cpr.canRunHere(r)) { 9064 // This provider has been published or is in the process 9065 // of being published... but it is also allowed to run 9066 // in the caller's process, so don't make a connection 9067 // and just let the caller instantiate its own instance. 9068 ContentProviderHolder holder = cpr.newHolder(null); 9069 // don't give caller the provider object, it needs 9070 // to make its own. 9071 holder.provider = null; 9072 return holder; 9073 } 9074 9075 final long origId = Binder.clearCallingIdentity(); 9076 9077 checkTime(startTime, "getContentProviderImpl: incProviderCountLocked"); 9078 9079 // In this case the provider instance already exists, so we can 9080 // return it right away. 9081 conn = incProviderCountLocked(r, cpr, token, stable); 9082 if (conn != null && (conn.stableCount+conn.unstableCount) == 1) { 9083 if (cpr.proc != null && r.setAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 9084 // If this is a perceptible app accessing the provider, 9085 // make sure to count it as being accessed and thus 9086 // back up on the LRU list. This is good because 9087 // content providers are often expensive to start. 9088 checkTime(startTime, "getContentProviderImpl: before updateLruProcess"); 9089 updateLruProcessLocked(cpr.proc, false, null); 9090 checkTime(startTime, "getContentProviderImpl: after updateLruProcess"); 9091 } 9092 } 9093 9094 if (cpr.proc != null) { 9095 if (false) { 9096 if (cpr.name.flattenToShortString().equals( 9097 "com.android.providers.calendar/.CalendarProvider2")) { 9098 Slog.v(TAG, "****************** KILLING " 9099 + cpr.name.flattenToShortString()); 9100 Process.killProcess(cpr.proc.pid); 9101 } 9102 } 9103 checkTime(startTime, "getContentProviderImpl: before updateOomAdj"); 9104 boolean success = updateOomAdjLocked(cpr.proc); 9105 checkTime(startTime, "getContentProviderImpl: after updateOomAdj"); 9106 if (DEBUG_PROVIDER) Slog.i(TAG, "Adjust success: " + success); 9107 // NOTE: there is still a race here where a signal could be 9108 // pending on the process even though we managed to update its 9109 // adj level. Not sure what to do about this, but at least 9110 // the race is now smaller. 9111 if (!success) { 9112 // Uh oh... it looks like the provider's process 9113 // has been killed on us. We need to wait for a new 9114 // process to be started, and make sure its death 9115 // doesn't kill our process. 9116 Slog.i(TAG, 9117 "Existing provider " + cpr.name.flattenToShortString() 9118 + " is crashing; detaching " + r); 9119 boolean lastRef = decProviderCountLocked(conn, cpr, token, stable); 9120 checkTime(startTime, "getContentProviderImpl: before appDied"); 9121 appDiedLocked(cpr.proc); 9122 checkTime(startTime, "getContentProviderImpl: after appDied"); 9123 if (!lastRef) { 9124 // This wasn't the last ref our process had on 9125 // the provider... we have now been killed, bail. 9126 return null; 9127 } 9128 providerRunning = false; 9129 conn = null; 9130 } 9131 } 9132 9133 Binder.restoreCallingIdentity(origId); 9134 } 9135 9136 boolean singleton; 9137 if (!providerRunning) { 9138 try { 9139 checkTime(startTime, "getContentProviderImpl: before resolveContentProvider"); 9140 cpi = AppGlobals.getPackageManager(). 9141 resolveContentProvider(name, 9142 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS, userId); 9143 checkTime(startTime, "getContentProviderImpl: after resolveContentProvider"); 9144 } catch (RemoteException ex) { 9145 } 9146 if (cpi == null) { 9147 return null; 9148 } 9149 // If the provider is a singleton AND 9150 // (it's a call within the same user || the provider is a 9151 // privileged app) 9152 // Then allow connecting to the singleton provider 9153 singleton = isSingleton(cpi.processName, cpi.applicationInfo, 9154 cpi.name, cpi.flags) 9155 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid); 9156 if (singleton) { 9157 userId = UserHandle.USER_OWNER; 9158 } 9159 cpi.applicationInfo = getAppInfoForUser(cpi.applicationInfo, userId); 9160 checkTime(startTime, "getContentProviderImpl: got app info for user"); 9161 9162 String msg; 9163 checkTime(startTime, "getContentProviderImpl: before checkContentProviderPermission"); 9164 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, !singleton)) 9165 != null) { 9166 throw new SecurityException(msg); 9167 } 9168 checkTime(startTime, "getContentProviderImpl: after checkContentProviderPermission"); 9169 9170 if (!mProcessesReady && !mDidUpdate && !mWaitingUpdate 9171 && !cpi.processName.equals("system")) { 9172 // If this content provider does not run in the system 9173 // process, and the system is not yet ready to run other 9174 // processes, then fail fast instead of hanging. 9175 throw new IllegalArgumentException( 9176 "Attempt to launch content provider before system ready"); 9177 } 9178 9179 // Make sure that the user who owns this provider is started. If not, 9180 // we don't want to allow it to run. 9181 if (mStartedUsers.get(userId) == null) { 9182 Slog.w(TAG, "Unable to launch app " 9183 + cpi.applicationInfo.packageName + "/" 9184 + cpi.applicationInfo.uid + " for provider " 9185 + name + ": user " + userId + " is stopped"); 9186 return null; 9187 } 9188 9189 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 9190 checkTime(startTime, "getContentProviderImpl: before getProviderByClass"); 9191 cpr = mProviderMap.getProviderByClass(comp, userId); 9192 checkTime(startTime, "getContentProviderImpl: after getProviderByClass"); 9193 final boolean firstClass = cpr == null; 9194 if (firstClass) { 9195 try { 9196 checkTime(startTime, "getContentProviderImpl: before getApplicationInfo"); 9197 ApplicationInfo ai = 9198 AppGlobals.getPackageManager(). 9199 getApplicationInfo( 9200 cpi.applicationInfo.packageName, 9201 STOCK_PM_FLAGS, userId); 9202 checkTime(startTime, "getContentProviderImpl: after getApplicationInfo"); 9203 if (ai == null) { 9204 Slog.w(TAG, "No package info for content provider " 9205 + cpi.name); 9206 return null; 9207 } 9208 ai = getAppInfoForUser(ai, userId); 9209 cpr = new ContentProviderRecord(this, cpi, ai, comp, singleton); 9210 } catch (RemoteException ex) { 9211 // pm is in same process, this will never happen. 9212 } 9213 } 9214 9215 checkTime(startTime, "getContentProviderImpl: now have ContentProviderRecord"); 9216 9217 if (r != null && cpr.canRunHere(r)) { 9218 // If this is a multiprocess provider, then just return its 9219 // info and allow the caller to instantiate it. Only do 9220 // this if the provider is the same user as the caller's 9221 // process, or can run as root (so can be in any process). 9222 return cpr.newHolder(null); 9223 } 9224 9225 if (DEBUG_PROVIDER) { 9226 RuntimeException e = new RuntimeException("here"); 9227 Slog.w(TAG, "LAUNCHING REMOTE PROVIDER (myuid " + (r != null ? r.uid : null) 9228 + " pruid " + cpr.appInfo.uid + "): " + cpr.info.name, e); 9229 } 9230 9231 // This is single process, and our app is now connecting to it. 9232 // See if we are already in the process of launching this 9233 // provider. 9234 final int N = mLaunchingProviders.size(); 9235 int i; 9236 for (i=0; i<N; i++) { 9237 if (mLaunchingProviders.get(i) == cpr) { 9238 break; 9239 } 9240 } 9241 9242 // If the provider is not already being launched, then get it 9243 // started. 9244 if (i >= N) { 9245 final long origId = Binder.clearCallingIdentity(); 9246 9247 try { 9248 // Content provider is now in use, its package can't be stopped. 9249 try { 9250 checkTime(startTime, "getContentProviderImpl: before set stopped state"); 9251 AppGlobals.getPackageManager().setPackageStoppedState( 9252 cpr.appInfo.packageName, false, userId); 9253 checkTime(startTime, "getContentProviderImpl: after set stopped state"); 9254 } catch (RemoteException e) { 9255 } catch (IllegalArgumentException e) { 9256 Slog.w(TAG, "Failed trying to unstop package " 9257 + cpr.appInfo.packageName + ": " + e); 9258 } 9259 9260 // Use existing process if already started 9261 checkTime(startTime, "getContentProviderImpl: looking for process record"); 9262 ProcessRecord proc = getProcessRecordLocked( 9263 cpi.processName, cpr.appInfo.uid, false); 9264 if (proc != null && proc.thread != null) { 9265 if (DEBUG_PROVIDER) { 9266 Slog.d(TAG, "Installing in existing process " + proc); 9267 } 9268 checkTime(startTime, "getContentProviderImpl: scheduling install"); 9269 proc.pubProviders.put(cpi.name, cpr); 9270 try { 9271 proc.thread.scheduleInstallProvider(cpi); 9272 } catch (RemoteException e) { 9273 } 9274 } else { 9275 checkTime(startTime, "getContentProviderImpl: before start process"); 9276 proc = startProcessLocked(cpi.processName, 9277 cpr.appInfo, false, 0, "content provider", 9278 new ComponentName(cpi.applicationInfo.packageName, 9279 cpi.name), false, false, false); 9280 checkTime(startTime, "getContentProviderImpl: after start process"); 9281 if (proc == null) { 9282 Slog.w(TAG, "Unable to launch app " 9283 + cpi.applicationInfo.packageName + "/" 9284 + cpi.applicationInfo.uid + " for provider " 9285 + name + ": process is bad"); 9286 return null; 9287 } 9288 } 9289 cpr.launchingApp = proc; 9290 mLaunchingProviders.add(cpr); 9291 } finally { 9292 Binder.restoreCallingIdentity(origId); 9293 } 9294 } 9295 9296 checkTime(startTime, "getContentProviderImpl: updating data structures"); 9297 9298 // Make sure the provider is published (the same provider class 9299 // may be published under multiple names). 9300 if (firstClass) { 9301 mProviderMap.putProviderByClass(comp, cpr); 9302 } 9303 9304 mProviderMap.putProviderByName(name, cpr); 9305 conn = incProviderCountLocked(r, cpr, token, stable); 9306 if (conn != null) { 9307 conn.waiting = true; 9308 } 9309 } 9310 checkTime(startTime, "getContentProviderImpl: done!"); 9311 } 9312 9313 // Wait for the provider to be published... 9314 synchronized (cpr) { 9315 while (cpr.provider == null) { 9316 if (cpr.launchingApp == null) { 9317 Slog.w(TAG, "Unable to launch app " 9318 + cpi.applicationInfo.packageName + "/" 9319 + cpi.applicationInfo.uid + " for provider " 9320 + name + ": launching app became null"); 9321 EventLog.writeEvent(EventLogTags.AM_PROVIDER_LOST_PROCESS, 9322 UserHandle.getUserId(cpi.applicationInfo.uid), 9323 cpi.applicationInfo.packageName, 9324 cpi.applicationInfo.uid, name); 9325 return null; 9326 } 9327 try { 9328 if (DEBUG_MU) { 9329 Slog.v(TAG_MU, "Waiting to start provider " + cpr + " launchingApp=" 9330 + cpr.launchingApp); 9331 } 9332 if (conn != null) { 9333 conn.waiting = true; 9334 } 9335 cpr.wait(); 9336 } catch (InterruptedException ex) { 9337 } finally { 9338 if (conn != null) { 9339 conn.waiting = false; 9340 } 9341 } 9342 } 9343 } 9344 return cpr != null ? cpr.newHolder(conn) : null; 9345 } 9346 9347 @Override 9348 public final ContentProviderHolder getContentProvider( 9349 IApplicationThread caller, String name, int userId, boolean stable) { 9350 enforceNotIsolatedCaller("getContentProvider"); 9351 if (caller == null) { 9352 String msg = "null IApplicationThread when getting content provider " 9353 + name; 9354 Slog.w(TAG, msg); 9355 throw new SecurityException(msg); 9356 } 9357 // The incoming user check is now handled in checkContentProviderPermissionLocked() to deal 9358 // with cross-user grant. 9359 return getContentProviderImpl(caller, name, null, stable, userId); 9360 } 9361 9362 public ContentProviderHolder getContentProviderExternal( 9363 String name, int userId, IBinder token) { 9364 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 9365 "Do not have permission in call getContentProviderExternal()"); 9366 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 9367 false, ALLOW_FULL_ONLY, "getContentProvider", null); 9368 return getContentProviderExternalUnchecked(name, token, userId); 9369 } 9370 9371 private ContentProviderHolder getContentProviderExternalUnchecked(String name, 9372 IBinder token, int userId) { 9373 return getContentProviderImpl(null, name, token, true, userId); 9374 } 9375 9376 /** 9377 * Drop a content provider from a ProcessRecord's bookkeeping 9378 */ 9379 public void removeContentProvider(IBinder connection, boolean stable) { 9380 enforceNotIsolatedCaller("removeContentProvider"); 9381 long ident = Binder.clearCallingIdentity(); 9382 try { 9383 synchronized (this) { 9384 ContentProviderConnection conn; 9385 try { 9386 conn = (ContentProviderConnection)connection; 9387 } catch (ClassCastException e) { 9388 String msg ="removeContentProvider: " + connection 9389 + " not a ContentProviderConnection"; 9390 Slog.w(TAG, msg); 9391 throw new IllegalArgumentException(msg); 9392 } 9393 if (conn == null) { 9394 throw new NullPointerException("connection is null"); 9395 } 9396 if (decProviderCountLocked(conn, null, null, stable)) { 9397 updateOomAdjLocked(); 9398 } 9399 } 9400 } finally { 9401 Binder.restoreCallingIdentity(ident); 9402 } 9403 } 9404 9405 public void removeContentProviderExternal(String name, IBinder token) { 9406 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 9407 "Do not have permission in call removeContentProviderExternal()"); 9408 removeContentProviderExternalUnchecked(name, token, UserHandle.getCallingUserId()); 9409 } 9410 9411 private void removeContentProviderExternalUnchecked(String name, IBinder token, int userId) { 9412 synchronized (this) { 9413 ContentProviderRecord cpr = mProviderMap.getProviderByName(name, userId); 9414 if(cpr == null) { 9415 //remove from mProvidersByClass 9416 if(localLOGV) Slog.v(TAG, name+" content provider not found in providers list"); 9417 return; 9418 } 9419 9420 //update content provider record entry info 9421 ComponentName comp = new ComponentName(cpr.info.packageName, cpr.info.name); 9422 ContentProviderRecord localCpr = mProviderMap.getProviderByClass(comp, userId); 9423 if (localCpr.hasExternalProcessHandles()) { 9424 if (localCpr.removeExternalProcessHandleLocked(token)) { 9425 updateOomAdjLocked(); 9426 } else { 9427 Slog.e(TAG, "Attmpt to remove content provider " + localCpr 9428 + " with no external reference for token: " 9429 + token + "."); 9430 } 9431 } else { 9432 Slog.e(TAG, "Attmpt to remove content provider: " + localCpr 9433 + " with no external references."); 9434 } 9435 } 9436 } 9437 9438 public final void publishContentProviders(IApplicationThread caller, 9439 List<ContentProviderHolder> providers) { 9440 if (providers == null) { 9441 return; 9442 } 9443 9444 enforceNotIsolatedCaller("publishContentProviders"); 9445 synchronized (this) { 9446 final ProcessRecord r = getRecordForAppLocked(caller); 9447 if (DEBUG_MU) 9448 Slog.v(TAG_MU, "ProcessRecord uid = " + r.uid); 9449 if (r == null) { 9450 throw new SecurityException( 9451 "Unable to find app for caller " + caller 9452 + " (pid=" + Binder.getCallingPid() 9453 + ") when publishing content providers"); 9454 } 9455 9456 final long origId = Binder.clearCallingIdentity(); 9457 9458 final int N = providers.size(); 9459 for (int i=0; i<N; i++) { 9460 ContentProviderHolder src = providers.get(i); 9461 if (src == null || src.info == null || src.provider == null) { 9462 continue; 9463 } 9464 ContentProviderRecord dst = r.pubProviders.get(src.info.name); 9465 if (DEBUG_MU) 9466 Slog.v(TAG_MU, "ContentProviderRecord uid = " + dst.uid); 9467 if (dst != null) { 9468 ComponentName comp = new ComponentName(dst.info.packageName, dst.info.name); 9469 mProviderMap.putProviderByClass(comp, dst); 9470 String names[] = dst.info.authority.split(";"); 9471 for (int j = 0; j < names.length; j++) { 9472 mProviderMap.putProviderByName(names[j], dst); 9473 } 9474 9475 int NL = mLaunchingProviders.size(); 9476 int j; 9477 for (j=0; j<NL; j++) { 9478 if (mLaunchingProviders.get(j) == dst) { 9479 mLaunchingProviders.remove(j); 9480 j--; 9481 NL--; 9482 } 9483 } 9484 synchronized (dst) { 9485 dst.provider = src.provider; 9486 dst.proc = r; 9487 dst.notifyAll(); 9488 } 9489 updateOomAdjLocked(r); 9490 } 9491 } 9492 9493 Binder.restoreCallingIdentity(origId); 9494 } 9495 } 9496 9497 public boolean refContentProvider(IBinder connection, int stable, int unstable) { 9498 ContentProviderConnection conn; 9499 try { 9500 conn = (ContentProviderConnection)connection; 9501 } catch (ClassCastException e) { 9502 String msg ="refContentProvider: " + connection 9503 + " not a ContentProviderConnection"; 9504 Slog.w(TAG, msg); 9505 throw new IllegalArgumentException(msg); 9506 } 9507 if (conn == null) { 9508 throw new NullPointerException("connection is null"); 9509 } 9510 9511 synchronized (this) { 9512 if (stable > 0) { 9513 conn.numStableIncs += stable; 9514 } 9515 stable = conn.stableCount + stable; 9516 if (stable < 0) { 9517 throw new IllegalStateException("stableCount < 0: " + stable); 9518 } 9519 9520 if (unstable > 0) { 9521 conn.numUnstableIncs += unstable; 9522 } 9523 unstable = conn.unstableCount + unstable; 9524 if (unstable < 0) { 9525 throw new IllegalStateException("unstableCount < 0: " + unstable); 9526 } 9527 9528 if ((stable+unstable) <= 0) { 9529 throw new IllegalStateException("ref counts can't go to zero here: stable=" 9530 + stable + " unstable=" + unstable); 9531 } 9532 conn.stableCount = stable; 9533 conn.unstableCount = unstable; 9534 return !conn.dead; 9535 } 9536 } 9537 9538 public void unstableProviderDied(IBinder connection) { 9539 ContentProviderConnection conn; 9540 try { 9541 conn = (ContentProviderConnection)connection; 9542 } catch (ClassCastException e) { 9543 String msg ="refContentProvider: " + connection 9544 + " not a ContentProviderConnection"; 9545 Slog.w(TAG, msg); 9546 throw new IllegalArgumentException(msg); 9547 } 9548 if (conn == null) { 9549 throw new NullPointerException("connection is null"); 9550 } 9551 9552 // Safely retrieve the content provider associated with the connection. 9553 IContentProvider provider; 9554 synchronized (this) { 9555 provider = conn.provider.provider; 9556 } 9557 9558 if (provider == null) { 9559 // Um, yeah, we're way ahead of you. 9560 return; 9561 } 9562 9563 // Make sure the caller is being honest with us. 9564 if (provider.asBinder().pingBinder()) { 9565 // Er, no, still looks good to us. 9566 synchronized (this) { 9567 Slog.w(TAG, "unstableProviderDied: caller " + Binder.getCallingUid() 9568 + " says " + conn + " died, but we don't agree"); 9569 return; 9570 } 9571 } 9572 9573 // Well look at that! It's dead! 9574 synchronized (this) { 9575 if (conn.provider.provider != provider) { 9576 // But something changed... good enough. 9577 return; 9578 } 9579 9580 ProcessRecord proc = conn.provider.proc; 9581 if (proc == null || proc.thread == null) { 9582 // Seems like the process is already cleaned up. 9583 return; 9584 } 9585 9586 // As far as we're concerned, this is just like receiving a 9587 // death notification... just a bit prematurely. 9588 Slog.i(TAG, "Process " + proc.processName + " (pid " + proc.pid 9589 + ") early provider death"); 9590 final long ident = Binder.clearCallingIdentity(); 9591 try { 9592 appDiedLocked(proc); 9593 } finally { 9594 Binder.restoreCallingIdentity(ident); 9595 } 9596 } 9597 } 9598 9599 @Override 9600 public void appNotRespondingViaProvider(IBinder connection) { 9601 enforceCallingPermission( 9602 android.Manifest.permission.REMOVE_TASKS, "appNotRespondingViaProvider()"); 9603 9604 final ContentProviderConnection conn = (ContentProviderConnection) connection; 9605 if (conn == null) { 9606 Slog.w(TAG, "ContentProviderConnection is null"); 9607 return; 9608 } 9609 9610 final ProcessRecord host = conn.provider.proc; 9611 if (host == null) { 9612 Slog.w(TAG, "Failed to find hosting ProcessRecord"); 9613 return; 9614 } 9615 9616 final long token = Binder.clearCallingIdentity(); 9617 try { 9618 appNotResponding(host, null, null, false, "ContentProvider not responding"); 9619 } finally { 9620 Binder.restoreCallingIdentity(token); 9621 } 9622 } 9623 9624 public final void installSystemProviders() { 9625 List<ProviderInfo> providers; 9626 synchronized (this) { 9627 ProcessRecord app = mProcessNames.get("system", Process.SYSTEM_UID); 9628 providers = generateApplicationProvidersLocked(app); 9629 if (providers != null) { 9630 for (int i=providers.size()-1; i>=0; i--) { 9631 ProviderInfo pi = (ProviderInfo)providers.get(i); 9632 if ((pi.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) == 0) { 9633 Slog.w(TAG, "Not installing system proc provider " + pi.name 9634 + ": not system .apk"); 9635 providers.remove(i); 9636 } 9637 } 9638 } 9639 } 9640 if (providers != null) { 9641 mSystemThread.installSystemProviders(providers); 9642 } 9643 9644 mCoreSettingsObserver = new CoreSettingsObserver(this); 9645 9646 //mUsageStatsService.monitorPackages(); 9647 } 9648 9649 /** 9650 * Allows apps to retrieve the MIME type of a URI. 9651 * If an app is in the same user as the ContentProvider, or if it is allowed to interact across 9652 * users, then it does not need permission to access the ContentProvider. 9653 * Either, it needs cross-user uri grants. 9654 * 9655 * CTS tests for this functionality can be run with "runtest cts-appsecurity". 9656 * 9657 * Test cases are at cts/tests/appsecurity-tests/test-apps/UsePermissionDiffCert/ 9658 * src/com/android/cts/usespermissiondiffcertapp/AccessPermissionWithDiffSigTest.java 9659 */ 9660 public String getProviderMimeType(Uri uri, int userId) { 9661 enforceNotIsolatedCaller("getProviderMimeType"); 9662 final String name = uri.getAuthority(); 9663 int callingUid = Binder.getCallingUid(); 9664 int callingPid = Binder.getCallingPid(); 9665 long ident = 0; 9666 boolean clearedIdentity = false; 9667 userId = unsafeConvertIncomingUser(userId); 9668 if (canClearIdentity(callingPid, callingUid, userId)) { 9669 clearedIdentity = true; 9670 ident = Binder.clearCallingIdentity(); 9671 } 9672 ContentProviderHolder holder = null; 9673 try { 9674 holder = getContentProviderExternalUnchecked(name, null, userId); 9675 if (holder != null) { 9676 return holder.provider.getType(uri); 9677 } 9678 } catch (RemoteException e) { 9679 Log.w(TAG, "Content provider dead retrieving " + uri, e); 9680 return null; 9681 } finally { 9682 // We need to clear the identity to call removeContentProviderExternalUnchecked 9683 if (!clearedIdentity) { 9684 ident = Binder.clearCallingIdentity(); 9685 } 9686 try { 9687 if (holder != null) { 9688 removeContentProviderExternalUnchecked(name, null, userId); 9689 } 9690 } finally { 9691 Binder.restoreCallingIdentity(ident); 9692 } 9693 } 9694 9695 return null; 9696 } 9697 9698 private boolean canClearIdentity(int callingPid, int callingUid, int userId) { 9699 if (UserHandle.getUserId(callingUid) == userId) { 9700 return true; 9701 } 9702 if (checkComponentPermission(INTERACT_ACROSS_USERS, callingPid, 9703 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED 9704 || checkComponentPermission(INTERACT_ACROSS_USERS_FULL, callingPid, 9705 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED) { 9706 return true; 9707 } 9708 return false; 9709 } 9710 9711 // ========================================================= 9712 // GLOBAL MANAGEMENT 9713 // ========================================================= 9714 9715 final ProcessRecord newProcessRecordLocked(ApplicationInfo info, String customProcess, 9716 boolean isolated, int isolatedUid) { 9717 String proc = customProcess != null ? customProcess : info.processName; 9718 BatteryStatsImpl.Uid.Proc ps = null; 9719 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 9720 int uid = info.uid; 9721 if (isolated) { 9722 if (isolatedUid == 0) { 9723 int userId = UserHandle.getUserId(uid); 9724 int stepsLeft = Process.LAST_ISOLATED_UID - Process.FIRST_ISOLATED_UID + 1; 9725 while (true) { 9726 if (mNextIsolatedProcessUid < Process.FIRST_ISOLATED_UID 9727 || mNextIsolatedProcessUid > Process.LAST_ISOLATED_UID) { 9728 mNextIsolatedProcessUid = Process.FIRST_ISOLATED_UID; 9729 } 9730 uid = UserHandle.getUid(userId, mNextIsolatedProcessUid); 9731 mNextIsolatedProcessUid++; 9732 if (mIsolatedProcesses.indexOfKey(uid) < 0) { 9733 // No process for this uid, use it. 9734 break; 9735 } 9736 stepsLeft--; 9737 if (stepsLeft <= 0) { 9738 return null; 9739 } 9740 } 9741 } else { 9742 // Special case for startIsolatedProcess (internal only), where 9743 // the uid of the isolated process is specified by the caller. 9744 uid = isolatedUid; 9745 } 9746 } 9747 return new ProcessRecord(stats, info, proc, uid); 9748 } 9749 9750 final ProcessRecord addAppLocked(ApplicationInfo info, boolean isolated, 9751 String abiOverride) { 9752 ProcessRecord app; 9753 if (!isolated) { 9754 app = getProcessRecordLocked(info.processName, info.uid, true); 9755 } else { 9756 app = null; 9757 } 9758 9759 if (app == null) { 9760 app = newProcessRecordLocked(info, null, isolated, 0); 9761 mProcessNames.put(info.processName, app.uid, app); 9762 if (isolated) { 9763 mIsolatedProcesses.put(app.uid, app); 9764 } 9765 updateLruProcessLocked(app, false, null); 9766 updateOomAdjLocked(); 9767 } 9768 9769 // This package really, really can not be stopped. 9770 try { 9771 AppGlobals.getPackageManager().setPackageStoppedState( 9772 info.packageName, false, UserHandle.getUserId(app.uid)); 9773 } catch (RemoteException e) { 9774 } catch (IllegalArgumentException e) { 9775 Slog.w(TAG, "Failed trying to unstop package " 9776 + info.packageName + ": " + e); 9777 } 9778 9779 if ((info.flags&(ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) 9780 == (ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) { 9781 app.persistent = true; 9782 app.maxAdj = ProcessList.PERSISTENT_PROC_ADJ; 9783 } 9784 if (app.thread == null && mPersistentStartingProcesses.indexOf(app) < 0) { 9785 mPersistentStartingProcesses.add(app); 9786 startProcessLocked(app, "added application", app.processName, abiOverride, 9787 null /* entryPoint */, null /* entryPointArgs */); 9788 } 9789 9790 return app; 9791 } 9792 9793 public void unhandledBack() { 9794 enforceCallingPermission(android.Manifest.permission.FORCE_BACK, 9795 "unhandledBack()"); 9796 9797 synchronized(this) { 9798 final long origId = Binder.clearCallingIdentity(); 9799 try { 9800 getFocusedStack().unhandledBackLocked(); 9801 } finally { 9802 Binder.restoreCallingIdentity(origId); 9803 } 9804 } 9805 } 9806 9807 public ParcelFileDescriptor openContentUri(Uri uri) throws RemoteException { 9808 enforceNotIsolatedCaller("openContentUri"); 9809 final int userId = UserHandle.getCallingUserId(); 9810 String name = uri.getAuthority(); 9811 ContentProviderHolder cph = getContentProviderExternalUnchecked(name, null, userId); 9812 ParcelFileDescriptor pfd = null; 9813 if (cph != null) { 9814 // We record the binder invoker's uid in thread-local storage before 9815 // going to the content provider to open the file. Later, in the code 9816 // that handles all permissions checks, we look for this uid and use 9817 // that rather than the Activity Manager's own uid. The effect is that 9818 // we do the check against the caller's permissions even though it looks 9819 // to the content provider like the Activity Manager itself is making 9820 // the request. 9821 sCallerIdentity.set(new Identity( 9822 Binder.getCallingPid(), Binder.getCallingUid())); 9823 try { 9824 pfd = cph.provider.openFile(null, uri, "r", null); 9825 } catch (FileNotFoundException e) { 9826 // do nothing; pfd will be returned null 9827 } finally { 9828 // Ensure that whatever happens, we clean up the identity state 9829 sCallerIdentity.remove(); 9830 } 9831 9832 // We've got the fd now, so we're done with the provider. 9833 removeContentProviderExternalUnchecked(name, null, userId); 9834 } else { 9835 Slog.d(TAG, "Failed to get provider for authority '" + name + "'"); 9836 } 9837 return pfd; 9838 } 9839 9840 // Actually is sleeping or shutting down or whatever else in the future 9841 // is an inactive state. 9842 public boolean isSleepingOrShuttingDown() { 9843 return mSleeping || mShuttingDown; 9844 } 9845 9846 public boolean isSleeping() { 9847 return mSleeping; 9848 } 9849 9850 void goingToSleep() { 9851 synchronized(this) { 9852 mWentToSleep = true; 9853 updateEventDispatchingLocked(); 9854 goToSleepIfNeededLocked(); 9855 } 9856 } 9857 9858 void finishRunningVoiceLocked() { 9859 if (mRunningVoice) { 9860 mRunningVoice = false; 9861 goToSleepIfNeededLocked(); 9862 } 9863 } 9864 9865 void goToSleepIfNeededLocked() { 9866 if (mWentToSleep && !mRunningVoice) { 9867 if (!mSleeping) { 9868 mSleeping = true; 9869 mStackSupervisor.goingToSleepLocked(); 9870 9871 // Initialize the wake times of all processes. 9872 checkExcessivePowerUsageLocked(false); 9873 mHandler.removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 9874 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 9875 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 9876 } 9877 } 9878 } 9879 9880 void notifyTaskPersisterLocked(TaskRecord task, boolean flush) { 9881 if (task != null && task.stack != null && task.stack.isHomeStack()) { 9882 // Never persist the home stack. 9883 return; 9884 } 9885 mTaskPersister.wakeup(task, flush); 9886 } 9887 9888 @Override 9889 public boolean shutdown(int timeout) { 9890 if (checkCallingPermission(android.Manifest.permission.SHUTDOWN) 9891 != PackageManager.PERMISSION_GRANTED) { 9892 throw new SecurityException("Requires permission " 9893 + android.Manifest.permission.SHUTDOWN); 9894 } 9895 9896 boolean timedout = false; 9897 9898 synchronized(this) { 9899 mShuttingDown = true; 9900 updateEventDispatchingLocked(); 9901 timedout = mStackSupervisor.shutdownLocked(timeout); 9902 } 9903 9904 mAppOpsService.shutdown(); 9905 if (mUsageStatsService != null) { 9906 mUsageStatsService.prepareShutdown(); 9907 } 9908 mBatteryStatsService.shutdown(); 9909 synchronized (this) { 9910 mProcessStats.shutdownLocked(); 9911 } 9912 notifyTaskPersisterLocked(null, true); 9913 9914 return timedout; 9915 } 9916 9917 public final void activitySlept(IBinder token) { 9918 if (localLOGV) Slog.v(TAG, "Activity slept: token=" + token); 9919 9920 final long origId = Binder.clearCallingIdentity(); 9921 9922 synchronized (this) { 9923 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9924 if (r != null) { 9925 mStackSupervisor.activitySleptLocked(r); 9926 } 9927 } 9928 9929 Binder.restoreCallingIdentity(origId); 9930 } 9931 9932 void logLockScreen(String msg) { 9933 if (DEBUG_LOCKSCREEN) Slog.d(TAG, Debug.getCallers(2) + ":" + msg + 9934 " mLockScreenShown=" + mLockScreenShown + " mWentToSleep=" + 9935 mWentToSleep + " mSleeping=" + mSleeping); 9936 } 9937 9938 private void comeOutOfSleepIfNeededLocked() { 9939 if ((!mWentToSleep && !mLockScreenShown) || mRunningVoice) { 9940 if (mSleeping) { 9941 mSleeping = false; 9942 mStackSupervisor.comeOutOfSleepIfNeededLocked(); 9943 } 9944 } 9945 } 9946 9947 void wakingUp() { 9948 synchronized(this) { 9949 mWentToSleep = false; 9950 updateEventDispatchingLocked(); 9951 comeOutOfSleepIfNeededLocked(); 9952 } 9953 } 9954 9955 void startRunningVoiceLocked() { 9956 if (!mRunningVoice) { 9957 mRunningVoice = true; 9958 comeOutOfSleepIfNeededLocked(); 9959 } 9960 } 9961 9962 private void updateEventDispatchingLocked() { 9963 mWindowManager.setEventDispatching(mBooted && !mShuttingDown); 9964 } 9965 9966 public void setLockScreenShown(boolean shown) { 9967 if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER) 9968 != PackageManager.PERMISSION_GRANTED) { 9969 throw new SecurityException("Requires permission " 9970 + android.Manifest.permission.DEVICE_POWER); 9971 } 9972 9973 synchronized(this) { 9974 long ident = Binder.clearCallingIdentity(); 9975 try { 9976 if (DEBUG_LOCKSCREEN) logLockScreen(" shown=" + shown); 9977 mLockScreenShown = shown; 9978 comeOutOfSleepIfNeededLocked(); 9979 } finally { 9980 Binder.restoreCallingIdentity(ident); 9981 } 9982 } 9983 } 9984 9985 @Override 9986 public void stopAppSwitches() { 9987 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 9988 != PackageManager.PERMISSION_GRANTED) { 9989 throw new SecurityException("Requires permission " 9990 + android.Manifest.permission.STOP_APP_SWITCHES); 9991 } 9992 9993 synchronized(this) { 9994 mAppSwitchesAllowedTime = SystemClock.uptimeMillis() 9995 + APP_SWITCH_DELAY_TIME; 9996 mDidAppSwitch = false; 9997 mHandler.removeMessages(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 9998 Message msg = mHandler.obtainMessage(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 9999 mHandler.sendMessageDelayed(msg, APP_SWITCH_DELAY_TIME); 10000 } 10001 } 10002 10003 public void resumeAppSwitches() { 10004 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 10005 != PackageManager.PERMISSION_GRANTED) { 10006 throw new SecurityException("Requires permission " 10007 + android.Manifest.permission.STOP_APP_SWITCHES); 10008 } 10009 10010 synchronized(this) { 10011 // Note that we don't execute any pending app switches... we will 10012 // let those wait until either the timeout, or the next start 10013 // activity request. 10014 mAppSwitchesAllowedTime = 0; 10015 } 10016 } 10017 10018 boolean checkAppSwitchAllowedLocked(int callingPid, int callingUid, 10019 String name) { 10020 if (mAppSwitchesAllowedTime < SystemClock.uptimeMillis()) { 10021 return true; 10022 } 10023 10024 final int perm = checkComponentPermission( 10025 android.Manifest.permission.STOP_APP_SWITCHES, callingPid, 10026 callingUid, -1, true); 10027 if (perm == PackageManager.PERMISSION_GRANTED) { 10028 return true; 10029 } 10030 10031 Slog.w(TAG, name + " request from " + callingUid + " stopped"); 10032 return false; 10033 } 10034 10035 public void setDebugApp(String packageName, boolean waitForDebugger, 10036 boolean persistent) { 10037 enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP, 10038 "setDebugApp()"); 10039 10040 long ident = Binder.clearCallingIdentity(); 10041 try { 10042 // Note that this is not really thread safe if there are multiple 10043 // callers into it at the same time, but that's not a situation we 10044 // care about. 10045 if (persistent) { 10046 final ContentResolver resolver = mContext.getContentResolver(); 10047 Settings.Global.putString( 10048 resolver, Settings.Global.DEBUG_APP, 10049 packageName); 10050 Settings.Global.putInt( 10051 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 10052 waitForDebugger ? 1 : 0); 10053 } 10054 10055 synchronized (this) { 10056 if (!persistent) { 10057 mOrigDebugApp = mDebugApp; 10058 mOrigWaitForDebugger = mWaitForDebugger; 10059 } 10060 mDebugApp = packageName; 10061 mWaitForDebugger = waitForDebugger; 10062 mDebugTransient = !persistent; 10063 if (packageName != null) { 10064 forceStopPackageLocked(packageName, -1, false, false, true, true, 10065 false, UserHandle.USER_ALL, "set debug app"); 10066 } 10067 } 10068 } finally { 10069 Binder.restoreCallingIdentity(ident); 10070 } 10071 } 10072 10073 void setOpenGlTraceApp(ApplicationInfo app, String processName) { 10074 synchronized (this) { 10075 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 10076 if (!isDebuggable) { 10077 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 10078 throw new SecurityException("Process not debuggable: " + app.packageName); 10079 } 10080 } 10081 10082 mOpenGlTraceApp = processName; 10083 } 10084 } 10085 10086 void setProfileApp(ApplicationInfo app, String processName, ProfilerInfo profilerInfo) { 10087 synchronized (this) { 10088 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 10089 if (!isDebuggable) { 10090 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 10091 throw new SecurityException("Process not debuggable: " + app.packageName); 10092 } 10093 } 10094 mProfileApp = processName; 10095 mProfileFile = profilerInfo.profileFile; 10096 if (mProfileFd != null) { 10097 try { 10098 mProfileFd.close(); 10099 } catch (IOException e) { 10100 } 10101 mProfileFd = null; 10102 } 10103 mProfileFd = profilerInfo.profileFd; 10104 mSamplingInterval = profilerInfo.samplingInterval; 10105 mAutoStopProfiler = profilerInfo.autoStopProfiler; 10106 mProfileType = 0; 10107 } 10108 } 10109 10110 @Override 10111 public void setAlwaysFinish(boolean enabled) { 10112 enforceCallingPermission(android.Manifest.permission.SET_ALWAYS_FINISH, 10113 "setAlwaysFinish()"); 10114 10115 Settings.Global.putInt( 10116 mContext.getContentResolver(), 10117 Settings.Global.ALWAYS_FINISH_ACTIVITIES, enabled ? 1 : 0); 10118 10119 synchronized (this) { 10120 mAlwaysFinishActivities = enabled; 10121 } 10122 } 10123 10124 @Override 10125 public void setActivityController(IActivityController controller) { 10126 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 10127 "setActivityController()"); 10128 synchronized (this) { 10129 mController = controller; 10130 Watchdog.getInstance().setActivityController(controller); 10131 } 10132 } 10133 10134 @Override 10135 public void setUserIsMonkey(boolean userIsMonkey) { 10136 synchronized (this) { 10137 synchronized (mPidsSelfLocked) { 10138 final int callingPid = Binder.getCallingPid(); 10139 ProcessRecord precessRecord = mPidsSelfLocked.get(callingPid); 10140 if (precessRecord == null) { 10141 throw new SecurityException("Unknown process: " + callingPid); 10142 } 10143 if (precessRecord.instrumentationUiAutomationConnection == null) { 10144 throw new SecurityException("Only an instrumentation process " 10145 + "with a UiAutomation can call setUserIsMonkey"); 10146 } 10147 } 10148 mUserIsMonkey = userIsMonkey; 10149 } 10150 } 10151 10152 @Override 10153 public boolean isUserAMonkey() { 10154 synchronized (this) { 10155 // If there is a controller also implies the user is a monkey. 10156 return (mUserIsMonkey || mController != null); 10157 } 10158 } 10159 10160 public void requestBugReport() { 10161 enforceCallingPermission(android.Manifest.permission.DUMP, "requestBugReport"); 10162 SystemProperties.set("ctl.start", "bugreport"); 10163 } 10164 10165 public static long getInputDispatchingTimeoutLocked(ActivityRecord r) { 10166 return r != null ? getInputDispatchingTimeoutLocked(r.app) : KEY_DISPATCHING_TIMEOUT; 10167 } 10168 10169 public static long getInputDispatchingTimeoutLocked(ProcessRecord r) { 10170 if (r != null && (r.instrumentationClass != null || r.usingWrapper)) { 10171 return INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT; 10172 } 10173 return KEY_DISPATCHING_TIMEOUT; 10174 } 10175 10176 @Override 10177 public long inputDispatchingTimedOut(int pid, final boolean aboveSystem, String reason) { 10178 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 10179 != PackageManager.PERMISSION_GRANTED) { 10180 throw new SecurityException("Requires permission " 10181 + android.Manifest.permission.FILTER_EVENTS); 10182 } 10183 ProcessRecord proc; 10184 long timeout; 10185 synchronized (this) { 10186 synchronized (mPidsSelfLocked) { 10187 proc = mPidsSelfLocked.get(pid); 10188 } 10189 timeout = getInputDispatchingTimeoutLocked(proc); 10190 } 10191 10192 if (!inputDispatchingTimedOut(proc, null, null, aboveSystem, reason)) { 10193 return -1; 10194 } 10195 10196 return timeout; 10197 } 10198 10199 /** 10200 * Handle input dispatching timeouts. 10201 * Returns whether input dispatching should be aborted or not. 10202 */ 10203 public boolean inputDispatchingTimedOut(final ProcessRecord proc, 10204 final ActivityRecord activity, final ActivityRecord parent, 10205 final boolean aboveSystem, String reason) { 10206 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 10207 != PackageManager.PERMISSION_GRANTED) { 10208 throw new SecurityException("Requires permission " 10209 + android.Manifest.permission.FILTER_EVENTS); 10210 } 10211 10212 final String annotation; 10213 if (reason == null) { 10214 annotation = "Input dispatching timed out"; 10215 } else { 10216 annotation = "Input dispatching timed out (" + reason + ")"; 10217 } 10218 10219 if (proc != null) { 10220 synchronized (this) { 10221 if (proc.debugging) { 10222 return false; 10223 } 10224 10225 if (mDidDexOpt) { 10226 // Give more time since we were dexopting. 10227 mDidDexOpt = false; 10228 return false; 10229 } 10230 10231 if (proc.instrumentationClass != null) { 10232 Bundle info = new Bundle(); 10233 info.putString("shortMsg", "keyDispatchingTimedOut"); 10234 info.putString("longMsg", annotation); 10235 finishInstrumentationLocked(proc, Activity.RESULT_CANCELED, info); 10236 return true; 10237 } 10238 } 10239 mHandler.post(new Runnable() { 10240 @Override 10241 public void run() { 10242 appNotResponding(proc, activity, parent, aboveSystem, annotation); 10243 } 10244 }); 10245 } 10246 10247 return true; 10248 } 10249 10250 public Bundle getAssistContextExtras(int requestType) { 10251 enforceCallingPermission(android.Manifest.permission.GET_TOP_ACTIVITY_INFO, 10252 "getAssistContextExtras()"); 10253 PendingAssistExtras pae; 10254 Bundle extras = new Bundle(); 10255 synchronized (this) { 10256 ActivityRecord activity = getFocusedStack().mResumedActivity; 10257 if (activity == null) { 10258 Slog.w(TAG, "getAssistContextExtras failed: no resumed activity"); 10259 return null; 10260 } 10261 extras.putString(Intent.EXTRA_ASSIST_PACKAGE, activity.packageName); 10262 if (activity.app == null || activity.app.thread == null) { 10263 Slog.w(TAG, "getAssistContextExtras failed: no process for " + activity); 10264 return extras; 10265 } 10266 if (activity.app.pid == Binder.getCallingPid()) { 10267 Slog.w(TAG, "getAssistContextExtras failed: request process same as " + activity); 10268 return extras; 10269 } 10270 pae = new PendingAssistExtras(activity); 10271 try { 10272 activity.app.thread.requestAssistContextExtras(activity.appToken, pae, 10273 requestType); 10274 mPendingAssistExtras.add(pae); 10275 mHandler.postDelayed(pae, PENDING_ASSIST_EXTRAS_TIMEOUT); 10276 } catch (RemoteException e) { 10277 Slog.w(TAG, "getAssistContextExtras failed: crash calling " + activity); 10278 return extras; 10279 } 10280 } 10281 synchronized (pae) { 10282 while (!pae.haveResult) { 10283 try { 10284 pae.wait(); 10285 } catch (InterruptedException e) { 10286 } 10287 } 10288 if (pae.result != null) { 10289 extras.putBundle(Intent.EXTRA_ASSIST_CONTEXT, pae.result); 10290 } 10291 } 10292 synchronized (this) { 10293 mPendingAssistExtras.remove(pae); 10294 mHandler.removeCallbacks(pae); 10295 } 10296 return extras; 10297 } 10298 10299 public void reportAssistContextExtras(IBinder token, Bundle extras) { 10300 PendingAssistExtras pae = (PendingAssistExtras)token; 10301 synchronized (pae) { 10302 pae.result = extras; 10303 pae.haveResult = true; 10304 pae.notifyAll(); 10305 } 10306 } 10307 10308 public void registerProcessObserver(IProcessObserver observer) { 10309 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 10310 "registerProcessObserver()"); 10311 synchronized (this) { 10312 mProcessObservers.register(observer); 10313 } 10314 } 10315 10316 @Override 10317 public void unregisterProcessObserver(IProcessObserver observer) { 10318 synchronized (this) { 10319 mProcessObservers.unregister(observer); 10320 } 10321 } 10322 10323 @Override 10324 public boolean convertFromTranslucent(IBinder token) { 10325 final long origId = Binder.clearCallingIdentity(); 10326 try { 10327 synchronized (this) { 10328 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10329 if (r == null) { 10330 return false; 10331 } 10332 final boolean translucentChanged = r.changeWindowTranslucency(true); 10333 if (translucentChanged) { 10334 r.task.stack.releaseBackgroundResources(); 10335 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 10336 } 10337 mWindowManager.setAppFullscreen(token, true); 10338 return translucentChanged; 10339 } 10340 } finally { 10341 Binder.restoreCallingIdentity(origId); 10342 } 10343 } 10344 10345 @Override 10346 public boolean convertToTranslucent(IBinder token, ActivityOptions options) { 10347 final long origId = Binder.clearCallingIdentity(); 10348 try { 10349 synchronized (this) { 10350 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10351 if (r == null) { 10352 return false; 10353 } 10354 int index = r.task.mActivities.lastIndexOf(r); 10355 if (index > 0) { 10356 ActivityRecord under = r.task.mActivities.get(index - 1); 10357 under.returningOptions = options; 10358 } 10359 final boolean translucentChanged = r.changeWindowTranslucency(false); 10360 if (translucentChanged) { 10361 r.task.stack.convertToTranslucent(r); 10362 } 10363 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 10364 mWindowManager.setAppFullscreen(token, false); 10365 return translucentChanged; 10366 } 10367 } finally { 10368 Binder.restoreCallingIdentity(origId); 10369 } 10370 } 10371 10372 @Override 10373 public boolean requestVisibleBehind(IBinder token, boolean visible) { 10374 final long origId = Binder.clearCallingIdentity(); 10375 try { 10376 synchronized (this) { 10377 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10378 if (r != null) { 10379 return mStackSupervisor.requestVisibleBehindLocked(r, visible); 10380 } 10381 } 10382 return false; 10383 } finally { 10384 Binder.restoreCallingIdentity(origId); 10385 } 10386 } 10387 10388 @Override 10389 public boolean isBackgroundVisibleBehind(IBinder token) { 10390 final long origId = Binder.clearCallingIdentity(); 10391 try { 10392 synchronized (this) { 10393 final ActivityStack stack = ActivityRecord.getStackLocked(token); 10394 final boolean visible = stack == null ? false : stack.hasVisibleBehindActivity(); 10395 if (ActivityStackSupervisor.DEBUG_VISIBLE_BEHIND) Slog.d(TAG, 10396 "isBackgroundVisibleBehind: stack=" + stack + " visible=" + visible); 10397 return visible; 10398 } 10399 } finally { 10400 Binder.restoreCallingIdentity(origId); 10401 } 10402 } 10403 10404 @Override 10405 public ActivityOptions getActivityOptions(IBinder token) { 10406 final long origId = Binder.clearCallingIdentity(); 10407 try { 10408 synchronized (this) { 10409 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10410 if (r != null) { 10411 final ActivityOptions activityOptions = r.pendingOptions; 10412 r.pendingOptions = null; 10413 return activityOptions; 10414 } 10415 return null; 10416 } 10417 } finally { 10418 Binder.restoreCallingIdentity(origId); 10419 } 10420 } 10421 10422 @Override 10423 public void setImmersive(IBinder token, boolean immersive) { 10424 synchronized(this) { 10425 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10426 if (r == null) { 10427 throw new IllegalArgumentException(); 10428 } 10429 r.immersive = immersive; 10430 10431 // update associated state if we're frontmost 10432 if (r == mFocusedActivity) { 10433 if (DEBUG_IMMERSIVE) { 10434 Slog.d(TAG, "Frontmost changed immersion: "+ r); 10435 } 10436 applyUpdateLockStateLocked(r); 10437 } 10438 } 10439 } 10440 10441 @Override 10442 public boolean isImmersive(IBinder token) { 10443 synchronized (this) { 10444 ActivityRecord r = ActivityRecord.isInStackLocked(token); 10445 if (r == null) { 10446 throw new IllegalArgumentException(); 10447 } 10448 return r.immersive; 10449 } 10450 } 10451 10452 public boolean isTopActivityImmersive() { 10453 enforceNotIsolatedCaller("startActivity"); 10454 synchronized (this) { 10455 ActivityRecord r = getFocusedStack().topRunningActivityLocked(null); 10456 return (r != null) ? r.immersive : false; 10457 } 10458 } 10459 10460 @Override 10461 public boolean isTopOfTask(IBinder token) { 10462 synchronized (this) { 10463 ActivityRecord r = ActivityRecord.isInStackLocked(token); 10464 if (r == null) { 10465 throw new IllegalArgumentException(); 10466 } 10467 return r.task.getTopActivity() == r; 10468 } 10469 } 10470 10471 public final void enterSafeMode() { 10472 synchronized(this) { 10473 // It only makes sense to do this before the system is ready 10474 // and started launching other packages. 10475 if (!mSystemReady) { 10476 try { 10477 AppGlobals.getPackageManager().enterSafeMode(); 10478 } catch (RemoteException e) { 10479 } 10480 } 10481 10482 mSafeMode = true; 10483 } 10484 } 10485 10486 public final void showSafeModeOverlay() { 10487 View v = LayoutInflater.from(mContext).inflate( 10488 com.android.internal.R.layout.safe_mode, null); 10489 WindowManager.LayoutParams lp = new WindowManager.LayoutParams(); 10490 lp.type = WindowManager.LayoutParams.TYPE_SECURE_SYSTEM_OVERLAY; 10491 lp.width = WindowManager.LayoutParams.WRAP_CONTENT; 10492 lp.height = WindowManager.LayoutParams.WRAP_CONTENT; 10493 lp.gravity = Gravity.BOTTOM | Gravity.START; 10494 lp.format = v.getBackground().getOpacity(); 10495 lp.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE 10496 | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE; 10497 lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; 10498 ((WindowManager)mContext.getSystemService( 10499 Context.WINDOW_SERVICE)).addView(v, lp); 10500 } 10501 10502 public void noteWakeupAlarm(IIntentSender sender, int sourceUid, String sourcePkg) { 10503 if (!(sender instanceof PendingIntentRecord)) { 10504 return; 10505 } 10506 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 10507 synchronized (stats) { 10508 if (mBatteryStatsService.isOnBattery()) { 10509 mBatteryStatsService.enforceCallingPermission(); 10510 PendingIntentRecord rec = (PendingIntentRecord)sender; 10511 int MY_UID = Binder.getCallingUid(); 10512 int uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid; 10513 BatteryStatsImpl.Uid.Pkg pkg = 10514 stats.getPackageStatsLocked(sourceUid >= 0 ? sourceUid : uid, 10515 sourcePkg != null ? sourcePkg : rec.key.packageName); 10516 pkg.incWakeupsLocked(); 10517 } 10518 } 10519 } 10520 10521 public boolean killPids(int[] pids, String pReason, boolean secure) { 10522 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10523 throw new SecurityException("killPids only available to the system"); 10524 } 10525 String reason = (pReason == null) ? "Unknown" : pReason; 10526 // XXX Note: don't acquire main activity lock here, because the window 10527 // manager calls in with its locks held. 10528 10529 boolean killed = false; 10530 synchronized (mPidsSelfLocked) { 10531 int[] types = new int[pids.length]; 10532 int worstType = 0; 10533 for (int i=0; i<pids.length; i++) { 10534 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 10535 if (proc != null) { 10536 int type = proc.setAdj; 10537 types[i] = type; 10538 if (type > worstType) { 10539 worstType = type; 10540 } 10541 } 10542 } 10543 10544 // If the worst oom_adj is somewhere in the cached proc LRU range, 10545 // then constrain it so we will kill all cached procs. 10546 if (worstType < ProcessList.CACHED_APP_MAX_ADJ 10547 && worstType > ProcessList.CACHED_APP_MIN_ADJ) { 10548 worstType = ProcessList.CACHED_APP_MIN_ADJ; 10549 } 10550 10551 // If this is not a secure call, don't let it kill processes that 10552 // are important. 10553 if (!secure && worstType < ProcessList.SERVICE_ADJ) { 10554 worstType = ProcessList.SERVICE_ADJ; 10555 } 10556 10557 Slog.w(TAG, "Killing processes " + reason + " at adjustment " + worstType); 10558 for (int i=0; i<pids.length; i++) { 10559 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 10560 if (proc == null) { 10561 continue; 10562 } 10563 int adj = proc.setAdj; 10564 if (adj >= worstType && !proc.killedByAm) { 10565 proc.kill(reason, true); 10566 killed = true; 10567 } 10568 } 10569 } 10570 return killed; 10571 } 10572 10573 @Override 10574 public void killUid(int uid, String reason) { 10575 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10576 throw new SecurityException("killUid only available to the system"); 10577 } 10578 synchronized (this) { 10579 killPackageProcessesLocked(null, UserHandle.getAppId(uid), UserHandle.getUserId(uid), 10580 ProcessList.FOREGROUND_APP_ADJ-1, false, true, true, false, 10581 reason != null ? reason : "kill uid"); 10582 } 10583 } 10584 10585 @Override 10586 public boolean killProcessesBelowForeground(String reason) { 10587 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10588 throw new SecurityException("killProcessesBelowForeground() only available to system"); 10589 } 10590 10591 return killProcessesBelowAdj(ProcessList.FOREGROUND_APP_ADJ, reason); 10592 } 10593 10594 private boolean killProcessesBelowAdj(int belowAdj, String reason) { 10595 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10596 throw new SecurityException("killProcessesBelowAdj() only available to system"); 10597 } 10598 10599 boolean killed = false; 10600 synchronized (mPidsSelfLocked) { 10601 final int size = mPidsSelfLocked.size(); 10602 for (int i = 0; i < size; i++) { 10603 final int pid = mPidsSelfLocked.keyAt(i); 10604 final ProcessRecord proc = mPidsSelfLocked.valueAt(i); 10605 if (proc == null) continue; 10606 10607 final int adj = proc.setAdj; 10608 if (adj > belowAdj && !proc.killedByAm) { 10609 proc.kill(reason, true); 10610 killed = true; 10611 } 10612 } 10613 } 10614 return killed; 10615 } 10616 10617 @Override 10618 public void hang(final IBinder who, boolean allowRestart) { 10619 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 10620 != PackageManager.PERMISSION_GRANTED) { 10621 throw new SecurityException("Requires permission " 10622 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 10623 } 10624 10625 final IBinder.DeathRecipient death = new DeathRecipient() { 10626 @Override 10627 public void binderDied() { 10628 synchronized (this) { 10629 notifyAll(); 10630 } 10631 } 10632 }; 10633 10634 try { 10635 who.linkToDeath(death, 0); 10636 } catch (RemoteException e) { 10637 Slog.w(TAG, "hang: given caller IBinder is already dead."); 10638 return; 10639 } 10640 10641 synchronized (this) { 10642 Watchdog.getInstance().setAllowRestart(allowRestart); 10643 Slog.i(TAG, "Hanging system process at request of pid " + Binder.getCallingPid()); 10644 synchronized (death) { 10645 while (who.isBinderAlive()) { 10646 try { 10647 death.wait(); 10648 } catch (InterruptedException e) { 10649 } 10650 } 10651 } 10652 Watchdog.getInstance().setAllowRestart(true); 10653 } 10654 } 10655 10656 @Override 10657 public void restart() { 10658 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 10659 != PackageManager.PERMISSION_GRANTED) { 10660 throw new SecurityException("Requires permission " 10661 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 10662 } 10663 10664 Log.i(TAG, "Sending shutdown broadcast..."); 10665 10666 BroadcastReceiver br = new BroadcastReceiver() { 10667 @Override public void onReceive(Context context, Intent intent) { 10668 // Now the broadcast is done, finish up the low-level shutdown. 10669 Log.i(TAG, "Shutting down activity manager..."); 10670 shutdown(10000); 10671 Log.i(TAG, "Shutdown complete, restarting!"); 10672 Process.killProcess(Process.myPid()); 10673 System.exit(10); 10674 } 10675 }; 10676 10677 // First send the high-level shut down broadcast. 10678 Intent intent = new Intent(Intent.ACTION_SHUTDOWN); 10679 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 10680 intent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 10681 /* For now we are not doing a clean shutdown, because things seem to get unhappy. 10682 mContext.sendOrderedBroadcastAsUser(intent, 10683 UserHandle.ALL, null, br, mHandler, 0, null, null); 10684 */ 10685 br.onReceive(mContext, intent); 10686 } 10687 10688 private long getLowRamTimeSinceIdle(long now) { 10689 return mLowRamTimeSinceLastIdle + (mLowRamStartTime > 0 ? (now-mLowRamStartTime) : 0); 10690 } 10691 10692 @Override 10693 public void performIdleMaintenance() { 10694 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 10695 != PackageManager.PERMISSION_GRANTED) { 10696 throw new SecurityException("Requires permission " 10697 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 10698 } 10699 10700 synchronized (this) { 10701 final long now = SystemClock.uptimeMillis(); 10702 final long timeSinceLastIdle = now - mLastIdleTime; 10703 final long lowRamSinceLastIdle = getLowRamTimeSinceIdle(now); 10704 mLastIdleTime = now; 10705 mLowRamTimeSinceLastIdle = 0; 10706 if (mLowRamStartTime != 0) { 10707 mLowRamStartTime = now; 10708 } 10709 10710 StringBuilder sb = new StringBuilder(128); 10711 sb.append("Idle maintenance over "); 10712 TimeUtils.formatDuration(timeSinceLastIdle, sb); 10713 sb.append(" low RAM for "); 10714 TimeUtils.formatDuration(lowRamSinceLastIdle, sb); 10715 Slog.i(TAG, sb.toString()); 10716 10717 // If at least 1/3 of our time since the last idle period has been spent 10718 // with RAM low, then we want to kill processes. 10719 boolean doKilling = lowRamSinceLastIdle > (timeSinceLastIdle/3); 10720 10721 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 10722 ProcessRecord proc = mLruProcesses.get(i); 10723 if (proc.notCachedSinceIdle) { 10724 if (proc.setProcState > ActivityManager.PROCESS_STATE_TOP 10725 && proc.setProcState <= ActivityManager.PROCESS_STATE_SERVICE) { 10726 if (doKilling && proc.initialIdlePss != 0 10727 && proc.lastPss > ((proc.initialIdlePss*3)/2)) { 10728 proc.kill("idle maint (pss " + proc.lastPss 10729 + " from " + proc.initialIdlePss + ")", true); 10730 } 10731 } 10732 } else if (proc.setProcState < ActivityManager.PROCESS_STATE_HOME) { 10733 proc.notCachedSinceIdle = true; 10734 proc.initialIdlePss = 0; 10735 proc.nextPssTime = ProcessList.computeNextPssTime(proc.curProcState, true, 10736 isSleeping(), now); 10737 } 10738 } 10739 10740 mHandler.removeMessages(REQUEST_ALL_PSS_MSG); 10741 mHandler.sendEmptyMessageDelayed(REQUEST_ALL_PSS_MSG, 2*60*1000); 10742 } 10743 } 10744 10745 private void retrieveSettings() { 10746 final ContentResolver resolver = mContext.getContentResolver(); 10747 String debugApp = Settings.Global.getString( 10748 resolver, Settings.Global.DEBUG_APP); 10749 boolean waitForDebugger = Settings.Global.getInt( 10750 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 0) != 0; 10751 boolean alwaysFinishActivities = Settings.Global.getInt( 10752 resolver, Settings.Global.ALWAYS_FINISH_ACTIVITIES, 0) != 0; 10753 boolean forceRtl = Settings.Global.getInt( 10754 resolver, Settings.Global.DEVELOPMENT_FORCE_RTL, 0) != 0; 10755 // Transfer any global setting for forcing RTL layout, into a System Property 10756 SystemProperties.set(Settings.Global.DEVELOPMENT_FORCE_RTL, forceRtl ? "1":"0"); 10757 10758 Configuration configuration = new Configuration(); 10759 Settings.System.getConfiguration(resolver, configuration); 10760 if (forceRtl) { 10761 // This will take care of setting the correct layout direction flags 10762 configuration.setLayoutDirection(configuration.locale); 10763 } 10764 10765 synchronized (this) { 10766 mDebugApp = mOrigDebugApp = debugApp; 10767 mWaitForDebugger = mOrigWaitForDebugger = waitForDebugger; 10768 mAlwaysFinishActivities = alwaysFinishActivities; 10769 // This happens before any activities are started, so we can 10770 // change mConfiguration in-place. 10771 updateConfigurationLocked(configuration, null, false, true); 10772 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Initial config: " + mConfiguration); 10773 } 10774 } 10775 10776 /** Loads resources after the current configuration has been set. */ 10777 private void loadResourcesOnSystemReady() { 10778 final Resources res = mContext.getResources(); 10779 mHasRecents = res.getBoolean(com.android.internal.R.bool.config_hasRecents); 10780 mThumbnailWidth = res.getDimensionPixelSize(com.android.internal.R.dimen.thumbnail_width); 10781 mThumbnailHeight = res.getDimensionPixelSize(com.android.internal.R.dimen.thumbnail_height); 10782 } 10783 10784 public boolean testIsSystemReady() { 10785 // no need to synchronize(this) just to read & return the value 10786 return mSystemReady; 10787 } 10788 10789 private static File getCalledPreBootReceiversFile() { 10790 File dataDir = Environment.getDataDirectory(); 10791 File systemDir = new File(dataDir, "system"); 10792 File fname = new File(systemDir, CALLED_PRE_BOOTS_FILENAME); 10793 return fname; 10794 } 10795 10796 private static ArrayList<ComponentName> readLastDonePreBootReceivers() { 10797 ArrayList<ComponentName> lastDoneReceivers = new ArrayList<ComponentName>(); 10798 File file = getCalledPreBootReceiversFile(); 10799 FileInputStream fis = null; 10800 try { 10801 fis = new FileInputStream(file); 10802 DataInputStream dis = new DataInputStream(new BufferedInputStream(fis, 2048)); 10803 int fvers = dis.readInt(); 10804 if (fvers == LAST_PREBOOT_DELIVERED_FILE_VERSION) { 10805 String vers = dis.readUTF(); 10806 String codename = dis.readUTF(); 10807 String build = dis.readUTF(); 10808 if (android.os.Build.VERSION.RELEASE.equals(vers) 10809 && android.os.Build.VERSION.CODENAME.equals(codename) 10810 && android.os.Build.VERSION.INCREMENTAL.equals(build)) { 10811 int num = dis.readInt(); 10812 while (num > 0) { 10813 num--; 10814 String pkg = dis.readUTF(); 10815 String cls = dis.readUTF(); 10816 lastDoneReceivers.add(new ComponentName(pkg, cls)); 10817 } 10818 } 10819 } 10820 } catch (FileNotFoundException e) { 10821 } catch (IOException e) { 10822 Slog.w(TAG, "Failure reading last done pre-boot receivers", e); 10823 } finally { 10824 if (fis != null) { 10825 try { 10826 fis.close(); 10827 } catch (IOException e) { 10828 } 10829 } 10830 } 10831 return lastDoneReceivers; 10832 } 10833 10834 private static void writeLastDonePreBootReceivers(ArrayList<ComponentName> list) { 10835 File file = getCalledPreBootReceiversFile(); 10836 FileOutputStream fos = null; 10837 DataOutputStream dos = null; 10838 try { 10839 fos = new FileOutputStream(file); 10840 dos = new DataOutputStream(new BufferedOutputStream(fos, 2048)); 10841 dos.writeInt(LAST_PREBOOT_DELIVERED_FILE_VERSION); 10842 dos.writeUTF(android.os.Build.VERSION.RELEASE); 10843 dos.writeUTF(android.os.Build.VERSION.CODENAME); 10844 dos.writeUTF(android.os.Build.VERSION.INCREMENTAL); 10845 dos.writeInt(list.size()); 10846 for (int i=0; i<list.size(); i++) { 10847 dos.writeUTF(list.get(i).getPackageName()); 10848 dos.writeUTF(list.get(i).getClassName()); 10849 } 10850 } catch (IOException e) { 10851 Slog.w(TAG, "Failure writing last done pre-boot receivers", e); 10852 file.delete(); 10853 } finally { 10854 FileUtils.sync(fos); 10855 if (dos != null) { 10856 try { 10857 dos.close(); 10858 } catch (IOException e) { 10859 // TODO Auto-generated catch block 10860 e.printStackTrace(); 10861 } 10862 } 10863 } 10864 } 10865 10866 private boolean deliverPreBootCompleted(final Runnable onFinishCallback, 10867 ArrayList<ComponentName> doneReceivers, int userId) { 10868 boolean waitingUpdate = false; 10869 Intent intent = new Intent(Intent.ACTION_PRE_BOOT_COMPLETED); 10870 List<ResolveInfo> ris = null; 10871 try { 10872 ris = AppGlobals.getPackageManager().queryIntentReceivers( 10873 intent, null, 0, userId); 10874 } catch (RemoteException e) { 10875 } 10876 if (ris != null) { 10877 for (int i=ris.size()-1; i>=0; i--) { 10878 if ((ris.get(i).activityInfo.applicationInfo.flags 10879 &ApplicationInfo.FLAG_SYSTEM) == 0) { 10880 ris.remove(i); 10881 } 10882 } 10883 intent.addFlags(Intent.FLAG_RECEIVER_BOOT_UPGRADE); 10884 10885 // For User 0, load the version number. When delivering to a new user, deliver 10886 // to all receivers. 10887 if (userId == UserHandle.USER_OWNER) { 10888 ArrayList<ComponentName> lastDoneReceivers = readLastDonePreBootReceivers(); 10889 for (int i=0; i<ris.size(); i++) { 10890 ActivityInfo ai = ris.get(i).activityInfo; 10891 ComponentName comp = new ComponentName(ai.packageName, ai.name); 10892 if (lastDoneReceivers.contains(comp)) { 10893 // We already did the pre boot receiver for this app with the current 10894 // platform version, so don't do it again... 10895 ris.remove(i); 10896 i--; 10897 // ...however, do keep it as one that has been done, so we don't 10898 // forget about it when rewriting the file of last done receivers. 10899 doneReceivers.add(comp); 10900 } 10901 } 10902 } 10903 10904 // If primary user, send broadcast to all available users, else just to userId 10905 final int[] users = userId == UserHandle.USER_OWNER ? getUsersLocked() 10906 : new int[] { userId }; 10907 for (int i = 0; i < ris.size(); i++) { 10908 ActivityInfo ai = ris.get(i).activityInfo; 10909 ComponentName comp = new ComponentName(ai.packageName, ai.name); 10910 doneReceivers.add(comp); 10911 intent.setComponent(comp); 10912 for (int j=0; j<users.length; j++) { 10913 IIntentReceiver finisher = null; 10914 // On last receiver and user, set up a completion callback 10915 if (i == ris.size() - 1 && j == users.length - 1 && onFinishCallback != null) { 10916 finisher = new IIntentReceiver.Stub() { 10917 public void performReceive(Intent intent, int resultCode, 10918 String data, Bundle extras, boolean ordered, 10919 boolean sticky, int sendingUser) { 10920 // The raw IIntentReceiver interface is called 10921 // with the AM lock held, so redispatch to 10922 // execute our code without the lock. 10923 mHandler.post(onFinishCallback); 10924 } 10925 }; 10926 } 10927 Slog.i(TAG, "Sending system update to " + intent.getComponent() 10928 + " for user " + users[j]); 10929 broadcastIntentLocked(null, null, intent, null, finisher, 10930 0, null, null, null, AppOpsManager.OP_NONE, 10931 true, false, MY_PID, Process.SYSTEM_UID, 10932 users[j]); 10933 if (finisher != null) { 10934 waitingUpdate = true; 10935 } 10936 } 10937 } 10938 } 10939 10940 return waitingUpdate; 10941 } 10942 10943 public void systemReady(final Runnable goingCallback) { 10944 synchronized(this) { 10945 if (mSystemReady) { 10946 // If we're done calling all the receivers, run the next "boot phase" passed in 10947 // by the SystemServer 10948 if (goingCallback != null) { 10949 goingCallback.run(); 10950 } 10951 return; 10952 } 10953 10954 // Make sure we have the current profile info, since it is needed for 10955 // security checks. 10956 updateCurrentProfileIdsLocked(); 10957 10958 if (mRecentTasks == null) { 10959 mRecentTasks = mTaskPersister.restoreTasksLocked(); 10960 if (!mRecentTasks.isEmpty()) { 10961 mStackSupervisor.createStackForRestoredTaskHistory(mRecentTasks); 10962 } 10963 cleanupRecentTasksLocked(UserHandle.USER_ALL); 10964 mTaskPersister.startPersisting(); 10965 } 10966 10967 // Check to see if there are any update receivers to run. 10968 if (!mDidUpdate) { 10969 if (mWaitingUpdate) { 10970 return; 10971 } 10972 final ArrayList<ComponentName> doneReceivers = new ArrayList<ComponentName>(); 10973 mWaitingUpdate = deliverPreBootCompleted(new Runnable() { 10974 public void run() { 10975 synchronized (ActivityManagerService.this) { 10976 mDidUpdate = true; 10977 } 10978 writeLastDonePreBootReceivers(doneReceivers); 10979 showBootMessage(mContext.getText( 10980 R.string.android_upgrading_complete), 10981 false); 10982 systemReady(goingCallback); 10983 } 10984 }, doneReceivers, UserHandle.USER_OWNER); 10985 10986 if (mWaitingUpdate) { 10987 return; 10988 } 10989 mDidUpdate = true; 10990 } 10991 10992 mAppOpsService.systemReady(); 10993 mSystemReady = true; 10994 } 10995 10996 ArrayList<ProcessRecord> procsToKill = null; 10997 synchronized(mPidsSelfLocked) { 10998 for (int i=mPidsSelfLocked.size()-1; i>=0; i--) { 10999 ProcessRecord proc = mPidsSelfLocked.valueAt(i); 11000 if (!isAllowedWhileBooting(proc.info)){ 11001 if (procsToKill == null) { 11002 procsToKill = new ArrayList<ProcessRecord>(); 11003 } 11004 procsToKill.add(proc); 11005 } 11006 } 11007 } 11008 11009 synchronized(this) { 11010 if (procsToKill != null) { 11011 for (int i=procsToKill.size()-1; i>=0; i--) { 11012 ProcessRecord proc = procsToKill.get(i); 11013 Slog.i(TAG, "Removing system update proc: " + proc); 11014 removeProcessLocked(proc, true, false, "system update done"); 11015 } 11016 } 11017 11018 // Now that we have cleaned up any update processes, we 11019 // are ready to start launching real processes and know that 11020 // we won't trample on them any more. 11021 mProcessesReady = true; 11022 } 11023 11024 Slog.i(TAG, "System now ready"); 11025 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_AMS_READY, 11026 SystemClock.uptimeMillis()); 11027 11028 synchronized(this) { 11029 // Make sure we have no pre-ready processes sitting around. 11030 11031 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) { 11032 ResolveInfo ri = mContext.getPackageManager() 11033 .resolveActivity(new Intent(Intent.ACTION_FACTORY_TEST), 11034 STOCK_PM_FLAGS); 11035 CharSequence errorMsg = null; 11036 if (ri != null) { 11037 ActivityInfo ai = ri.activityInfo; 11038 ApplicationInfo app = ai.applicationInfo; 11039 if ((app.flags&ApplicationInfo.FLAG_SYSTEM) != 0) { 11040 mTopAction = Intent.ACTION_FACTORY_TEST; 11041 mTopData = null; 11042 mTopComponent = new ComponentName(app.packageName, 11043 ai.name); 11044 } else { 11045 errorMsg = mContext.getResources().getText( 11046 com.android.internal.R.string.factorytest_not_system); 11047 } 11048 } else { 11049 errorMsg = mContext.getResources().getText( 11050 com.android.internal.R.string.factorytest_no_action); 11051 } 11052 if (errorMsg != null) { 11053 mTopAction = null; 11054 mTopData = null; 11055 mTopComponent = null; 11056 Message msg = Message.obtain(); 11057 msg.what = SHOW_FACTORY_ERROR_MSG; 11058 msg.getData().putCharSequence("msg", errorMsg); 11059 mHandler.sendMessage(msg); 11060 } 11061 } 11062 } 11063 11064 retrieveSettings(); 11065 loadResourcesOnSystemReady(); 11066 11067 synchronized (this) { 11068 readGrantedUriPermissionsLocked(); 11069 } 11070 11071 if (goingCallback != null) goingCallback.run(); 11072 11073 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 11074 Integer.toString(mCurrentUserId), mCurrentUserId); 11075 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 11076 Integer.toString(mCurrentUserId), mCurrentUserId); 11077 mSystemServiceManager.startUser(mCurrentUserId); 11078 11079 synchronized (this) { 11080 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 11081 try { 11082 List apps = AppGlobals.getPackageManager(). 11083 getPersistentApplications(STOCK_PM_FLAGS); 11084 if (apps != null) { 11085 int N = apps.size(); 11086 int i; 11087 for (i=0; i<N; i++) { 11088 ApplicationInfo info 11089 = (ApplicationInfo)apps.get(i); 11090 if (info != null && 11091 !info.packageName.equals("android")) { 11092 addAppLocked(info, false, null /* ABI override */); 11093 } 11094 } 11095 } 11096 } catch (RemoteException ex) { 11097 // pm is in same process, this will never happen. 11098 } 11099 } 11100 11101 // Start up initial activity. 11102 mBooting = true; 11103 11104 try { 11105 if (AppGlobals.getPackageManager().hasSystemUidErrors()) { 11106 Message msg = Message.obtain(); 11107 msg.what = SHOW_UID_ERROR_MSG; 11108 mHandler.sendMessage(msg); 11109 } 11110 } catch (RemoteException e) { 11111 } 11112 11113 long ident = Binder.clearCallingIdentity(); 11114 try { 11115 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 11116 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 11117 | Intent.FLAG_RECEIVER_FOREGROUND); 11118 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 11119 broadcastIntentLocked(null, null, intent, 11120 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 11121 false, false, MY_PID, Process.SYSTEM_UID, mCurrentUserId); 11122 intent = new Intent(Intent.ACTION_USER_STARTING); 11123 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 11124 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 11125 broadcastIntentLocked(null, null, intent, 11126 null, new IIntentReceiver.Stub() { 11127 @Override 11128 public void performReceive(Intent intent, int resultCode, String data, 11129 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 11130 throws RemoteException { 11131 } 11132 }, 0, null, null, 11133 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 11134 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 11135 } catch (Throwable t) { 11136 Slog.wtf(TAG, "Failed sending first user broadcasts", t); 11137 } finally { 11138 Binder.restoreCallingIdentity(ident); 11139 } 11140 mStackSupervisor.resumeTopActivitiesLocked(); 11141 sendUserSwitchBroadcastsLocked(-1, mCurrentUserId); 11142 } 11143 } 11144 11145 private boolean makeAppCrashingLocked(ProcessRecord app, 11146 String shortMsg, String longMsg, String stackTrace) { 11147 app.crashing = true; 11148 app.crashingReport = generateProcessError(app, 11149 ActivityManager.ProcessErrorStateInfo.CRASHED, null, shortMsg, longMsg, stackTrace); 11150 startAppProblemLocked(app); 11151 app.stopFreezingAllLocked(); 11152 return handleAppCrashLocked(app, shortMsg, longMsg, stackTrace); 11153 } 11154 11155 private void makeAppNotRespondingLocked(ProcessRecord app, 11156 String activity, String shortMsg, String longMsg) { 11157 app.notResponding = true; 11158 app.notRespondingReport = generateProcessError(app, 11159 ActivityManager.ProcessErrorStateInfo.NOT_RESPONDING, 11160 activity, shortMsg, longMsg, null); 11161 startAppProblemLocked(app); 11162 app.stopFreezingAllLocked(); 11163 } 11164 11165 /** 11166 * Generate a process error record, suitable for attachment to a ProcessRecord. 11167 * 11168 * @param app The ProcessRecord in which the error occurred. 11169 * @param condition Crashing, Application Not Responding, etc. Values are defined in 11170 * ActivityManager.AppErrorStateInfo 11171 * @param activity The activity associated with the crash, if known. 11172 * @param shortMsg Short message describing the crash. 11173 * @param longMsg Long message describing the crash. 11174 * @param stackTrace Full crash stack trace, may be null. 11175 * 11176 * @return Returns a fully-formed AppErrorStateInfo record. 11177 */ 11178 private ActivityManager.ProcessErrorStateInfo generateProcessError(ProcessRecord app, 11179 int condition, String activity, String shortMsg, String longMsg, String stackTrace) { 11180 ActivityManager.ProcessErrorStateInfo report = new ActivityManager.ProcessErrorStateInfo(); 11181 11182 report.condition = condition; 11183 report.processName = app.processName; 11184 report.pid = app.pid; 11185 report.uid = app.info.uid; 11186 report.tag = activity; 11187 report.shortMsg = shortMsg; 11188 report.longMsg = longMsg; 11189 report.stackTrace = stackTrace; 11190 11191 return report; 11192 } 11193 11194 void killAppAtUsersRequest(ProcessRecord app, Dialog fromDialog) { 11195 synchronized (this) { 11196 app.crashing = false; 11197 app.crashingReport = null; 11198 app.notResponding = false; 11199 app.notRespondingReport = null; 11200 if (app.anrDialog == fromDialog) { 11201 app.anrDialog = null; 11202 } 11203 if (app.waitDialog == fromDialog) { 11204 app.waitDialog = null; 11205 } 11206 if (app.pid > 0 && app.pid != MY_PID) { 11207 handleAppCrashLocked(app, null, null, null); 11208 app.kill("user request after error", true); 11209 } 11210 } 11211 } 11212 11213 private boolean handleAppCrashLocked(ProcessRecord app, String shortMsg, String longMsg, 11214 String stackTrace) { 11215 long now = SystemClock.uptimeMillis(); 11216 11217 Long crashTime; 11218 if (!app.isolated) { 11219 crashTime = mProcessCrashTimes.get(app.info.processName, app.uid); 11220 } else { 11221 crashTime = null; 11222 } 11223 if (crashTime != null && now < crashTime+ProcessList.MIN_CRASH_INTERVAL) { 11224 // This process loses! 11225 Slog.w(TAG, "Process " + app.info.processName 11226 + " has crashed too many times: killing!"); 11227 EventLog.writeEvent(EventLogTags.AM_PROCESS_CRASHED_TOO_MUCH, 11228 app.userId, app.info.processName, app.uid); 11229 mStackSupervisor.handleAppCrashLocked(app); 11230 if (!app.persistent) { 11231 // We don't want to start this process again until the user 11232 // explicitly does so... but for persistent process, we really 11233 // need to keep it running. If a persistent process is actually 11234 // repeatedly crashing, then badness for everyone. 11235 EventLog.writeEvent(EventLogTags.AM_PROC_BAD, app.userId, app.uid, 11236 app.info.processName); 11237 if (!app.isolated) { 11238 // XXX We don't have a way to mark isolated processes 11239 // as bad, since they don't have a peristent identity. 11240 mBadProcesses.put(app.info.processName, app.uid, 11241 new BadProcessInfo(now, shortMsg, longMsg, stackTrace)); 11242 mProcessCrashTimes.remove(app.info.processName, app.uid); 11243 } 11244 app.bad = true; 11245 app.removed = true; 11246 // Don't let services in this process be restarted and potentially 11247 // annoy the user repeatedly. Unless it is persistent, since those 11248 // processes run critical code. 11249 removeProcessLocked(app, false, false, "crash"); 11250 mStackSupervisor.resumeTopActivitiesLocked(); 11251 return false; 11252 } 11253 mStackSupervisor.resumeTopActivitiesLocked(); 11254 } else { 11255 mStackSupervisor.finishTopRunningActivityLocked(app); 11256 } 11257 11258 // Bump up the crash count of any services currently running in the proc. 11259 for (int i=app.services.size()-1; i>=0; i--) { 11260 // Any services running in the application need to be placed 11261 // back in the pending list. 11262 ServiceRecord sr = app.services.valueAt(i); 11263 sr.crashCount++; 11264 } 11265 11266 // If the crashing process is what we consider to be the "home process" and it has been 11267 // replaced by a third-party app, clear the package preferred activities from packages 11268 // with a home activity running in the process to prevent a repeatedly crashing app 11269 // from blocking the user to manually clear the list. 11270 final ArrayList<ActivityRecord> activities = app.activities; 11271 if (app == mHomeProcess && activities.size() > 0 11272 && (mHomeProcess.info.flags & ApplicationInfo.FLAG_SYSTEM) == 0) { 11273 for (int activityNdx = activities.size() - 1; activityNdx >= 0; --activityNdx) { 11274 final ActivityRecord r = activities.get(activityNdx); 11275 if (r.isHomeActivity()) { 11276 Log.i(TAG, "Clearing package preferred activities from " + r.packageName); 11277 try { 11278 ActivityThread.getPackageManager() 11279 .clearPackagePreferredActivities(r.packageName); 11280 } catch (RemoteException c) { 11281 // pm is in same process, this will never happen. 11282 } 11283 } 11284 } 11285 } 11286 11287 if (!app.isolated) { 11288 // XXX Can't keep track of crash times for isolated processes, 11289 // because they don't have a perisistent identity. 11290 mProcessCrashTimes.put(app.info.processName, app.uid, now); 11291 } 11292 11293 if (app.crashHandler != null) mHandler.post(app.crashHandler); 11294 return true; 11295 } 11296 11297 void startAppProblemLocked(ProcessRecord app) { 11298 // If this app is not running under the current user, then we 11299 // can't give it a report button because that would require 11300 // launching the report UI under a different user. 11301 app.errorReportReceiver = null; 11302 11303 for (int userId : mCurrentProfileIds) { 11304 if (app.userId == userId) { 11305 app.errorReportReceiver = ApplicationErrorReport.getErrorReportReceiver( 11306 mContext, app.info.packageName, app.info.flags); 11307 } 11308 } 11309 skipCurrentReceiverLocked(app); 11310 } 11311 11312 void skipCurrentReceiverLocked(ProcessRecord app) { 11313 for (BroadcastQueue queue : mBroadcastQueues) { 11314 queue.skipCurrentReceiverLocked(app); 11315 } 11316 } 11317 11318 /** 11319 * Used by {@link com.android.internal.os.RuntimeInit} to report when an application crashes. 11320 * The application process will exit immediately after this call returns. 11321 * @param app object of the crashing app, null for the system server 11322 * @param crashInfo describing the exception 11323 */ 11324 public void handleApplicationCrash(IBinder app, ApplicationErrorReport.CrashInfo crashInfo) { 11325 ProcessRecord r = findAppProcess(app, "Crash"); 11326 final String processName = app == null ? "system_server" 11327 : (r == null ? "unknown" : r.processName); 11328 11329 handleApplicationCrashInner("crash", r, processName, crashInfo); 11330 } 11331 11332 /* Native crash reporting uses this inner version because it needs to be somewhat 11333 * decoupled from the AM-managed cleanup lifecycle 11334 */ 11335 void handleApplicationCrashInner(String eventType, ProcessRecord r, String processName, 11336 ApplicationErrorReport.CrashInfo crashInfo) { 11337 EventLog.writeEvent(EventLogTags.AM_CRASH, Binder.getCallingPid(), 11338 UserHandle.getUserId(Binder.getCallingUid()), processName, 11339 r == null ? -1 : r.info.flags, 11340 crashInfo.exceptionClassName, 11341 crashInfo.exceptionMessage, 11342 crashInfo.throwFileName, 11343 crashInfo.throwLineNumber); 11344 11345 addErrorToDropBox(eventType, r, processName, null, null, null, null, null, crashInfo); 11346 11347 crashApplication(r, crashInfo); 11348 } 11349 11350 public void handleApplicationStrictModeViolation( 11351 IBinder app, 11352 int violationMask, 11353 StrictMode.ViolationInfo info) { 11354 ProcessRecord r = findAppProcess(app, "StrictMode"); 11355 if (r == null) { 11356 return; 11357 } 11358 11359 if ((violationMask & StrictMode.PENALTY_DROPBOX) != 0) { 11360 Integer stackFingerprint = info.hashCode(); 11361 boolean logIt = true; 11362 synchronized (mAlreadyLoggedViolatedStacks) { 11363 if (mAlreadyLoggedViolatedStacks.contains(stackFingerprint)) { 11364 logIt = false; 11365 // TODO: sub-sample into EventLog for these, with 11366 // the info.durationMillis? Then we'd get 11367 // the relative pain numbers, without logging all 11368 // the stack traces repeatedly. We'd want to do 11369 // likewise in the client code, which also does 11370 // dup suppression, before the Binder call. 11371 } else { 11372 if (mAlreadyLoggedViolatedStacks.size() >= MAX_DUP_SUPPRESSED_STACKS) { 11373 mAlreadyLoggedViolatedStacks.clear(); 11374 } 11375 mAlreadyLoggedViolatedStacks.add(stackFingerprint); 11376 } 11377 } 11378 if (logIt) { 11379 logStrictModeViolationToDropBox(r, info); 11380 } 11381 } 11382 11383 if ((violationMask & StrictMode.PENALTY_DIALOG) != 0) { 11384 AppErrorResult result = new AppErrorResult(); 11385 synchronized (this) { 11386 final long origId = Binder.clearCallingIdentity(); 11387 11388 Message msg = Message.obtain(); 11389 msg.what = SHOW_STRICT_MODE_VIOLATION_MSG; 11390 HashMap<String, Object> data = new HashMap<String, Object>(); 11391 data.put("result", result); 11392 data.put("app", r); 11393 data.put("violationMask", violationMask); 11394 data.put("info", info); 11395 msg.obj = data; 11396 mHandler.sendMessage(msg); 11397 11398 Binder.restoreCallingIdentity(origId); 11399 } 11400 int res = result.get(); 11401 Slog.w(TAG, "handleApplicationStrictModeViolation; res=" + res); 11402 } 11403 } 11404 11405 // Depending on the policy in effect, there could be a bunch of 11406 // these in quick succession so we try to batch these together to 11407 // minimize disk writes, number of dropbox entries, and maximize 11408 // compression, by having more fewer, larger records. 11409 private void logStrictModeViolationToDropBox( 11410 ProcessRecord process, 11411 StrictMode.ViolationInfo info) { 11412 if (info == null) { 11413 return; 11414 } 11415 final boolean isSystemApp = process == null || 11416 (process.info.flags & (ApplicationInfo.FLAG_SYSTEM | 11417 ApplicationInfo.FLAG_UPDATED_SYSTEM_APP)) != 0; 11418 final String processName = process == null ? "unknown" : process.processName; 11419 final String dropboxTag = isSystemApp ? "system_app_strictmode" : "data_app_strictmode"; 11420 final DropBoxManager dbox = (DropBoxManager) 11421 mContext.getSystemService(Context.DROPBOX_SERVICE); 11422 11423 // Exit early if the dropbox isn't configured to accept this report type. 11424 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 11425 11426 boolean bufferWasEmpty; 11427 boolean needsFlush; 11428 final StringBuilder sb = isSystemApp ? mStrictModeBuffer : new StringBuilder(1024); 11429 synchronized (sb) { 11430 bufferWasEmpty = sb.length() == 0; 11431 appendDropBoxProcessHeaders(process, processName, sb); 11432 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 11433 sb.append("System-App: ").append(isSystemApp).append("\n"); 11434 sb.append("Uptime-Millis: ").append(info.violationUptimeMillis).append("\n"); 11435 if (info.violationNumThisLoop != 0) { 11436 sb.append("Loop-Violation-Number: ").append(info.violationNumThisLoop).append("\n"); 11437 } 11438 if (info.numAnimationsRunning != 0) { 11439 sb.append("Animations-Running: ").append(info.numAnimationsRunning).append("\n"); 11440 } 11441 if (info.broadcastIntentAction != null) { 11442 sb.append("Broadcast-Intent-Action: ").append(info.broadcastIntentAction).append("\n"); 11443 } 11444 if (info.durationMillis != -1) { 11445 sb.append("Duration-Millis: ").append(info.durationMillis).append("\n"); 11446 } 11447 if (info.numInstances != -1) { 11448 sb.append("Instance-Count: ").append(info.numInstances).append("\n"); 11449 } 11450 if (info.tags != null) { 11451 for (String tag : info.tags) { 11452 sb.append("Span-Tag: ").append(tag).append("\n"); 11453 } 11454 } 11455 sb.append("\n"); 11456 if (info.crashInfo != null && info.crashInfo.stackTrace != null) { 11457 sb.append(info.crashInfo.stackTrace); 11458 } 11459 sb.append("\n"); 11460 11461 // Only buffer up to ~64k. Various logging bits truncate 11462 // things at 128k. 11463 needsFlush = (sb.length() > 64 * 1024); 11464 } 11465 11466 // Flush immediately if the buffer's grown too large, or this 11467 // is a non-system app. Non-system apps are isolated with a 11468 // different tag & policy and not batched. 11469 // 11470 // Batching is useful during internal testing with 11471 // StrictMode settings turned up high. Without batching, 11472 // thousands of separate files could be created on boot. 11473 if (!isSystemApp || needsFlush) { 11474 new Thread("Error dump: " + dropboxTag) { 11475 @Override 11476 public void run() { 11477 String report; 11478 synchronized (sb) { 11479 report = sb.toString(); 11480 sb.delete(0, sb.length()); 11481 sb.trimToSize(); 11482 } 11483 if (report.length() != 0) { 11484 dbox.addText(dropboxTag, report); 11485 } 11486 } 11487 }.start(); 11488 return; 11489 } 11490 11491 // System app batching: 11492 if (!bufferWasEmpty) { 11493 // An existing dropbox-writing thread is outstanding, so 11494 // we don't need to start it up. The existing thread will 11495 // catch the buffer appends we just did. 11496 return; 11497 } 11498 11499 // Worker thread to both batch writes and to avoid blocking the caller on I/O. 11500 // (After this point, we shouldn't access AMS internal data structures.) 11501 new Thread("Error dump: " + dropboxTag) { 11502 @Override 11503 public void run() { 11504 // 5 second sleep to let stacks arrive and be batched together 11505 try { 11506 Thread.sleep(5000); // 5 seconds 11507 } catch (InterruptedException e) {} 11508 11509 String errorReport; 11510 synchronized (mStrictModeBuffer) { 11511 errorReport = mStrictModeBuffer.toString(); 11512 if (errorReport.length() == 0) { 11513 return; 11514 } 11515 mStrictModeBuffer.delete(0, mStrictModeBuffer.length()); 11516 mStrictModeBuffer.trimToSize(); 11517 } 11518 dbox.addText(dropboxTag, errorReport); 11519 } 11520 }.start(); 11521 } 11522 11523 /** 11524 * Used by {@link Log} via {@link com.android.internal.os.RuntimeInit} to report serious errors. 11525 * @param app object of the crashing app, null for the system server 11526 * @param tag reported by the caller 11527 * @param system whether this wtf is coming from the system 11528 * @param crashInfo describing the context of the error 11529 * @return true if the process should exit immediately (WTF is fatal) 11530 */ 11531 public boolean handleApplicationWtf(IBinder app, final String tag, boolean system, 11532 final ApplicationErrorReport.CrashInfo crashInfo) { 11533 final ProcessRecord r = findAppProcess(app, "WTF"); 11534 final String processName = app == null ? "system_server" 11535 : (r == null ? "unknown" : r.processName); 11536 11537 EventLog.writeEvent(EventLogTags.AM_WTF, 11538 UserHandle.getUserId(Binder.getCallingUid()), Binder.getCallingPid(), 11539 processName, 11540 r == null ? -1 : r.info.flags, 11541 tag, crashInfo.exceptionMessage); 11542 11543 if (system) { 11544 // If this is coming from the system, we could very well have low-level 11545 // system locks held, so we want to do this all asynchronously. And we 11546 // never want this to become fatal, so there is that too. 11547 mHandler.post(new Runnable() { 11548 @Override public void run() { 11549 addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, 11550 crashInfo); 11551 } 11552 }); 11553 return false; 11554 } 11555 11556 addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, crashInfo); 11557 11558 if (r != null && r.pid != Process.myPid() && 11559 Settings.Global.getInt(mContext.getContentResolver(), 11560 Settings.Global.WTF_IS_FATAL, 0) != 0) { 11561 crashApplication(r, crashInfo); 11562 return true; 11563 } else { 11564 return false; 11565 } 11566 } 11567 11568 /** 11569 * @param app object of some object (as stored in {@link com.android.internal.os.RuntimeInit}) 11570 * @return the corresponding {@link ProcessRecord} object, or null if none could be found 11571 */ 11572 private ProcessRecord findAppProcess(IBinder app, String reason) { 11573 if (app == null) { 11574 return null; 11575 } 11576 11577 synchronized (this) { 11578 final int NP = mProcessNames.getMap().size(); 11579 for (int ip=0; ip<NP; ip++) { 11580 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 11581 final int NA = apps.size(); 11582 for (int ia=0; ia<NA; ia++) { 11583 ProcessRecord p = apps.valueAt(ia); 11584 if (p.thread != null && p.thread.asBinder() == app) { 11585 return p; 11586 } 11587 } 11588 } 11589 11590 Slog.w(TAG, "Can't find mystery application for " + reason 11591 + " from pid=" + Binder.getCallingPid() 11592 + " uid=" + Binder.getCallingUid() + ": " + app); 11593 return null; 11594 } 11595 } 11596 11597 /** 11598 * Utility function for addErrorToDropBox and handleStrictModeViolation's logging 11599 * to append various headers to the dropbox log text. 11600 */ 11601 private void appendDropBoxProcessHeaders(ProcessRecord process, String processName, 11602 StringBuilder sb) { 11603 // Watchdog thread ends up invoking this function (with 11604 // a null ProcessRecord) to add the stack file to dropbox. 11605 // Do not acquire a lock on this (am) in such cases, as it 11606 // could cause a potential deadlock, if and when watchdog 11607 // is invoked due to unavailability of lock on am and it 11608 // would prevent watchdog from killing system_server. 11609 if (process == null) { 11610 sb.append("Process: ").append(processName).append("\n"); 11611 return; 11612 } 11613 // Note: ProcessRecord 'process' is guarded by the service 11614 // instance. (notably process.pkgList, which could otherwise change 11615 // concurrently during execution of this method) 11616 synchronized (this) { 11617 sb.append("Process: ").append(processName).append("\n"); 11618 int flags = process.info.flags; 11619 IPackageManager pm = AppGlobals.getPackageManager(); 11620 sb.append("Flags: 0x").append(Integer.toString(flags, 16)).append("\n"); 11621 for (int ip=0; ip<process.pkgList.size(); ip++) { 11622 String pkg = process.pkgList.keyAt(ip); 11623 sb.append("Package: ").append(pkg); 11624 try { 11625 PackageInfo pi = pm.getPackageInfo(pkg, 0, UserHandle.getCallingUserId()); 11626 if (pi != null) { 11627 sb.append(" v").append(pi.versionCode); 11628 if (pi.versionName != null) { 11629 sb.append(" (").append(pi.versionName).append(")"); 11630 } 11631 } 11632 } catch (RemoteException e) { 11633 Slog.e(TAG, "Error getting package info: " + pkg, e); 11634 } 11635 sb.append("\n"); 11636 } 11637 } 11638 } 11639 11640 private static String processClass(ProcessRecord process) { 11641 if (process == null || process.pid == MY_PID) { 11642 return "system_server"; 11643 } else if ((process.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 11644 return "system_app"; 11645 } else { 11646 return "data_app"; 11647 } 11648 } 11649 11650 /** 11651 * Write a description of an error (crash, WTF, ANR) to the drop box. 11652 * @param eventType to include in the drop box tag ("crash", "wtf", etc.) 11653 * @param process which caused the error, null means the system server 11654 * @param activity which triggered the error, null if unknown 11655 * @param parent activity related to the error, null if unknown 11656 * @param subject line related to the error, null if absent 11657 * @param report in long form describing the error, null if absent 11658 * @param logFile to include in the report, null if none 11659 * @param crashInfo giving an application stack trace, null if absent 11660 */ 11661 public void addErrorToDropBox(String eventType, 11662 ProcessRecord process, String processName, ActivityRecord activity, 11663 ActivityRecord parent, String subject, 11664 final String report, final File logFile, 11665 final ApplicationErrorReport.CrashInfo crashInfo) { 11666 // NOTE -- this must never acquire the ActivityManagerService lock, 11667 // otherwise the watchdog may be prevented from resetting the system. 11668 11669 final String dropboxTag = processClass(process) + "_" + eventType; 11670 final DropBoxManager dbox = (DropBoxManager) 11671 mContext.getSystemService(Context.DROPBOX_SERVICE); 11672 11673 // Exit early if the dropbox isn't configured to accept this report type. 11674 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 11675 11676 final StringBuilder sb = new StringBuilder(1024); 11677 appendDropBoxProcessHeaders(process, processName, sb); 11678 if (activity != null) { 11679 sb.append("Activity: ").append(activity.shortComponentName).append("\n"); 11680 } 11681 if (parent != null && parent.app != null && parent.app.pid != process.pid) { 11682 sb.append("Parent-Process: ").append(parent.app.processName).append("\n"); 11683 } 11684 if (parent != null && parent != activity) { 11685 sb.append("Parent-Activity: ").append(parent.shortComponentName).append("\n"); 11686 } 11687 if (subject != null) { 11688 sb.append("Subject: ").append(subject).append("\n"); 11689 } 11690 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 11691 if (Debug.isDebuggerConnected()) { 11692 sb.append("Debugger: Connected\n"); 11693 } 11694 sb.append("\n"); 11695 11696 // Do the rest in a worker thread to avoid blocking the caller on I/O 11697 // (After this point, we shouldn't access AMS internal data structures.) 11698 Thread worker = new Thread("Error dump: " + dropboxTag) { 11699 @Override 11700 public void run() { 11701 if (report != null) { 11702 sb.append(report); 11703 } 11704 if (logFile != null) { 11705 try { 11706 sb.append(FileUtils.readTextFile(logFile, DROPBOX_MAX_SIZE, 11707 "\n\n[[TRUNCATED]]")); 11708 } catch (IOException e) { 11709 Slog.e(TAG, "Error reading " + logFile, e); 11710 } 11711 } 11712 if (crashInfo != null && crashInfo.stackTrace != null) { 11713 sb.append(crashInfo.stackTrace); 11714 } 11715 11716 String setting = Settings.Global.ERROR_LOGCAT_PREFIX + dropboxTag; 11717 int lines = Settings.Global.getInt(mContext.getContentResolver(), setting, 0); 11718 if (lines > 0) { 11719 sb.append("\n"); 11720 11721 // Merge several logcat streams, and take the last N lines 11722 InputStreamReader input = null; 11723 try { 11724 java.lang.Process logcat = new ProcessBuilder("/system/bin/logcat", 11725 "-v", "time", "-b", "events", "-b", "system", "-b", "main", 11726 "-b", "crash", 11727 "-t", String.valueOf(lines)).redirectErrorStream(true).start(); 11728 11729 try { logcat.getOutputStream().close(); } catch (IOException e) {} 11730 try { logcat.getErrorStream().close(); } catch (IOException e) {} 11731 input = new InputStreamReader(logcat.getInputStream()); 11732 11733 int num; 11734 char[] buf = new char[8192]; 11735 while ((num = input.read(buf)) > 0) sb.append(buf, 0, num); 11736 } catch (IOException e) { 11737 Slog.e(TAG, "Error running logcat", e); 11738 } finally { 11739 if (input != null) try { input.close(); } catch (IOException e) {} 11740 } 11741 } 11742 11743 dbox.addText(dropboxTag, sb.toString()); 11744 } 11745 }; 11746 11747 if (process == null) { 11748 // If process is null, we are being called from some internal code 11749 // and may be about to die -- run this synchronously. 11750 worker.run(); 11751 } else { 11752 worker.start(); 11753 } 11754 } 11755 11756 /** 11757 * Bring up the "unexpected error" dialog box for a crashing app. 11758 * Deal with edge cases (intercepts from instrumented applications, 11759 * ActivityController, error intent receivers, that sort of thing). 11760 * @param r the application crashing 11761 * @param crashInfo describing the failure 11762 */ 11763 private void crashApplication(ProcessRecord r, ApplicationErrorReport.CrashInfo crashInfo) { 11764 long timeMillis = System.currentTimeMillis(); 11765 String shortMsg = crashInfo.exceptionClassName; 11766 String longMsg = crashInfo.exceptionMessage; 11767 String stackTrace = crashInfo.stackTrace; 11768 if (shortMsg != null && longMsg != null) { 11769 longMsg = shortMsg + ": " + longMsg; 11770 } else if (shortMsg != null) { 11771 longMsg = shortMsg; 11772 } 11773 11774 AppErrorResult result = new AppErrorResult(); 11775 synchronized (this) { 11776 if (mController != null) { 11777 try { 11778 String name = r != null ? r.processName : null; 11779 int pid = r != null ? r.pid : Binder.getCallingPid(); 11780 int uid = r != null ? r.info.uid : Binder.getCallingUid(); 11781 if (!mController.appCrashed(name, pid, 11782 shortMsg, longMsg, timeMillis, crashInfo.stackTrace)) { 11783 if ("1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")) 11784 && "Native crash".equals(crashInfo.exceptionClassName)) { 11785 Slog.w(TAG, "Skip killing native crashed app " + name 11786 + "(" + pid + ") during testing"); 11787 } else { 11788 Slog.w(TAG, "Force-killing crashed app " + name 11789 + " at watcher's request"); 11790 if (r != null) { 11791 r.kill("crash", true); 11792 } else { 11793 // Huh. 11794 Process.killProcess(pid); 11795 Process.killProcessGroup(uid, pid); 11796 } 11797 } 11798 return; 11799 } 11800 } catch (RemoteException e) { 11801 mController = null; 11802 Watchdog.getInstance().setActivityController(null); 11803 } 11804 } 11805 11806 final long origId = Binder.clearCallingIdentity(); 11807 11808 // If this process is running instrumentation, finish it. 11809 if (r != null && r.instrumentationClass != null) { 11810 Slog.w(TAG, "Error in app " + r.processName 11811 + " running instrumentation " + r.instrumentationClass + ":"); 11812 if (shortMsg != null) Slog.w(TAG, " " + shortMsg); 11813 if (longMsg != null) Slog.w(TAG, " " + longMsg); 11814 Bundle info = new Bundle(); 11815 info.putString("shortMsg", shortMsg); 11816 info.putString("longMsg", longMsg); 11817 finishInstrumentationLocked(r, Activity.RESULT_CANCELED, info); 11818 Binder.restoreCallingIdentity(origId); 11819 return; 11820 } 11821 11822 // If we can't identify the process or it's already exceeded its crash quota, 11823 // quit right away without showing a crash dialog. 11824 if (r == null || !makeAppCrashingLocked(r, shortMsg, longMsg, stackTrace)) { 11825 Binder.restoreCallingIdentity(origId); 11826 return; 11827 } 11828 11829 Message msg = Message.obtain(); 11830 msg.what = SHOW_ERROR_MSG; 11831 HashMap data = new HashMap(); 11832 data.put("result", result); 11833 data.put("app", r); 11834 msg.obj = data; 11835 mHandler.sendMessage(msg); 11836 11837 Binder.restoreCallingIdentity(origId); 11838 } 11839 11840 int res = result.get(); 11841 11842 Intent appErrorIntent = null; 11843 synchronized (this) { 11844 if (r != null && !r.isolated) { 11845 // XXX Can't keep track of crash time for isolated processes, 11846 // since they don't have a persistent identity. 11847 mProcessCrashTimes.put(r.info.processName, r.uid, 11848 SystemClock.uptimeMillis()); 11849 } 11850 if (res == AppErrorDialog.FORCE_QUIT_AND_REPORT) { 11851 appErrorIntent = createAppErrorIntentLocked(r, timeMillis, crashInfo); 11852 } 11853 } 11854 11855 if (appErrorIntent != null) { 11856 try { 11857 mContext.startActivityAsUser(appErrorIntent, new UserHandle(r.userId)); 11858 } catch (ActivityNotFoundException e) { 11859 Slog.w(TAG, "bug report receiver dissappeared", e); 11860 } 11861 } 11862 } 11863 11864 Intent createAppErrorIntentLocked(ProcessRecord r, 11865 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 11866 ApplicationErrorReport report = createAppErrorReportLocked(r, timeMillis, crashInfo); 11867 if (report == null) { 11868 return null; 11869 } 11870 Intent result = new Intent(Intent.ACTION_APP_ERROR); 11871 result.setComponent(r.errorReportReceiver); 11872 result.putExtra(Intent.EXTRA_BUG_REPORT, report); 11873 result.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 11874 return result; 11875 } 11876 11877 private ApplicationErrorReport createAppErrorReportLocked(ProcessRecord r, 11878 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 11879 if (r.errorReportReceiver == null) { 11880 return null; 11881 } 11882 11883 if (!r.crashing && !r.notResponding && !r.forceCrashReport) { 11884 return null; 11885 } 11886 11887 ApplicationErrorReport report = new ApplicationErrorReport(); 11888 report.packageName = r.info.packageName; 11889 report.installerPackageName = r.errorReportReceiver.getPackageName(); 11890 report.processName = r.processName; 11891 report.time = timeMillis; 11892 report.systemApp = (r.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0; 11893 11894 if (r.crashing || r.forceCrashReport) { 11895 report.type = ApplicationErrorReport.TYPE_CRASH; 11896 report.crashInfo = crashInfo; 11897 } else if (r.notResponding) { 11898 report.type = ApplicationErrorReport.TYPE_ANR; 11899 report.anrInfo = new ApplicationErrorReport.AnrInfo(); 11900 11901 report.anrInfo.activity = r.notRespondingReport.tag; 11902 report.anrInfo.cause = r.notRespondingReport.shortMsg; 11903 report.anrInfo.info = r.notRespondingReport.longMsg; 11904 } 11905 11906 return report; 11907 } 11908 11909 public List<ActivityManager.ProcessErrorStateInfo> getProcessesInErrorState() { 11910 enforceNotIsolatedCaller("getProcessesInErrorState"); 11911 // assume our apps are happy - lazy create the list 11912 List<ActivityManager.ProcessErrorStateInfo> errList = null; 11913 11914 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 11915 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 11916 int userId = UserHandle.getUserId(Binder.getCallingUid()); 11917 11918 synchronized (this) { 11919 11920 // iterate across all processes 11921 for (int i=mLruProcesses.size()-1; i>=0; i--) { 11922 ProcessRecord app = mLruProcesses.get(i); 11923 if (!allUsers && app.userId != userId) { 11924 continue; 11925 } 11926 if ((app.thread != null) && (app.crashing || app.notResponding)) { 11927 // This one's in trouble, so we'll generate a report for it 11928 // crashes are higher priority (in case there's a crash *and* an anr) 11929 ActivityManager.ProcessErrorStateInfo report = null; 11930 if (app.crashing) { 11931 report = app.crashingReport; 11932 } else if (app.notResponding) { 11933 report = app.notRespondingReport; 11934 } 11935 11936 if (report != null) { 11937 if (errList == null) { 11938 errList = new ArrayList<ActivityManager.ProcessErrorStateInfo>(1); 11939 } 11940 errList.add(report); 11941 } else { 11942 Slog.w(TAG, "Missing app error report, app = " + app.processName + 11943 " crashing = " + app.crashing + 11944 " notResponding = " + app.notResponding); 11945 } 11946 } 11947 } 11948 } 11949 11950 return errList; 11951 } 11952 11953 static int procStateToImportance(int procState, int memAdj, 11954 ActivityManager.RunningAppProcessInfo currApp) { 11955 int imp = ActivityManager.RunningAppProcessInfo.procStateToImportance(procState); 11956 if (imp == ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND) { 11957 currApp.lru = memAdj; 11958 } else { 11959 currApp.lru = 0; 11960 } 11961 return imp; 11962 } 11963 11964 private void fillInProcMemInfo(ProcessRecord app, 11965 ActivityManager.RunningAppProcessInfo outInfo) { 11966 outInfo.pid = app.pid; 11967 outInfo.uid = app.info.uid; 11968 if (mHeavyWeightProcess == app) { 11969 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_CANT_SAVE_STATE; 11970 } 11971 if (app.persistent) { 11972 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_PERSISTENT; 11973 } 11974 if (app.activities.size() > 0) { 11975 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_HAS_ACTIVITIES; 11976 } 11977 outInfo.lastTrimLevel = app.trimMemoryLevel; 11978 int adj = app.curAdj; 11979 int procState = app.curProcState; 11980 outInfo.importance = procStateToImportance(procState, adj, outInfo); 11981 outInfo.importanceReasonCode = app.adjTypeCode; 11982 outInfo.processState = app.curProcState; 11983 } 11984 11985 public List<ActivityManager.RunningAppProcessInfo> getRunningAppProcesses() { 11986 enforceNotIsolatedCaller("getRunningAppProcesses"); 11987 // Lazy instantiation of list 11988 List<ActivityManager.RunningAppProcessInfo> runList = null; 11989 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 11990 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 11991 int userId = UserHandle.getUserId(Binder.getCallingUid()); 11992 synchronized (this) { 11993 // Iterate across all processes 11994 for (int i=mLruProcesses.size()-1; i>=0; i--) { 11995 ProcessRecord app = mLruProcesses.get(i); 11996 if (!allUsers && app.userId != userId) { 11997 continue; 11998 } 11999 if ((app.thread != null) && (!app.crashing && !app.notResponding)) { 12000 // Generate process state info for running application 12001 ActivityManager.RunningAppProcessInfo currApp = 12002 new ActivityManager.RunningAppProcessInfo(app.processName, 12003 app.pid, app.getPackageList()); 12004 fillInProcMemInfo(app, currApp); 12005 if (app.adjSource instanceof ProcessRecord) { 12006 currApp.importanceReasonPid = ((ProcessRecord)app.adjSource).pid; 12007 currApp.importanceReasonImportance = 12008 ActivityManager.RunningAppProcessInfo.procStateToImportance( 12009 app.adjSourceProcState); 12010 } else if (app.adjSource instanceof ActivityRecord) { 12011 ActivityRecord r = (ActivityRecord)app.adjSource; 12012 if (r.app != null) currApp.importanceReasonPid = r.app.pid; 12013 } 12014 if (app.adjTarget instanceof ComponentName) { 12015 currApp.importanceReasonComponent = (ComponentName)app.adjTarget; 12016 } 12017 //Slog.v(TAG, "Proc " + app.processName + ": imp=" + currApp.importance 12018 // + " lru=" + currApp.lru); 12019 if (runList == null) { 12020 runList = new ArrayList<ActivityManager.RunningAppProcessInfo>(); 12021 } 12022 runList.add(currApp); 12023 } 12024 } 12025 } 12026 return runList; 12027 } 12028 12029 public List<ApplicationInfo> getRunningExternalApplications() { 12030 enforceNotIsolatedCaller("getRunningExternalApplications"); 12031 List<ActivityManager.RunningAppProcessInfo> runningApps = getRunningAppProcesses(); 12032 List<ApplicationInfo> retList = new ArrayList<ApplicationInfo>(); 12033 if (runningApps != null && runningApps.size() > 0) { 12034 Set<String> extList = new HashSet<String>(); 12035 for (ActivityManager.RunningAppProcessInfo app : runningApps) { 12036 if (app.pkgList != null) { 12037 for (String pkg : app.pkgList) { 12038 extList.add(pkg); 12039 } 12040 } 12041 } 12042 IPackageManager pm = AppGlobals.getPackageManager(); 12043 for (String pkg : extList) { 12044 try { 12045 ApplicationInfo info = pm.getApplicationInfo(pkg, 0, UserHandle.getCallingUserId()); 12046 if ((info.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0) { 12047 retList.add(info); 12048 } 12049 } catch (RemoteException e) { 12050 } 12051 } 12052 } 12053 return retList; 12054 } 12055 12056 @Override 12057 public void getMyMemoryState(ActivityManager.RunningAppProcessInfo outInfo) { 12058 enforceNotIsolatedCaller("getMyMemoryState"); 12059 synchronized (this) { 12060 ProcessRecord proc; 12061 synchronized (mPidsSelfLocked) { 12062 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 12063 } 12064 fillInProcMemInfo(proc, outInfo); 12065 } 12066 } 12067 12068 @Override 12069 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 12070 if (checkCallingPermission(android.Manifest.permission.DUMP) 12071 != PackageManager.PERMISSION_GRANTED) { 12072 pw.println("Permission Denial: can't dump ActivityManager from from pid=" 12073 + Binder.getCallingPid() 12074 + ", uid=" + Binder.getCallingUid() 12075 + " without permission " 12076 + android.Manifest.permission.DUMP); 12077 return; 12078 } 12079 12080 boolean dumpAll = false; 12081 boolean dumpClient = false; 12082 String dumpPackage = null; 12083 12084 int opti = 0; 12085 while (opti < args.length) { 12086 String opt = args[opti]; 12087 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 12088 break; 12089 } 12090 opti++; 12091 if ("-a".equals(opt)) { 12092 dumpAll = true; 12093 } else if ("-c".equals(opt)) { 12094 dumpClient = true; 12095 } else if ("-h".equals(opt)) { 12096 pw.println("Activity manager dump options:"); 12097 pw.println(" [-a] [-c] [-h] [cmd] ..."); 12098 pw.println(" cmd may be one of:"); 12099 pw.println(" a[ctivities]: activity stack state"); 12100 pw.println(" r[recents]: recent activities state"); 12101 pw.println(" b[roadcasts] [PACKAGE_NAME] [history [-s]]: broadcast state"); 12102 pw.println(" i[ntents] [PACKAGE_NAME]: pending intent state"); 12103 pw.println(" p[rocesses] [PACKAGE_NAME]: process state"); 12104 pw.println(" o[om]: out of memory management"); 12105 pw.println(" prov[iders] [COMP_SPEC ...]: content provider state"); 12106 pw.println(" provider [COMP_SPEC]: provider client-side state"); 12107 pw.println(" s[ervices] [COMP_SPEC ...]: service state"); 12108 pw.println(" service [COMP_SPEC]: service client-side state"); 12109 pw.println(" package [PACKAGE_NAME]: all state related to given package"); 12110 pw.println(" all: dump all activities"); 12111 pw.println(" top: dump the top activity"); 12112 pw.println(" cmd may also be a COMP_SPEC to dump activities."); 12113 pw.println(" COMP_SPEC may be a component name (com.foo/.myApp),"); 12114 pw.println(" a partial substring in a component name, a"); 12115 pw.println(" hex object identifier."); 12116 pw.println(" -a: include all available server state."); 12117 pw.println(" -c: include client state."); 12118 return; 12119 } else { 12120 pw.println("Unknown argument: " + opt + "; use -h for help"); 12121 } 12122 } 12123 12124 long origId = Binder.clearCallingIdentity(); 12125 boolean more = false; 12126 // Is the caller requesting to dump a particular piece of data? 12127 if (opti < args.length) { 12128 String cmd = args[opti]; 12129 opti++; 12130 if ("activities".equals(cmd) || "a".equals(cmd)) { 12131 synchronized (this) { 12132 dumpActivitiesLocked(fd, pw, args, opti, true, dumpClient, null); 12133 } 12134 } else if ("recents".equals(cmd) || "r".equals(cmd)) { 12135 synchronized (this) { 12136 dumpRecentsLocked(fd, pw, args, opti, true, null); 12137 } 12138 } else if ("broadcasts".equals(cmd) || "b".equals(cmd)) { 12139 String[] newArgs; 12140 String name; 12141 if (opti >= args.length) { 12142 name = null; 12143 newArgs = EMPTY_STRING_ARRAY; 12144 } else { 12145 name = args[opti]; 12146 opti++; 12147 newArgs = new String[args.length - opti]; 12148 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12149 args.length - opti); 12150 } 12151 synchronized (this) { 12152 dumpBroadcastsLocked(fd, pw, args, opti, true, name); 12153 } 12154 } else if ("intents".equals(cmd) || "i".equals(cmd)) { 12155 String[] newArgs; 12156 String name; 12157 if (opti >= args.length) { 12158 name = null; 12159 newArgs = EMPTY_STRING_ARRAY; 12160 } else { 12161 name = args[opti]; 12162 opti++; 12163 newArgs = new String[args.length - opti]; 12164 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12165 args.length - opti); 12166 } 12167 synchronized (this) { 12168 dumpPendingIntentsLocked(fd, pw, args, opti, true, name); 12169 } 12170 } else if ("processes".equals(cmd) || "p".equals(cmd)) { 12171 String[] newArgs; 12172 String name; 12173 if (opti >= args.length) { 12174 name = null; 12175 newArgs = EMPTY_STRING_ARRAY; 12176 } else { 12177 name = args[opti]; 12178 opti++; 12179 newArgs = new String[args.length - opti]; 12180 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12181 args.length - opti); 12182 } 12183 synchronized (this) { 12184 dumpProcessesLocked(fd, pw, args, opti, true, name); 12185 } 12186 } else if ("oom".equals(cmd) || "o".equals(cmd)) { 12187 synchronized (this) { 12188 dumpOomLocked(fd, pw, args, opti, true); 12189 } 12190 } else if ("provider".equals(cmd)) { 12191 String[] newArgs; 12192 String name; 12193 if (opti >= args.length) { 12194 name = null; 12195 newArgs = EMPTY_STRING_ARRAY; 12196 } else { 12197 name = args[opti]; 12198 opti++; 12199 newArgs = new String[args.length - opti]; 12200 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, args.length - opti); 12201 } 12202 if (!dumpProvider(fd, pw, name, newArgs, 0, dumpAll)) { 12203 pw.println("No providers match: " + name); 12204 pw.println("Use -h for help."); 12205 } 12206 } else if ("providers".equals(cmd) || "prov".equals(cmd)) { 12207 synchronized (this) { 12208 dumpProvidersLocked(fd, pw, args, opti, true, null); 12209 } 12210 } else if ("service".equals(cmd)) { 12211 String[] newArgs; 12212 String name; 12213 if (opti >= args.length) { 12214 name = null; 12215 newArgs = EMPTY_STRING_ARRAY; 12216 } else { 12217 name = args[opti]; 12218 opti++; 12219 newArgs = new String[args.length - opti]; 12220 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12221 args.length - opti); 12222 } 12223 if (!mServices.dumpService(fd, pw, name, newArgs, 0, dumpAll)) { 12224 pw.println("No services match: " + name); 12225 pw.println("Use -h for help."); 12226 } 12227 } else if ("package".equals(cmd)) { 12228 String[] newArgs; 12229 if (opti >= args.length) { 12230 pw.println("package: no package name specified"); 12231 pw.println("Use -h for help."); 12232 } else { 12233 dumpPackage = args[opti]; 12234 opti++; 12235 newArgs = new String[args.length - opti]; 12236 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12237 args.length - opti); 12238 args = newArgs; 12239 opti = 0; 12240 more = true; 12241 } 12242 } else if ("services".equals(cmd) || "s".equals(cmd)) { 12243 synchronized (this) { 12244 mServices.dumpServicesLocked(fd, pw, args, opti, true, dumpClient, null); 12245 } 12246 } else { 12247 // Dumping a single activity? 12248 if (!dumpActivity(fd, pw, cmd, args, opti, dumpAll)) { 12249 pw.println("Bad activity command, or no activities match: " + cmd); 12250 pw.println("Use -h for help."); 12251 } 12252 } 12253 if (!more) { 12254 Binder.restoreCallingIdentity(origId); 12255 return; 12256 } 12257 } 12258 12259 // No piece of data specified, dump everything. 12260 synchronized (this) { 12261 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12262 pw.println(); 12263 if (dumpAll) { 12264 pw.println("-------------------------------------------------------------------------------"); 12265 } 12266 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12267 pw.println(); 12268 if (dumpAll) { 12269 pw.println("-------------------------------------------------------------------------------"); 12270 } 12271 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12272 pw.println(); 12273 if (dumpAll) { 12274 pw.println("-------------------------------------------------------------------------------"); 12275 } 12276 mServices.dumpServicesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 12277 pw.println(); 12278 if (dumpAll) { 12279 pw.println("-------------------------------------------------------------------------------"); 12280 } 12281 dumpRecentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12282 pw.println(); 12283 if (dumpAll) { 12284 pw.println("-------------------------------------------------------------------------------"); 12285 } 12286 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 12287 pw.println(); 12288 if (dumpAll) { 12289 pw.println("-------------------------------------------------------------------------------"); 12290 } 12291 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12292 } 12293 Binder.restoreCallingIdentity(origId); 12294 } 12295 12296 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12297 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) { 12298 pw.println("ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)"); 12299 12300 boolean printedAnything = mStackSupervisor.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient, 12301 dumpPackage); 12302 boolean needSep = printedAnything; 12303 12304 boolean printed = ActivityStackSupervisor.printThisActivity(pw, mFocusedActivity, 12305 dumpPackage, needSep, " mFocusedActivity: "); 12306 if (printed) { 12307 printedAnything = true; 12308 needSep = false; 12309 } 12310 12311 if (dumpPackage == null) { 12312 if (needSep) { 12313 pw.println(); 12314 } 12315 needSep = true; 12316 printedAnything = true; 12317 mStackSupervisor.dump(pw, " "); 12318 } 12319 12320 if (!printedAnything) { 12321 pw.println(" (nothing)"); 12322 } 12323 } 12324 12325 void dumpRecentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12326 int opti, boolean dumpAll, String dumpPackage) { 12327 pw.println("ACTIVITY MANAGER RECENT ACTIVITIES (dumpsys activity recents)"); 12328 12329 boolean printedAnything = false; 12330 12331 if (mRecentTasks.size() > 0) { 12332 boolean printedHeader = false; 12333 12334 final int N = mRecentTasks.size(); 12335 for (int i=0; i<N; i++) { 12336 TaskRecord tr = mRecentTasks.get(i); 12337 if (dumpPackage != null) { 12338 if (tr.realActivity == null || 12339 !dumpPackage.equals(tr.realActivity)) { 12340 continue; 12341 } 12342 } 12343 if (!printedHeader) { 12344 pw.println(" Recent tasks:"); 12345 printedHeader = true; 12346 printedAnything = true; 12347 } 12348 pw.print(" * Recent #"); pw.print(i); pw.print(": "); 12349 pw.println(tr); 12350 if (dumpAll) { 12351 mRecentTasks.get(i).dump(pw, " "); 12352 } 12353 } 12354 } 12355 12356 if (!printedAnything) { 12357 pw.println(" (nothing)"); 12358 } 12359 } 12360 12361 void dumpProcessesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12362 int opti, boolean dumpAll, String dumpPackage) { 12363 boolean needSep = false; 12364 boolean printedAnything = false; 12365 int numPers = 0; 12366 12367 pw.println("ACTIVITY MANAGER RUNNING PROCESSES (dumpsys activity processes)"); 12368 12369 if (dumpAll) { 12370 final int NP = mProcessNames.getMap().size(); 12371 for (int ip=0; ip<NP; ip++) { 12372 SparseArray<ProcessRecord> procs = mProcessNames.getMap().valueAt(ip); 12373 final int NA = procs.size(); 12374 for (int ia=0; ia<NA; ia++) { 12375 ProcessRecord r = procs.valueAt(ia); 12376 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 12377 continue; 12378 } 12379 if (!needSep) { 12380 pw.println(" All known processes:"); 12381 needSep = true; 12382 printedAnything = true; 12383 } 12384 pw.print(r.persistent ? " *PERS*" : " *APP*"); 12385 pw.print(" UID "); pw.print(procs.keyAt(ia)); 12386 pw.print(" "); pw.println(r); 12387 r.dump(pw, " "); 12388 if (r.persistent) { 12389 numPers++; 12390 } 12391 } 12392 } 12393 } 12394 12395 if (mIsolatedProcesses.size() > 0) { 12396 boolean printed = false; 12397 for (int i=0; i<mIsolatedProcesses.size(); i++) { 12398 ProcessRecord r = mIsolatedProcesses.valueAt(i); 12399 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 12400 continue; 12401 } 12402 if (!printed) { 12403 if (needSep) { 12404 pw.println(); 12405 } 12406 pw.println(" Isolated process list (sorted by uid):"); 12407 printedAnything = true; 12408 printed = true; 12409 needSep = true; 12410 } 12411 pw.println(String.format("%sIsolated #%2d: %s", 12412 " ", i, r.toString())); 12413 } 12414 } 12415 12416 if (mLruProcesses.size() > 0) { 12417 if (needSep) { 12418 pw.println(); 12419 } 12420 pw.print(" Process LRU list (sorted by oom_adj, "); pw.print(mLruProcesses.size()); 12421 pw.print(" total, non-act at "); 12422 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 12423 pw.print(", non-svc at "); 12424 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 12425 pw.println("):"); 12426 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", false, dumpPackage); 12427 needSep = true; 12428 printedAnything = true; 12429 } 12430 12431 if (dumpAll || dumpPackage != null) { 12432 synchronized (mPidsSelfLocked) { 12433 boolean printed = false; 12434 for (int i=0; i<mPidsSelfLocked.size(); i++) { 12435 ProcessRecord r = mPidsSelfLocked.valueAt(i); 12436 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 12437 continue; 12438 } 12439 if (!printed) { 12440 if (needSep) pw.println(); 12441 needSep = true; 12442 pw.println(" PID mappings:"); 12443 printed = true; 12444 printedAnything = true; 12445 } 12446 pw.print(" PID #"); pw.print(mPidsSelfLocked.keyAt(i)); 12447 pw.print(": "); pw.println(mPidsSelfLocked.valueAt(i)); 12448 } 12449 } 12450 } 12451 12452 if (mForegroundProcesses.size() > 0) { 12453 synchronized (mPidsSelfLocked) { 12454 boolean printed = false; 12455 for (int i=0; i<mForegroundProcesses.size(); i++) { 12456 ProcessRecord r = mPidsSelfLocked.get( 12457 mForegroundProcesses.valueAt(i).pid); 12458 if (dumpPackage != null && (r == null 12459 || !r.pkgList.containsKey(dumpPackage))) { 12460 continue; 12461 } 12462 if (!printed) { 12463 if (needSep) pw.println(); 12464 needSep = true; 12465 pw.println(" Foreground Processes:"); 12466 printed = true; 12467 printedAnything = true; 12468 } 12469 pw.print(" PID #"); pw.print(mForegroundProcesses.keyAt(i)); 12470 pw.print(": "); pw.println(mForegroundProcesses.valueAt(i)); 12471 } 12472 } 12473 } 12474 12475 if (mPersistentStartingProcesses.size() > 0) { 12476 if (needSep) pw.println(); 12477 needSep = true; 12478 printedAnything = true; 12479 pw.println(" Persisent processes that are starting:"); 12480 dumpProcessList(pw, this, mPersistentStartingProcesses, " ", 12481 "Starting Norm", "Restarting PERS", dumpPackage); 12482 } 12483 12484 if (mRemovedProcesses.size() > 0) { 12485 if (needSep) pw.println(); 12486 needSep = true; 12487 printedAnything = true; 12488 pw.println(" Processes that are being removed:"); 12489 dumpProcessList(pw, this, mRemovedProcesses, " ", 12490 "Removed Norm", "Removed PERS", dumpPackage); 12491 } 12492 12493 if (mProcessesOnHold.size() > 0) { 12494 if (needSep) pw.println(); 12495 needSep = true; 12496 printedAnything = true; 12497 pw.println(" Processes that are on old until the system is ready:"); 12498 dumpProcessList(pw, this, mProcessesOnHold, " ", 12499 "OnHold Norm", "OnHold PERS", dumpPackage); 12500 } 12501 12502 needSep = dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, dumpPackage); 12503 12504 if (mProcessCrashTimes.getMap().size() > 0) { 12505 boolean printed = false; 12506 long now = SystemClock.uptimeMillis(); 12507 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 12508 final int NP = pmap.size(); 12509 for (int ip=0; ip<NP; ip++) { 12510 String pname = pmap.keyAt(ip); 12511 SparseArray<Long> uids = pmap.valueAt(ip); 12512 final int N = uids.size(); 12513 for (int i=0; i<N; i++) { 12514 int puid = uids.keyAt(i); 12515 ProcessRecord r = mProcessNames.get(pname, puid); 12516 if (dumpPackage != null && (r == null 12517 || !r.pkgList.containsKey(dumpPackage))) { 12518 continue; 12519 } 12520 if (!printed) { 12521 if (needSep) pw.println(); 12522 needSep = true; 12523 pw.println(" Time since processes crashed:"); 12524 printed = true; 12525 printedAnything = true; 12526 } 12527 pw.print(" Process "); pw.print(pname); 12528 pw.print(" uid "); pw.print(puid); 12529 pw.print(": last crashed "); 12530 TimeUtils.formatDuration(now-uids.valueAt(i), pw); 12531 pw.println(" ago"); 12532 } 12533 } 12534 } 12535 12536 if (mBadProcesses.getMap().size() > 0) { 12537 boolean printed = false; 12538 final ArrayMap<String, SparseArray<BadProcessInfo>> pmap = mBadProcesses.getMap(); 12539 final int NP = pmap.size(); 12540 for (int ip=0; ip<NP; ip++) { 12541 String pname = pmap.keyAt(ip); 12542 SparseArray<BadProcessInfo> uids = pmap.valueAt(ip); 12543 final int N = uids.size(); 12544 for (int i=0; i<N; i++) { 12545 int puid = uids.keyAt(i); 12546 ProcessRecord r = mProcessNames.get(pname, puid); 12547 if (dumpPackage != null && (r == null 12548 || !r.pkgList.containsKey(dumpPackage))) { 12549 continue; 12550 } 12551 if (!printed) { 12552 if (needSep) pw.println(); 12553 needSep = true; 12554 pw.println(" Bad processes:"); 12555 printedAnything = true; 12556 } 12557 BadProcessInfo info = uids.valueAt(i); 12558 pw.print(" Bad process "); pw.print(pname); 12559 pw.print(" uid "); pw.print(puid); 12560 pw.print(": crashed at time "); pw.println(info.time); 12561 if (info.shortMsg != null) { 12562 pw.print(" Short msg: "); pw.println(info.shortMsg); 12563 } 12564 if (info.longMsg != null) { 12565 pw.print(" Long msg: "); pw.println(info.longMsg); 12566 } 12567 if (info.stack != null) { 12568 pw.println(" Stack:"); 12569 int lastPos = 0; 12570 for (int pos=0; pos<info.stack.length(); pos++) { 12571 if (info.stack.charAt(pos) == '\n') { 12572 pw.print(" "); 12573 pw.write(info.stack, lastPos, pos-lastPos); 12574 pw.println(); 12575 lastPos = pos+1; 12576 } 12577 } 12578 if (lastPos < info.stack.length()) { 12579 pw.print(" "); 12580 pw.write(info.stack, lastPos, info.stack.length()-lastPos); 12581 pw.println(); 12582 } 12583 } 12584 } 12585 } 12586 } 12587 12588 if (dumpPackage == null) { 12589 pw.println(); 12590 needSep = false; 12591 pw.println(" mStartedUsers:"); 12592 for (int i=0; i<mStartedUsers.size(); i++) { 12593 UserStartedState uss = mStartedUsers.valueAt(i); 12594 pw.print(" User #"); pw.print(uss.mHandle.getIdentifier()); 12595 pw.print(": "); uss.dump("", pw); 12596 } 12597 pw.print(" mStartedUserArray: ["); 12598 for (int i=0; i<mStartedUserArray.length; i++) { 12599 if (i > 0) pw.print(", "); 12600 pw.print(mStartedUserArray[i]); 12601 } 12602 pw.println("]"); 12603 pw.print(" mUserLru: ["); 12604 for (int i=0; i<mUserLru.size(); i++) { 12605 if (i > 0) pw.print(", "); 12606 pw.print(mUserLru.get(i)); 12607 } 12608 pw.println("]"); 12609 if (dumpAll) { 12610 pw.print(" mStartedUserArray: "); pw.println(Arrays.toString(mStartedUserArray)); 12611 } 12612 synchronized (mUserProfileGroupIdsSelfLocked) { 12613 if (mUserProfileGroupIdsSelfLocked.size() > 0) { 12614 pw.println(" mUserProfileGroupIds:"); 12615 for (int i=0; i<mUserProfileGroupIdsSelfLocked.size(); i++) { 12616 pw.print(" User #"); 12617 pw.print(mUserProfileGroupIdsSelfLocked.keyAt(i)); 12618 pw.print(" -> profile #"); 12619 pw.println(mUserProfileGroupIdsSelfLocked.valueAt(i)); 12620 } 12621 } 12622 } 12623 } 12624 if (mHomeProcess != null && (dumpPackage == null 12625 || mHomeProcess.pkgList.containsKey(dumpPackage))) { 12626 if (needSep) { 12627 pw.println(); 12628 needSep = false; 12629 } 12630 pw.println(" mHomeProcess: " + mHomeProcess); 12631 } 12632 if (mPreviousProcess != null && (dumpPackage == null 12633 || mPreviousProcess.pkgList.containsKey(dumpPackage))) { 12634 if (needSep) { 12635 pw.println(); 12636 needSep = false; 12637 } 12638 pw.println(" mPreviousProcess: " + mPreviousProcess); 12639 } 12640 if (dumpAll) { 12641 StringBuilder sb = new StringBuilder(128); 12642 sb.append(" mPreviousProcessVisibleTime: "); 12643 TimeUtils.formatDuration(mPreviousProcessVisibleTime, sb); 12644 pw.println(sb); 12645 } 12646 if (mHeavyWeightProcess != null && (dumpPackage == null 12647 || mHeavyWeightProcess.pkgList.containsKey(dumpPackage))) { 12648 if (needSep) { 12649 pw.println(); 12650 needSep = false; 12651 } 12652 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 12653 } 12654 if (dumpPackage == null) { 12655 pw.println(" mConfiguration: " + mConfiguration); 12656 } 12657 if (dumpAll) { 12658 pw.println(" mConfigWillChange: " + getFocusedStack().mConfigWillChange); 12659 if (mCompatModePackages.getPackages().size() > 0) { 12660 boolean printed = false; 12661 for (Map.Entry<String, Integer> entry 12662 : mCompatModePackages.getPackages().entrySet()) { 12663 String pkg = entry.getKey(); 12664 int mode = entry.getValue(); 12665 if (dumpPackage != null && !dumpPackage.equals(pkg)) { 12666 continue; 12667 } 12668 if (!printed) { 12669 pw.println(" mScreenCompatPackages:"); 12670 printed = true; 12671 } 12672 pw.print(" "); pw.print(pkg); pw.print(": "); 12673 pw.print(mode); pw.println(); 12674 } 12675 } 12676 } 12677 if (dumpPackage == null) { 12678 if (mSleeping || mWentToSleep || mLockScreenShown) { 12679 pw.println(" mSleeping=" + mSleeping + " mWentToSleep=" + mWentToSleep 12680 + " mLockScreenShown " + mLockScreenShown); 12681 } 12682 if (mShuttingDown || mRunningVoice) { 12683 pw.print(" mShuttingDown=" + mShuttingDown + " mRunningVoice=" + mRunningVoice); 12684 } 12685 } 12686 if (mDebugApp != null || mOrigDebugApp != null || mDebugTransient 12687 || mOrigWaitForDebugger) { 12688 if (dumpPackage == null || dumpPackage.equals(mDebugApp) 12689 || dumpPackage.equals(mOrigDebugApp)) { 12690 if (needSep) { 12691 pw.println(); 12692 needSep = false; 12693 } 12694 pw.println(" mDebugApp=" + mDebugApp + "/orig=" + mOrigDebugApp 12695 + " mDebugTransient=" + mDebugTransient 12696 + " mOrigWaitForDebugger=" + mOrigWaitForDebugger); 12697 } 12698 } 12699 if (mOpenGlTraceApp != null) { 12700 if (dumpPackage == null || dumpPackage.equals(mOpenGlTraceApp)) { 12701 if (needSep) { 12702 pw.println(); 12703 needSep = false; 12704 } 12705 pw.println(" mOpenGlTraceApp=" + mOpenGlTraceApp); 12706 } 12707 } 12708 if (mProfileApp != null || mProfileProc != null || mProfileFile != null 12709 || mProfileFd != null) { 12710 if (dumpPackage == null || dumpPackage.equals(mProfileApp)) { 12711 if (needSep) { 12712 pw.println(); 12713 needSep = false; 12714 } 12715 pw.println(" mProfileApp=" + mProfileApp + " mProfileProc=" + mProfileProc); 12716 pw.println(" mProfileFile=" + mProfileFile + " mProfileFd=" + mProfileFd); 12717 pw.println(" mSamplingInterval=" + mSamplingInterval + " mAutoStopProfiler=" 12718 + mAutoStopProfiler); 12719 pw.println(" mProfileType=" + mProfileType); 12720 } 12721 } 12722 if (dumpPackage == null) { 12723 if (mAlwaysFinishActivities || mController != null) { 12724 pw.println(" mAlwaysFinishActivities=" + mAlwaysFinishActivities 12725 + " mController=" + mController); 12726 } 12727 if (dumpAll) { 12728 pw.println(" Total persistent processes: " + numPers); 12729 pw.println(" mProcessesReady=" + mProcessesReady 12730 + " mSystemReady=" + mSystemReady); 12731 pw.println(" mBooting=" + mBooting 12732 + " mBooted=" + mBooted 12733 + " mFactoryTest=" + mFactoryTest); 12734 pw.print(" mLastPowerCheckRealtime="); 12735 TimeUtils.formatDuration(mLastPowerCheckRealtime, pw); 12736 pw.println(""); 12737 pw.print(" mLastPowerCheckUptime="); 12738 TimeUtils.formatDuration(mLastPowerCheckUptime, pw); 12739 pw.println(""); 12740 pw.println(" mGoingToSleep=" + mStackSupervisor.mGoingToSleep); 12741 pw.println(" mLaunchingActivity=" + mStackSupervisor.mLaunchingActivity); 12742 pw.println(" mAdjSeq=" + mAdjSeq + " mLruSeq=" + mLruSeq); 12743 pw.println(" mNumNonCachedProcs=" + mNumNonCachedProcs 12744 + " (" + mLruProcesses.size() + " total)" 12745 + " mNumCachedHiddenProcs=" + mNumCachedHiddenProcs 12746 + " mNumServiceProcs=" + mNumServiceProcs 12747 + " mNewNumServiceProcs=" + mNewNumServiceProcs); 12748 pw.println(" mAllowLowerMemLevel=" + mAllowLowerMemLevel 12749 + " mLastMemoryLevel" + mLastMemoryLevel 12750 + " mLastNumProcesses" + mLastNumProcesses); 12751 long now = SystemClock.uptimeMillis(); 12752 pw.print(" mLastIdleTime="); 12753 TimeUtils.formatDuration(now, mLastIdleTime, pw); 12754 pw.print(" mLowRamSinceLastIdle="); 12755 TimeUtils.formatDuration(getLowRamTimeSinceIdle(now), pw); 12756 pw.println(); 12757 } 12758 } 12759 12760 if (!printedAnything) { 12761 pw.println(" (nothing)"); 12762 } 12763 } 12764 12765 boolean dumpProcessesToGc(FileDescriptor fd, PrintWriter pw, String[] args, 12766 int opti, boolean needSep, boolean dumpAll, String dumpPackage) { 12767 if (mProcessesToGc.size() > 0) { 12768 boolean printed = false; 12769 long now = SystemClock.uptimeMillis(); 12770 for (int i=0; i<mProcessesToGc.size(); i++) { 12771 ProcessRecord proc = mProcessesToGc.get(i); 12772 if (dumpPackage != null && !dumpPackage.equals(proc.info.packageName)) { 12773 continue; 12774 } 12775 if (!printed) { 12776 if (needSep) pw.println(); 12777 needSep = true; 12778 pw.println(" Processes that are waiting to GC:"); 12779 printed = true; 12780 } 12781 pw.print(" Process "); pw.println(proc); 12782 pw.print(" lowMem="); pw.print(proc.reportLowMemory); 12783 pw.print(", last gced="); 12784 pw.print(now-proc.lastRequestedGc); 12785 pw.print(" ms ago, last lowMem="); 12786 pw.print(now-proc.lastLowMemory); 12787 pw.println(" ms ago"); 12788 12789 } 12790 } 12791 return needSep; 12792 } 12793 12794 void printOomLevel(PrintWriter pw, String name, int adj) { 12795 pw.print(" "); 12796 if (adj >= 0) { 12797 pw.print(' '); 12798 if (adj < 10) pw.print(' '); 12799 } else { 12800 if (adj > -10) pw.print(' '); 12801 } 12802 pw.print(adj); 12803 pw.print(": "); 12804 pw.print(name); 12805 pw.print(" ("); 12806 pw.print(mProcessList.getMemLevel(adj)/1024); 12807 pw.println(" kB)"); 12808 } 12809 12810 boolean dumpOomLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12811 int opti, boolean dumpAll) { 12812 boolean needSep = false; 12813 12814 if (mLruProcesses.size() > 0) { 12815 if (needSep) pw.println(); 12816 needSep = true; 12817 pw.println(" OOM levels:"); 12818 printOomLevel(pw, "SYSTEM_ADJ", ProcessList.SYSTEM_ADJ); 12819 printOomLevel(pw, "PERSISTENT_PROC_ADJ", ProcessList.PERSISTENT_PROC_ADJ); 12820 printOomLevel(pw, "FOREGROUND_APP_ADJ", ProcessList.FOREGROUND_APP_ADJ); 12821 printOomLevel(pw, "VISIBLE_APP_ADJ", ProcessList.VISIBLE_APP_ADJ); 12822 printOomLevel(pw, "PERCEPTIBLE_APP_ADJ", ProcessList.PERCEPTIBLE_APP_ADJ); 12823 printOomLevel(pw, "BACKUP_APP_ADJ", ProcessList.BACKUP_APP_ADJ); 12824 printOomLevel(pw, "HEAVY_WEIGHT_APP_ADJ", ProcessList.HEAVY_WEIGHT_APP_ADJ); 12825 printOomLevel(pw, "SERVICE_ADJ", ProcessList.SERVICE_ADJ); 12826 printOomLevel(pw, "HOME_APP_ADJ", ProcessList.HOME_APP_ADJ); 12827 printOomLevel(pw, "PREVIOUS_APP_ADJ", ProcessList.PREVIOUS_APP_ADJ); 12828 printOomLevel(pw, "SERVICE_B_ADJ", ProcessList.SERVICE_B_ADJ); 12829 printOomLevel(pw, "CACHED_APP_MIN_ADJ", ProcessList.CACHED_APP_MIN_ADJ); 12830 printOomLevel(pw, "CACHED_APP_MAX_ADJ", ProcessList.CACHED_APP_MAX_ADJ); 12831 12832 if (needSep) pw.println(); 12833 pw.print(" Process OOM control ("); pw.print(mLruProcesses.size()); 12834 pw.print(" total, non-act at "); 12835 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 12836 pw.print(", non-svc at "); 12837 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 12838 pw.println("):"); 12839 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", true, null); 12840 needSep = true; 12841 } 12842 12843 dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, null); 12844 12845 pw.println(); 12846 pw.println(" mHomeProcess: " + mHomeProcess); 12847 pw.println(" mPreviousProcess: " + mPreviousProcess); 12848 if (mHeavyWeightProcess != null) { 12849 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 12850 } 12851 12852 return true; 12853 } 12854 12855 /** 12856 * There are three ways to call this: 12857 * - no provider specified: dump all the providers 12858 * - a flattened component name that matched an existing provider was specified as the 12859 * first arg: dump that one provider 12860 * - the first arg isn't the flattened component name of an existing provider: 12861 * dump all providers whose component contains the first arg as a substring 12862 */ 12863 protected boolean dumpProvider(FileDescriptor fd, PrintWriter pw, String name, String[] args, 12864 int opti, boolean dumpAll) { 12865 return mProviderMap.dumpProvider(fd, pw, name, args, opti, dumpAll); 12866 } 12867 12868 static class ItemMatcher { 12869 ArrayList<ComponentName> components; 12870 ArrayList<String> strings; 12871 ArrayList<Integer> objects; 12872 boolean all; 12873 12874 ItemMatcher() { 12875 all = true; 12876 } 12877 12878 void build(String name) { 12879 ComponentName componentName = ComponentName.unflattenFromString(name); 12880 if (componentName != null) { 12881 if (components == null) { 12882 components = new ArrayList<ComponentName>(); 12883 } 12884 components.add(componentName); 12885 all = false; 12886 } else { 12887 int objectId = 0; 12888 // Not a '/' separated full component name; maybe an object ID? 12889 try { 12890 objectId = Integer.parseInt(name, 16); 12891 if (objects == null) { 12892 objects = new ArrayList<Integer>(); 12893 } 12894 objects.add(objectId); 12895 all = false; 12896 } catch (RuntimeException e) { 12897 // Not an integer; just do string match. 12898 if (strings == null) { 12899 strings = new ArrayList<String>(); 12900 } 12901 strings.add(name); 12902 all = false; 12903 } 12904 } 12905 } 12906 12907 int build(String[] args, int opti) { 12908 for (; opti<args.length; opti++) { 12909 String name = args[opti]; 12910 if ("--".equals(name)) { 12911 return opti+1; 12912 } 12913 build(name); 12914 } 12915 return opti; 12916 } 12917 12918 boolean match(Object object, ComponentName comp) { 12919 if (all) { 12920 return true; 12921 } 12922 if (components != null) { 12923 for (int i=0; i<components.size(); i++) { 12924 if (components.get(i).equals(comp)) { 12925 return true; 12926 } 12927 } 12928 } 12929 if (objects != null) { 12930 for (int i=0; i<objects.size(); i++) { 12931 if (System.identityHashCode(object) == objects.get(i)) { 12932 return true; 12933 } 12934 } 12935 } 12936 if (strings != null) { 12937 String flat = comp.flattenToString(); 12938 for (int i=0; i<strings.size(); i++) { 12939 if (flat.contains(strings.get(i))) { 12940 return true; 12941 } 12942 } 12943 } 12944 return false; 12945 } 12946 } 12947 12948 /** 12949 * There are three things that cmd can be: 12950 * - a flattened component name that matches an existing activity 12951 * - the cmd arg isn't the flattened component name of an existing activity: 12952 * dump all activity whose component contains the cmd as a substring 12953 * - A hex number of the ActivityRecord object instance. 12954 */ 12955 protected boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name, String[] args, 12956 int opti, boolean dumpAll) { 12957 ArrayList<ActivityRecord> activities; 12958 12959 synchronized (this) { 12960 activities = mStackSupervisor.getDumpActivitiesLocked(name); 12961 } 12962 12963 if (activities.size() <= 0) { 12964 return false; 12965 } 12966 12967 String[] newArgs = new String[args.length - opti]; 12968 System.arraycopy(args, opti, newArgs, 0, args.length - opti); 12969 12970 TaskRecord lastTask = null; 12971 boolean needSep = false; 12972 for (int i=activities.size()-1; i>=0; i--) { 12973 ActivityRecord r = activities.get(i); 12974 if (needSep) { 12975 pw.println(); 12976 } 12977 needSep = true; 12978 synchronized (this) { 12979 if (lastTask != r.task) { 12980 lastTask = r.task; 12981 pw.print("TASK "); pw.print(lastTask.affinity); 12982 pw.print(" id="); pw.println(lastTask.taskId); 12983 if (dumpAll) { 12984 lastTask.dump(pw, " "); 12985 } 12986 } 12987 } 12988 dumpActivity(" ", fd, pw, activities.get(i), newArgs, dumpAll); 12989 } 12990 return true; 12991 } 12992 12993 /** 12994 * Invokes IApplicationThread.dumpActivity() on the thread of the specified activity if 12995 * there is a thread associated with the activity. 12996 */ 12997 private void dumpActivity(String prefix, FileDescriptor fd, PrintWriter pw, 12998 final ActivityRecord r, String[] args, boolean dumpAll) { 12999 String innerPrefix = prefix + " "; 13000 synchronized (this) { 13001 pw.print(prefix); pw.print("ACTIVITY "); pw.print(r.shortComponentName); 13002 pw.print(" "); pw.print(Integer.toHexString(System.identityHashCode(r))); 13003 pw.print(" pid="); 13004 if (r.app != null) pw.println(r.app.pid); 13005 else pw.println("(not running)"); 13006 if (dumpAll) { 13007 r.dump(pw, innerPrefix); 13008 } 13009 } 13010 if (r.app != null && r.app.thread != null) { 13011 // flush anything that is already in the PrintWriter since the thread is going 13012 // to write to the file descriptor directly 13013 pw.flush(); 13014 try { 13015 TransferPipe tp = new TransferPipe(); 13016 try { 13017 r.app.thread.dumpActivity(tp.getWriteFd().getFileDescriptor(), 13018 r.appToken, innerPrefix, args); 13019 tp.go(fd); 13020 } finally { 13021 tp.kill(); 13022 } 13023 } catch (IOException e) { 13024 pw.println(innerPrefix + "Failure while dumping the activity: " + e); 13025 } catch (RemoteException e) { 13026 pw.println(innerPrefix + "Got a RemoteException while dumping the activity"); 13027 } 13028 } 13029 } 13030 13031 void dumpBroadcastsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 13032 int opti, boolean dumpAll, String dumpPackage) { 13033 boolean needSep = false; 13034 boolean onlyHistory = false; 13035 boolean printedAnything = false; 13036 13037 if ("history".equals(dumpPackage)) { 13038 if (opti < args.length && "-s".equals(args[opti])) { 13039 dumpAll = false; 13040 } 13041 onlyHistory = true; 13042 dumpPackage = null; 13043 } 13044 13045 pw.println("ACTIVITY MANAGER BROADCAST STATE (dumpsys activity broadcasts)"); 13046 if (!onlyHistory && dumpAll) { 13047 if (mRegisteredReceivers.size() > 0) { 13048 boolean printed = false; 13049 Iterator it = mRegisteredReceivers.values().iterator(); 13050 while (it.hasNext()) { 13051 ReceiverList r = (ReceiverList)it.next(); 13052 if (dumpPackage != null && (r.app == null || 13053 !dumpPackage.equals(r.app.info.packageName))) { 13054 continue; 13055 } 13056 if (!printed) { 13057 pw.println(" Registered Receivers:"); 13058 needSep = true; 13059 printed = true; 13060 printedAnything = true; 13061 } 13062 pw.print(" * "); pw.println(r); 13063 r.dump(pw, " "); 13064 } 13065 } 13066 13067 if (mReceiverResolver.dump(pw, needSep ? 13068 "\n Receiver Resolver Table:" : " Receiver Resolver Table:", 13069 " ", dumpPackage, false)) { 13070 needSep = true; 13071 printedAnything = true; 13072 } 13073 } 13074 13075 for (BroadcastQueue q : mBroadcastQueues) { 13076 needSep = q.dumpLocked(fd, pw, args, opti, dumpAll, dumpPackage, needSep); 13077 printedAnything |= needSep; 13078 } 13079 13080 needSep = true; 13081 13082 if (!onlyHistory && mStickyBroadcasts != null && dumpPackage == null) { 13083 for (int user=0; user<mStickyBroadcasts.size(); user++) { 13084 if (needSep) { 13085 pw.println(); 13086 } 13087 needSep = true; 13088 printedAnything = true; 13089 pw.print(" Sticky broadcasts for user "); 13090 pw.print(mStickyBroadcasts.keyAt(user)); pw.println(":"); 13091 StringBuilder sb = new StringBuilder(128); 13092 for (Map.Entry<String, ArrayList<Intent>> ent 13093 : mStickyBroadcasts.valueAt(user).entrySet()) { 13094 pw.print(" * Sticky action "); pw.print(ent.getKey()); 13095 if (dumpAll) { 13096 pw.println(":"); 13097 ArrayList<Intent> intents = ent.getValue(); 13098 final int N = intents.size(); 13099 for (int i=0; i<N; i++) { 13100 sb.setLength(0); 13101 sb.append(" Intent: "); 13102 intents.get(i).toShortString(sb, false, true, false, false); 13103 pw.println(sb.toString()); 13104 Bundle bundle = intents.get(i).getExtras(); 13105 if (bundle != null) { 13106 pw.print(" "); 13107 pw.println(bundle.toString()); 13108 } 13109 } 13110 } else { 13111 pw.println(""); 13112 } 13113 } 13114 } 13115 } 13116 13117 if (!onlyHistory && dumpAll) { 13118 pw.println(); 13119 for (BroadcastQueue queue : mBroadcastQueues) { 13120 pw.println(" mBroadcastsScheduled [" + queue.mQueueName + "]=" 13121 + queue.mBroadcastsScheduled); 13122 } 13123 pw.println(" mHandler:"); 13124 mHandler.dump(new PrintWriterPrinter(pw), " "); 13125 needSep = true; 13126 printedAnything = true; 13127 } 13128 13129 if (!printedAnything) { 13130 pw.println(" (nothing)"); 13131 } 13132 } 13133 13134 void dumpProvidersLocked(FileDescriptor fd, PrintWriter pw, String[] args, 13135 int opti, boolean dumpAll, String dumpPackage) { 13136 boolean needSep; 13137 boolean printedAnything = false; 13138 13139 ItemMatcher matcher = new ItemMatcher(); 13140 matcher.build(args, opti); 13141 13142 pw.println("ACTIVITY MANAGER CONTENT PROVIDERS (dumpsys activity providers)"); 13143 13144 needSep = mProviderMap.dumpProvidersLocked(pw, dumpAll, dumpPackage); 13145 printedAnything |= needSep; 13146 13147 if (mLaunchingProviders.size() > 0) { 13148 boolean printed = false; 13149 for (int i=mLaunchingProviders.size()-1; i>=0; i--) { 13150 ContentProviderRecord r = mLaunchingProviders.get(i); 13151 if (dumpPackage != null && !dumpPackage.equals(r.name.getPackageName())) { 13152 continue; 13153 } 13154 if (!printed) { 13155 if (needSep) pw.println(); 13156 needSep = true; 13157 pw.println(" Launching content providers:"); 13158 printed = true; 13159 printedAnything = true; 13160 } 13161 pw.print(" Launching #"); pw.print(i); pw.print(": "); 13162 pw.println(r); 13163 } 13164 } 13165 13166 if (mGrantedUriPermissions.size() > 0) { 13167 boolean printed = false; 13168 int dumpUid = -2; 13169 if (dumpPackage != null) { 13170 try { 13171 dumpUid = mContext.getPackageManager().getPackageUid(dumpPackage, 0); 13172 } catch (NameNotFoundException e) { 13173 dumpUid = -1; 13174 } 13175 } 13176 for (int i=0; i<mGrantedUriPermissions.size(); i++) { 13177 int uid = mGrantedUriPermissions.keyAt(i); 13178 if (dumpUid >= -1 && UserHandle.getAppId(uid) != dumpUid) { 13179 continue; 13180 } 13181 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 13182 if (!printed) { 13183 if (needSep) pw.println(); 13184 needSep = true; 13185 pw.println(" Granted Uri Permissions:"); 13186 printed = true; 13187 printedAnything = true; 13188 } 13189 pw.print(" * UID "); pw.print(uid); pw.println(" holds:"); 13190 for (UriPermission perm : perms.values()) { 13191 pw.print(" "); pw.println(perm); 13192 if (dumpAll) { 13193 perm.dump(pw, " "); 13194 } 13195 } 13196 } 13197 } 13198 13199 if (!printedAnything) { 13200 pw.println(" (nothing)"); 13201 } 13202 } 13203 13204 void dumpPendingIntentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 13205 int opti, boolean dumpAll, String dumpPackage) { 13206 boolean printed = false; 13207 13208 pw.println("ACTIVITY MANAGER PENDING INTENTS (dumpsys activity intents)"); 13209 13210 if (mIntentSenderRecords.size() > 0) { 13211 Iterator<WeakReference<PendingIntentRecord>> it 13212 = mIntentSenderRecords.values().iterator(); 13213 while (it.hasNext()) { 13214 WeakReference<PendingIntentRecord> ref = it.next(); 13215 PendingIntentRecord rec = ref != null ? ref.get(): null; 13216 if (dumpPackage != null && (rec == null 13217 || !dumpPackage.equals(rec.key.packageName))) { 13218 continue; 13219 } 13220 printed = true; 13221 if (rec != null) { 13222 pw.print(" * "); pw.println(rec); 13223 if (dumpAll) { 13224 rec.dump(pw, " "); 13225 } 13226 } else { 13227 pw.print(" * "); pw.println(ref); 13228 } 13229 } 13230 } 13231 13232 if (!printed) { 13233 pw.println(" (nothing)"); 13234 } 13235 } 13236 13237 private static final int dumpProcessList(PrintWriter pw, 13238 ActivityManagerService service, List list, 13239 String prefix, String normalLabel, String persistentLabel, 13240 String dumpPackage) { 13241 int numPers = 0; 13242 final int N = list.size()-1; 13243 for (int i=N; i>=0; i--) { 13244 ProcessRecord r = (ProcessRecord)list.get(i); 13245 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 13246 continue; 13247 } 13248 pw.println(String.format("%s%s #%2d: %s", 13249 prefix, (r.persistent ? persistentLabel : normalLabel), 13250 i, r.toString())); 13251 if (r.persistent) { 13252 numPers++; 13253 } 13254 } 13255 return numPers; 13256 } 13257 13258 private static final boolean dumpProcessOomList(PrintWriter pw, 13259 ActivityManagerService service, List<ProcessRecord> origList, 13260 String prefix, String normalLabel, String persistentLabel, 13261 boolean inclDetails, String dumpPackage) { 13262 13263 ArrayList<Pair<ProcessRecord, Integer>> list 13264 = new ArrayList<Pair<ProcessRecord, Integer>>(origList.size()); 13265 for (int i=0; i<origList.size(); i++) { 13266 ProcessRecord r = origList.get(i); 13267 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 13268 continue; 13269 } 13270 list.add(new Pair<ProcessRecord, Integer>(origList.get(i), i)); 13271 } 13272 13273 if (list.size() <= 0) { 13274 return false; 13275 } 13276 13277 Comparator<Pair<ProcessRecord, Integer>> comparator 13278 = new Comparator<Pair<ProcessRecord, Integer>>() { 13279 @Override 13280 public int compare(Pair<ProcessRecord, Integer> object1, 13281 Pair<ProcessRecord, Integer> object2) { 13282 if (object1.first.setAdj != object2.first.setAdj) { 13283 return object1.first.setAdj > object2.first.setAdj ? -1 : 1; 13284 } 13285 if (object1.second.intValue() != object2.second.intValue()) { 13286 return object1.second.intValue() > object2.second.intValue() ? -1 : 1; 13287 } 13288 return 0; 13289 } 13290 }; 13291 13292 Collections.sort(list, comparator); 13293 13294 final long curRealtime = SystemClock.elapsedRealtime(); 13295 final long realtimeSince = curRealtime - service.mLastPowerCheckRealtime; 13296 final long curUptime = SystemClock.uptimeMillis(); 13297 final long uptimeSince = curUptime - service.mLastPowerCheckUptime; 13298 13299 for (int i=list.size()-1; i>=0; i--) { 13300 ProcessRecord r = list.get(i).first; 13301 String oomAdj = ProcessList.makeOomAdjString(r.setAdj); 13302 char schedGroup; 13303 switch (r.setSchedGroup) { 13304 case Process.THREAD_GROUP_BG_NONINTERACTIVE: 13305 schedGroup = 'B'; 13306 break; 13307 case Process.THREAD_GROUP_DEFAULT: 13308 schedGroup = 'F'; 13309 break; 13310 default: 13311 schedGroup = '?'; 13312 break; 13313 } 13314 char foreground; 13315 if (r.foregroundActivities) { 13316 foreground = 'A'; 13317 } else if (r.foregroundServices) { 13318 foreground = 'S'; 13319 } else { 13320 foreground = ' '; 13321 } 13322 String procState = ProcessList.makeProcStateString(r.curProcState); 13323 pw.print(prefix); 13324 pw.print(r.persistent ? persistentLabel : normalLabel); 13325 pw.print(" #"); 13326 int num = (origList.size()-1)-list.get(i).second; 13327 if (num < 10) pw.print(' '); 13328 pw.print(num); 13329 pw.print(": "); 13330 pw.print(oomAdj); 13331 pw.print(' '); 13332 pw.print(schedGroup); 13333 pw.print('/'); 13334 pw.print(foreground); 13335 pw.print('/'); 13336 pw.print(procState); 13337 pw.print(" trm:"); 13338 if (r.trimMemoryLevel < 10) pw.print(' '); 13339 pw.print(r.trimMemoryLevel); 13340 pw.print(' '); 13341 pw.print(r.toShortString()); 13342 pw.print(" ("); 13343 pw.print(r.adjType); 13344 pw.println(')'); 13345 if (r.adjSource != null || r.adjTarget != null) { 13346 pw.print(prefix); 13347 pw.print(" "); 13348 if (r.adjTarget instanceof ComponentName) { 13349 pw.print(((ComponentName)r.adjTarget).flattenToShortString()); 13350 } else if (r.adjTarget != null) { 13351 pw.print(r.adjTarget.toString()); 13352 } else { 13353 pw.print("{null}"); 13354 } 13355 pw.print("<="); 13356 if (r.adjSource instanceof ProcessRecord) { 13357 pw.print("Proc{"); 13358 pw.print(((ProcessRecord)r.adjSource).toShortString()); 13359 pw.println("}"); 13360 } else if (r.adjSource != null) { 13361 pw.println(r.adjSource.toString()); 13362 } else { 13363 pw.println("{null}"); 13364 } 13365 } 13366 if (inclDetails) { 13367 pw.print(prefix); 13368 pw.print(" "); 13369 pw.print("oom: max="); pw.print(r.maxAdj); 13370 pw.print(" curRaw="); pw.print(r.curRawAdj); 13371 pw.print(" setRaw="); pw.print(r.setRawAdj); 13372 pw.print(" cur="); pw.print(r.curAdj); 13373 pw.print(" set="); pw.println(r.setAdj); 13374 pw.print(prefix); 13375 pw.print(" "); 13376 pw.print("state: cur="); pw.print(ProcessList.makeProcStateString(r.curProcState)); 13377 pw.print(" set="); pw.print(ProcessList.makeProcStateString(r.setProcState)); 13378 pw.print(" lastPss="); pw.print(r.lastPss); 13379 pw.print(" lastCachedPss="); pw.println(r.lastCachedPss); 13380 pw.print(prefix); 13381 pw.print(" "); 13382 pw.print("cached="); pw.print(r.cached); 13383 pw.print(" empty="); pw.print(r.empty); 13384 pw.print(" hasAboveClient="); pw.println(r.hasAboveClient); 13385 13386 if (r.setProcState >= ActivityManager.PROCESS_STATE_SERVICE) { 13387 if (r.lastWakeTime != 0) { 13388 long wtime; 13389 BatteryStatsImpl stats = service.mBatteryStatsService.getActiveStatistics(); 13390 synchronized (stats) { 13391 wtime = stats.getProcessWakeTime(r.info.uid, 13392 r.pid, curRealtime); 13393 } 13394 long timeUsed = wtime - r.lastWakeTime; 13395 pw.print(prefix); 13396 pw.print(" "); 13397 pw.print("keep awake over "); 13398 TimeUtils.formatDuration(realtimeSince, pw); 13399 pw.print(" used "); 13400 TimeUtils.formatDuration(timeUsed, pw); 13401 pw.print(" ("); 13402 pw.print((timeUsed*100)/realtimeSince); 13403 pw.println("%)"); 13404 } 13405 if (r.lastCpuTime != 0) { 13406 long timeUsed = r.curCpuTime - r.lastCpuTime; 13407 pw.print(prefix); 13408 pw.print(" "); 13409 pw.print("run cpu over "); 13410 TimeUtils.formatDuration(uptimeSince, pw); 13411 pw.print(" used "); 13412 TimeUtils.formatDuration(timeUsed, pw); 13413 pw.print(" ("); 13414 pw.print((timeUsed*100)/uptimeSince); 13415 pw.println("%)"); 13416 } 13417 } 13418 } 13419 } 13420 return true; 13421 } 13422 13423 ArrayList<ProcessRecord> collectProcesses(PrintWriter pw, int start, String[] args) { 13424 ArrayList<ProcessRecord> procs; 13425 synchronized (this) { 13426 if (args != null && args.length > start 13427 && args[start].charAt(0) != '-') { 13428 procs = new ArrayList<ProcessRecord>(); 13429 int pid = -1; 13430 try { 13431 pid = Integer.parseInt(args[start]); 13432 } catch (NumberFormatException e) { 13433 } 13434 for (int i=mLruProcesses.size()-1; i>=0; i--) { 13435 ProcessRecord proc = mLruProcesses.get(i); 13436 if (proc.pid == pid) { 13437 procs.add(proc); 13438 } else if (proc.processName.equals(args[start])) { 13439 procs.add(proc); 13440 } 13441 } 13442 if (procs.size() <= 0) { 13443 return null; 13444 } 13445 } else { 13446 procs = new ArrayList<ProcessRecord>(mLruProcesses); 13447 } 13448 } 13449 return procs; 13450 } 13451 13452 final void dumpGraphicsHardwareUsage(FileDescriptor fd, 13453 PrintWriter pw, String[] args) { 13454 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 13455 if (procs == null) { 13456 pw.println("No process found for: " + args[0]); 13457 return; 13458 } 13459 13460 long uptime = SystemClock.uptimeMillis(); 13461 long realtime = SystemClock.elapsedRealtime(); 13462 pw.println("Applications Graphics Acceleration Info:"); 13463 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 13464 13465 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 13466 ProcessRecord r = procs.get(i); 13467 if (r.thread != null) { 13468 pw.println("\n** Graphics info for pid " + r.pid + " [" + r.processName + "] **"); 13469 pw.flush(); 13470 try { 13471 TransferPipe tp = new TransferPipe(); 13472 try { 13473 r.thread.dumpGfxInfo(tp.getWriteFd().getFileDescriptor(), args); 13474 tp.go(fd); 13475 } finally { 13476 tp.kill(); 13477 } 13478 } catch (IOException e) { 13479 pw.println("Failure while dumping the app: " + r); 13480 pw.flush(); 13481 } catch (RemoteException e) { 13482 pw.println("Got a RemoteException while dumping the app " + r); 13483 pw.flush(); 13484 } 13485 } 13486 } 13487 } 13488 13489 final void dumpDbInfo(FileDescriptor fd, PrintWriter pw, String[] args) { 13490 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 13491 if (procs == null) { 13492 pw.println("No process found for: " + args[0]); 13493 return; 13494 } 13495 13496 pw.println("Applications Database Info:"); 13497 13498 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 13499 ProcessRecord r = procs.get(i); 13500 if (r.thread != null) { 13501 pw.println("\n** Database info for pid " + r.pid + " [" + r.processName + "] **"); 13502 pw.flush(); 13503 try { 13504 TransferPipe tp = new TransferPipe(); 13505 try { 13506 r.thread.dumpDbInfo(tp.getWriteFd().getFileDescriptor(), args); 13507 tp.go(fd); 13508 } finally { 13509 tp.kill(); 13510 } 13511 } catch (IOException e) { 13512 pw.println("Failure while dumping the app: " + r); 13513 pw.flush(); 13514 } catch (RemoteException e) { 13515 pw.println("Got a RemoteException while dumping the app " + r); 13516 pw.flush(); 13517 } 13518 } 13519 } 13520 } 13521 13522 final static class MemItem { 13523 final boolean isProc; 13524 final String label; 13525 final String shortLabel; 13526 final long pss; 13527 final int id; 13528 final boolean hasActivities; 13529 ArrayList<MemItem> subitems; 13530 13531 public MemItem(String _label, String _shortLabel, long _pss, int _id, 13532 boolean _hasActivities) { 13533 isProc = true; 13534 label = _label; 13535 shortLabel = _shortLabel; 13536 pss = _pss; 13537 id = _id; 13538 hasActivities = _hasActivities; 13539 } 13540 13541 public MemItem(String _label, String _shortLabel, long _pss, int _id) { 13542 isProc = false; 13543 label = _label; 13544 shortLabel = _shortLabel; 13545 pss = _pss; 13546 id = _id; 13547 hasActivities = false; 13548 } 13549 } 13550 13551 static final void dumpMemItems(PrintWriter pw, String prefix, String tag, 13552 ArrayList<MemItem> items, boolean sort, boolean isCompact) { 13553 if (sort && !isCompact) { 13554 Collections.sort(items, new Comparator<MemItem>() { 13555 @Override 13556 public int compare(MemItem lhs, MemItem rhs) { 13557 if (lhs.pss < rhs.pss) { 13558 return 1; 13559 } else if (lhs.pss > rhs.pss) { 13560 return -1; 13561 } 13562 return 0; 13563 } 13564 }); 13565 } 13566 13567 for (int i=0; i<items.size(); i++) { 13568 MemItem mi = items.get(i); 13569 if (!isCompact) { 13570 pw.print(prefix); pw.printf("%7d kB: ", mi.pss); pw.println(mi.label); 13571 } else if (mi.isProc) { 13572 pw.print("proc,"); pw.print(tag); pw.print(","); pw.print(mi.shortLabel); 13573 pw.print(","); pw.print(mi.id); pw.print(","); pw.print(mi.pss); 13574 pw.println(mi.hasActivities ? ",a" : ",e"); 13575 } else { 13576 pw.print(tag); pw.print(","); pw.print(mi.shortLabel); pw.print(","); 13577 pw.println(mi.pss); 13578 } 13579 if (mi.subitems != null) { 13580 dumpMemItems(pw, prefix + " ", mi.shortLabel, mi.subitems, 13581 true, isCompact); 13582 } 13583 } 13584 } 13585 13586 // These are in KB. 13587 static final long[] DUMP_MEM_BUCKETS = new long[] { 13588 5*1024, 7*1024, 10*1024, 15*1024, 20*1024, 30*1024, 40*1024, 80*1024, 13589 120*1024, 160*1024, 200*1024, 13590 250*1024, 300*1024, 350*1024, 400*1024, 500*1024, 600*1024, 800*1024, 13591 1*1024*1024, 2*1024*1024, 5*1024*1024, 10*1024*1024, 20*1024*1024 13592 }; 13593 13594 static final void appendMemBucket(StringBuilder out, long memKB, String label, 13595 boolean stackLike) { 13596 int start = label.lastIndexOf('.'); 13597 if (start >= 0) start++; 13598 else start = 0; 13599 int end = label.length(); 13600 for (int i=0; i<DUMP_MEM_BUCKETS.length; i++) { 13601 if (DUMP_MEM_BUCKETS[i] >= memKB) { 13602 long bucket = DUMP_MEM_BUCKETS[i]/1024; 13603 out.append(bucket); 13604 out.append(stackLike ? "MB." : "MB "); 13605 out.append(label, start, end); 13606 return; 13607 } 13608 } 13609 out.append(memKB/1024); 13610 out.append(stackLike ? "MB." : "MB "); 13611 out.append(label, start, end); 13612 } 13613 13614 static final int[] DUMP_MEM_OOM_ADJ = new int[] { 13615 ProcessList.NATIVE_ADJ, 13616 ProcessList.SYSTEM_ADJ, ProcessList.PERSISTENT_PROC_ADJ, ProcessList.FOREGROUND_APP_ADJ, 13617 ProcessList.VISIBLE_APP_ADJ, ProcessList.PERCEPTIBLE_APP_ADJ, 13618 ProcessList.BACKUP_APP_ADJ, ProcessList.HEAVY_WEIGHT_APP_ADJ, 13619 ProcessList.SERVICE_ADJ, ProcessList.HOME_APP_ADJ, 13620 ProcessList.PREVIOUS_APP_ADJ, ProcessList.SERVICE_B_ADJ, ProcessList.CACHED_APP_MAX_ADJ 13621 }; 13622 static final String[] DUMP_MEM_OOM_LABEL = new String[] { 13623 "Native", 13624 "System", "Persistent", "Foreground", 13625 "Visible", "Perceptible", 13626 "Heavy Weight", "Backup", 13627 "A Services", "Home", 13628 "Previous", "B Services", "Cached" 13629 }; 13630 static final String[] DUMP_MEM_OOM_COMPACT_LABEL = new String[] { 13631 "native", 13632 "sys", "pers", "fore", 13633 "vis", "percept", 13634 "heavy", "backup", 13635 "servicea", "home", 13636 "prev", "serviceb", "cached" 13637 }; 13638 13639 private final void dumpApplicationMemoryUsageHeader(PrintWriter pw, long uptime, 13640 long realtime, boolean isCheckinRequest, boolean isCompact) { 13641 if (isCheckinRequest || isCompact) { 13642 // short checkin version 13643 pw.print("time,"); pw.print(uptime); pw.print(","); pw.println(realtime); 13644 } else { 13645 pw.println("Applications Memory Usage (kB):"); 13646 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 13647 } 13648 } 13649 13650 final void dumpApplicationMemoryUsage(FileDescriptor fd, 13651 PrintWriter pw, String prefix, String[] args, boolean brief, PrintWriter categoryPw) { 13652 boolean dumpDetails = false; 13653 boolean dumpFullDetails = false; 13654 boolean dumpDalvik = false; 13655 boolean oomOnly = false; 13656 boolean isCompact = false; 13657 boolean localOnly = false; 13658 13659 int opti = 0; 13660 while (opti < args.length) { 13661 String opt = args[opti]; 13662 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 13663 break; 13664 } 13665 opti++; 13666 if ("-a".equals(opt)) { 13667 dumpDetails = true; 13668 dumpFullDetails = true; 13669 dumpDalvik = true; 13670 } else if ("-d".equals(opt)) { 13671 dumpDalvik = true; 13672 } else if ("-c".equals(opt)) { 13673 isCompact = true; 13674 } else if ("--oom".equals(opt)) { 13675 oomOnly = true; 13676 } else if ("--local".equals(opt)) { 13677 localOnly = true; 13678 } else if ("-h".equals(opt)) { 13679 pw.println("meminfo dump options: [-a] [-d] [-c] [--oom] [process]"); 13680 pw.println(" -a: include all available information for each process."); 13681 pw.println(" -d: include dalvik details when dumping process details."); 13682 pw.println(" -c: dump in a compact machine-parseable representation."); 13683 pw.println(" --oom: only show processes organized by oom adj."); 13684 pw.println(" --local: only collect details locally, don't call process."); 13685 pw.println("If [process] is specified it can be the name or "); 13686 pw.println("pid of a specific process to dump."); 13687 return; 13688 } else { 13689 pw.println("Unknown argument: " + opt + "; use -h for help"); 13690 } 13691 } 13692 13693 final boolean isCheckinRequest = scanArgs(args, "--checkin"); 13694 long uptime = SystemClock.uptimeMillis(); 13695 long realtime = SystemClock.elapsedRealtime(); 13696 final long[] tmpLong = new long[1]; 13697 13698 ArrayList<ProcessRecord> procs = collectProcesses(pw, opti, args); 13699 if (procs == null) { 13700 // No Java processes. Maybe they want to print a native process. 13701 if (args != null && args.length > opti 13702 && args[opti].charAt(0) != '-') { 13703 ArrayList<ProcessCpuTracker.Stats> nativeProcs 13704 = new ArrayList<ProcessCpuTracker.Stats>(); 13705 updateCpuStatsNow(); 13706 int findPid = -1; 13707 try { 13708 findPid = Integer.parseInt(args[opti]); 13709 } catch (NumberFormatException e) { 13710 } 13711 synchronized (mProcessCpuThread) { 13712 final int N = mProcessCpuTracker.countStats(); 13713 for (int i=0; i<N; i++) { 13714 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 13715 if (st.pid == findPid || (st.baseName != null 13716 && st.baseName.equals(args[opti]))) { 13717 nativeProcs.add(st); 13718 } 13719 } 13720 } 13721 if (nativeProcs.size() > 0) { 13722 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, 13723 isCompact); 13724 Debug.MemoryInfo mi = null; 13725 for (int i = nativeProcs.size() - 1 ; i >= 0 ; i--) { 13726 final ProcessCpuTracker.Stats r = nativeProcs.get(i); 13727 final int pid = r.pid; 13728 if (!isCheckinRequest && dumpDetails) { 13729 pw.println("\n** MEMINFO in pid " + pid + " [" + r.baseName + "] **"); 13730 } 13731 if (mi == null) { 13732 mi = new Debug.MemoryInfo(); 13733 } 13734 if (dumpDetails || (!brief && !oomOnly)) { 13735 Debug.getMemoryInfo(pid, mi); 13736 } else { 13737 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 13738 mi.dalvikPrivateDirty = (int)tmpLong[0]; 13739 } 13740 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 13741 dumpDalvik, pid, r.baseName, 0, 0, 0, 0, 0, 0); 13742 if (isCheckinRequest) { 13743 pw.println(); 13744 } 13745 } 13746 return; 13747 } 13748 } 13749 pw.println("No process found for: " + args[opti]); 13750 return; 13751 } 13752 13753 if (!brief && !oomOnly && (procs.size() == 1 || isCheckinRequest)) { 13754 dumpDetails = true; 13755 } 13756 13757 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, isCompact); 13758 13759 String[] innerArgs = new String[args.length-opti]; 13760 System.arraycopy(args, opti, innerArgs, 0, args.length-opti); 13761 13762 ArrayList<MemItem> procMems = new ArrayList<MemItem>(); 13763 final SparseArray<MemItem> procMemsMap = new SparseArray<MemItem>(); 13764 long nativePss=0, dalvikPss=0, otherPss=0; 13765 long[] miscPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 13766 13767 long oomPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 13768 ArrayList<MemItem>[] oomProcs = (ArrayList<MemItem>[]) 13769 new ArrayList[DUMP_MEM_OOM_LABEL.length]; 13770 13771 long totalPss = 0; 13772 long cachedPss = 0; 13773 13774 Debug.MemoryInfo mi = null; 13775 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 13776 final ProcessRecord r = procs.get(i); 13777 final IApplicationThread thread; 13778 final int pid; 13779 final int oomAdj; 13780 final boolean hasActivities; 13781 synchronized (this) { 13782 thread = r.thread; 13783 pid = r.pid; 13784 oomAdj = r.getSetAdjWithServices(); 13785 hasActivities = r.activities.size() > 0; 13786 } 13787 if (thread != null) { 13788 if (!isCheckinRequest && dumpDetails) { 13789 pw.println("\n** MEMINFO in pid " + pid + " [" + r.processName + "] **"); 13790 } 13791 if (mi == null) { 13792 mi = new Debug.MemoryInfo(); 13793 } 13794 if (dumpDetails || (!brief && !oomOnly)) { 13795 Debug.getMemoryInfo(pid, mi); 13796 } else { 13797 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 13798 mi.dalvikPrivateDirty = (int)tmpLong[0]; 13799 } 13800 if (dumpDetails) { 13801 if (localOnly) { 13802 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 13803 dumpDalvik, pid, r.processName, 0, 0, 0, 0, 0, 0); 13804 if (isCheckinRequest) { 13805 pw.println(); 13806 } 13807 } else { 13808 try { 13809 pw.flush(); 13810 thread.dumpMemInfo(fd, mi, isCheckinRequest, dumpFullDetails, 13811 dumpDalvik, innerArgs); 13812 } catch (RemoteException e) { 13813 if (!isCheckinRequest) { 13814 pw.println("Got RemoteException!"); 13815 pw.flush(); 13816 } 13817 } 13818 } 13819 } 13820 13821 final long myTotalPss = mi.getTotalPss(); 13822 final long myTotalUss = mi.getTotalUss(); 13823 13824 synchronized (this) { 13825 if (r.thread != null && oomAdj == r.getSetAdjWithServices()) { 13826 // Record this for posterity if the process has been stable. 13827 r.baseProcessTracker.addPss(myTotalPss, myTotalUss, true, r.pkgList); 13828 } 13829 } 13830 13831 if (!isCheckinRequest && mi != null) { 13832 totalPss += myTotalPss; 13833 MemItem pssItem = new MemItem(r.processName + " (pid " + pid + 13834 (hasActivities ? " / activities)" : ")"), 13835 r.processName, myTotalPss, pid, hasActivities); 13836 procMems.add(pssItem); 13837 procMemsMap.put(pid, pssItem); 13838 13839 nativePss += mi.nativePss; 13840 dalvikPss += mi.dalvikPss; 13841 otherPss += mi.otherPss; 13842 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 13843 long mem = mi.getOtherPss(j); 13844 miscPss[j] += mem; 13845 otherPss -= mem; 13846 } 13847 13848 if (oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 13849 cachedPss += myTotalPss; 13850 } 13851 13852 for (int oomIndex=0; oomIndex<oomPss.length; oomIndex++) { 13853 if (oomAdj <= DUMP_MEM_OOM_ADJ[oomIndex] 13854 || oomIndex == (oomPss.length-1)) { 13855 oomPss[oomIndex] += myTotalPss; 13856 if (oomProcs[oomIndex] == null) { 13857 oomProcs[oomIndex] = new ArrayList<MemItem>(); 13858 } 13859 oomProcs[oomIndex].add(pssItem); 13860 break; 13861 } 13862 } 13863 } 13864 } 13865 } 13866 13867 long nativeProcTotalPss = 0; 13868 13869 if (!isCheckinRequest && procs.size() > 1) { 13870 // If we are showing aggregations, also look for native processes to 13871 // include so that our aggregations are more accurate. 13872 updateCpuStatsNow(); 13873 synchronized (mProcessCpuThread) { 13874 final int N = mProcessCpuTracker.countStats(); 13875 for (int i=0; i<N; i++) { 13876 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 13877 if (st.vsize > 0 && procMemsMap.indexOfKey(st.pid) < 0) { 13878 if (mi == null) { 13879 mi = new Debug.MemoryInfo(); 13880 } 13881 if (!brief && !oomOnly) { 13882 Debug.getMemoryInfo(st.pid, mi); 13883 } else { 13884 mi.nativePss = (int)Debug.getPss(st.pid, tmpLong); 13885 mi.nativePrivateDirty = (int)tmpLong[0]; 13886 } 13887 13888 final long myTotalPss = mi.getTotalPss(); 13889 totalPss += myTotalPss; 13890 nativeProcTotalPss += myTotalPss; 13891 13892 MemItem pssItem = new MemItem(st.name + " (pid " + st.pid + ")", 13893 st.name, myTotalPss, st.pid, false); 13894 procMems.add(pssItem); 13895 13896 nativePss += mi.nativePss; 13897 dalvikPss += mi.dalvikPss; 13898 otherPss += mi.otherPss; 13899 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 13900 long mem = mi.getOtherPss(j); 13901 miscPss[j] += mem; 13902 otherPss -= mem; 13903 } 13904 oomPss[0] += myTotalPss; 13905 if (oomProcs[0] == null) { 13906 oomProcs[0] = new ArrayList<MemItem>(); 13907 } 13908 oomProcs[0].add(pssItem); 13909 } 13910 } 13911 } 13912 13913 ArrayList<MemItem> catMems = new ArrayList<MemItem>(); 13914 13915 catMems.add(new MemItem("Native", "Native", nativePss, -1)); 13916 catMems.add(new MemItem("Dalvik", "Dalvik", dalvikPss, -2)); 13917 catMems.add(new MemItem("Unknown", "Unknown", otherPss, -3)); 13918 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 13919 String label = Debug.MemoryInfo.getOtherLabel(j); 13920 catMems.add(new MemItem(label, label, miscPss[j], j)); 13921 } 13922 13923 ArrayList<MemItem> oomMems = new ArrayList<MemItem>(); 13924 for (int j=0; j<oomPss.length; j++) { 13925 if (oomPss[j] != 0) { 13926 String label = isCompact ? DUMP_MEM_OOM_COMPACT_LABEL[j] 13927 : DUMP_MEM_OOM_LABEL[j]; 13928 MemItem item = new MemItem(label, label, oomPss[j], 13929 DUMP_MEM_OOM_ADJ[j]); 13930 item.subitems = oomProcs[j]; 13931 oomMems.add(item); 13932 } 13933 } 13934 13935 if (!brief && !oomOnly && !isCompact) { 13936 pw.println(); 13937 pw.println("Total PSS by process:"); 13938 dumpMemItems(pw, " ", "proc", procMems, true, isCompact); 13939 pw.println(); 13940 } 13941 if (!isCompact) { 13942 pw.println("Total PSS by OOM adjustment:"); 13943 } 13944 dumpMemItems(pw, " ", "oom", oomMems, false, isCompact); 13945 if (!brief && !oomOnly) { 13946 PrintWriter out = categoryPw != null ? categoryPw : pw; 13947 if (!isCompact) { 13948 out.println(); 13949 out.println("Total PSS by category:"); 13950 } 13951 dumpMemItems(out, " ", "cat", catMems, true, isCompact); 13952 } 13953 if (!isCompact) { 13954 pw.println(); 13955 } 13956 MemInfoReader memInfo = new MemInfoReader(); 13957 memInfo.readMemInfo(); 13958 if (nativeProcTotalPss > 0) { 13959 synchronized (this) { 13960 mProcessStats.addSysMemUsageLocked(memInfo.getCachedSizeKb(), 13961 memInfo.getFreeSizeKb(), memInfo.getZramTotalSizeKb(), 13962 memInfo.getBuffersSizeKb()+memInfo.getShmemSizeKb()+memInfo.getSlabSizeKb(), 13963 nativeProcTotalPss); 13964 } 13965 } 13966 if (!brief) { 13967 if (!isCompact) { 13968 pw.print("Total RAM: "); pw.print(memInfo.getTotalSizeKb()); 13969 pw.print(" kB (status "); 13970 switch (mLastMemoryLevel) { 13971 case ProcessStats.ADJ_MEM_FACTOR_NORMAL: 13972 pw.println("normal)"); 13973 break; 13974 case ProcessStats.ADJ_MEM_FACTOR_MODERATE: 13975 pw.println("moderate)"); 13976 break; 13977 case ProcessStats.ADJ_MEM_FACTOR_LOW: 13978 pw.println("low)"); 13979 break; 13980 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 13981 pw.println("critical)"); 13982 break; 13983 default: 13984 pw.print(mLastMemoryLevel); 13985 pw.println(")"); 13986 break; 13987 } 13988 pw.print(" Free RAM: "); pw.print(cachedPss + memInfo.getCachedSizeKb() 13989 + memInfo.getFreeSizeKb()); pw.print(" kB ("); 13990 pw.print(cachedPss); pw.print(" cached pss + "); 13991 pw.print(memInfo.getCachedSizeKb()); pw.print(" cached + "); 13992 pw.print(memInfo.getFreeSizeKb()); pw.println(" free)"); 13993 } else { 13994 pw.print("ram,"); pw.print(memInfo.getTotalSizeKb()); pw.print(","); 13995 pw.print(cachedPss + memInfo.getCachedSizeKb() 13996 + memInfo.getFreeSizeKb()); pw.print(","); 13997 pw.println(totalPss - cachedPss); 13998 } 13999 } 14000 if (!isCompact) { 14001 pw.print(" Used RAM: "); pw.print(totalPss - cachedPss 14002 + memInfo.getBuffersSizeKb() + memInfo.getShmemSizeKb() 14003 + memInfo.getSlabSizeKb()); pw.print(" kB ("); 14004 pw.print(totalPss - cachedPss); pw.print(" used pss + "); 14005 pw.print(memInfo.getBuffersSizeKb()); pw.print(" buffers + "); 14006 pw.print(memInfo.getShmemSizeKb()); pw.print(" shmem + "); 14007 pw.print(memInfo.getSlabSizeKb()); pw.println(" slab)"); 14008 pw.print(" Lost RAM: "); pw.print(memInfo.getTotalSizeKb() 14009 - totalPss - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 14010 - memInfo.getBuffersSizeKb() - memInfo.getShmemSizeKb() 14011 - memInfo.getSlabSizeKb()); pw.println(" kB"); 14012 } 14013 if (!brief) { 14014 if (memInfo.getZramTotalSizeKb() != 0) { 14015 if (!isCompact) { 14016 pw.print(" ZRAM: "); pw.print(memInfo.getZramTotalSizeKb()); 14017 pw.print(" kB physical used for "); 14018 pw.print(memInfo.getSwapTotalSizeKb() 14019 - memInfo.getSwapFreeSizeKb()); 14020 pw.print(" kB in swap ("); 14021 pw.print(memInfo.getSwapTotalSizeKb()); 14022 pw.println(" kB total swap)"); 14023 } else { 14024 pw.print("zram,"); pw.print(memInfo.getZramTotalSizeKb()); pw.print(","); 14025 pw.print(memInfo.getSwapTotalSizeKb()); pw.print(","); 14026 pw.println(memInfo.getSwapFreeSizeKb()); 14027 } 14028 } 14029 final int[] SINGLE_LONG_FORMAT = new int[] { 14030 Process.PROC_SPACE_TERM|Process.PROC_OUT_LONG 14031 }; 14032 long[] longOut = new long[1]; 14033 Process.readProcFile("/sys/kernel/mm/ksm/pages_shared", 14034 SINGLE_LONG_FORMAT, null, longOut, null); 14035 long shared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 14036 longOut[0] = 0; 14037 Process.readProcFile("/sys/kernel/mm/ksm/pages_sharing", 14038 SINGLE_LONG_FORMAT, null, longOut, null); 14039 long sharing = longOut[0] * ProcessList.PAGE_SIZE / 1024; 14040 longOut[0] = 0; 14041 Process.readProcFile("/sys/kernel/mm/ksm/pages_unshared", 14042 SINGLE_LONG_FORMAT, null, longOut, null); 14043 long unshared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 14044 longOut[0] = 0; 14045 Process.readProcFile("/sys/kernel/mm/ksm/pages_volatile", 14046 SINGLE_LONG_FORMAT, null, longOut, null); 14047 long voltile = longOut[0] * ProcessList.PAGE_SIZE / 1024; 14048 if (!isCompact) { 14049 if (sharing != 0 || shared != 0 || unshared != 0 || voltile != 0) { 14050 pw.print(" KSM: "); pw.print(sharing); 14051 pw.print(" kB saved from shared "); 14052 pw.print(shared); pw.println(" kB"); 14053 pw.print(" "); pw.print(unshared); pw.print(" kB unshared; "); 14054 pw.print(voltile); pw.println(" kB volatile"); 14055 } 14056 pw.print(" Tuning: "); 14057 pw.print(ActivityManager.staticGetMemoryClass()); 14058 pw.print(" (large "); 14059 pw.print(ActivityManager.staticGetLargeMemoryClass()); 14060 pw.print("), oom "); 14061 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 14062 pw.print(" kB"); 14063 pw.print(", restore limit "); 14064 pw.print(mProcessList.getCachedRestoreThresholdKb()); 14065 pw.print(" kB"); 14066 if (ActivityManager.isLowRamDeviceStatic()) { 14067 pw.print(" (low-ram)"); 14068 } 14069 if (ActivityManager.isHighEndGfx()) { 14070 pw.print(" (high-end-gfx)"); 14071 } 14072 pw.println(); 14073 } else { 14074 pw.print("ksm,"); pw.print(sharing); pw.print(","); 14075 pw.print(shared); pw.print(","); pw.print(unshared); pw.print(","); 14076 pw.println(voltile); 14077 pw.print("tuning,"); 14078 pw.print(ActivityManager.staticGetMemoryClass()); 14079 pw.print(','); 14080 pw.print(ActivityManager.staticGetLargeMemoryClass()); 14081 pw.print(','); 14082 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 14083 if (ActivityManager.isLowRamDeviceStatic()) { 14084 pw.print(",low-ram"); 14085 } 14086 if (ActivityManager.isHighEndGfx()) { 14087 pw.print(",high-end-gfx"); 14088 } 14089 pw.println(); 14090 } 14091 } 14092 } 14093 } 14094 14095 /** 14096 * Searches array of arguments for the specified string 14097 * @param args array of argument strings 14098 * @param value value to search for 14099 * @return true if the value is contained in the array 14100 */ 14101 private static boolean scanArgs(String[] args, String value) { 14102 if (args != null) { 14103 for (String arg : args) { 14104 if (value.equals(arg)) { 14105 return true; 14106 } 14107 } 14108 } 14109 return false; 14110 } 14111 14112 private final boolean removeDyingProviderLocked(ProcessRecord proc, 14113 ContentProviderRecord cpr, boolean always) { 14114 final boolean inLaunching = mLaunchingProviders.contains(cpr); 14115 14116 if (!inLaunching || always) { 14117 synchronized (cpr) { 14118 cpr.launchingApp = null; 14119 cpr.notifyAll(); 14120 } 14121 mProviderMap.removeProviderByClass(cpr.name, UserHandle.getUserId(cpr.uid)); 14122 String names[] = cpr.info.authority.split(";"); 14123 for (int j = 0; j < names.length; j++) { 14124 mProviderMap.removeProviderByName(names[j], UserHandle.getUserId(cpr.uid)); 14125 } 14126 } 14127 14128 for (int i=0; i<cpr.connections.size(); i++) { 14129 ContentProviderConnection conn = cpr.connections.get(i); 14130 if (conn.waiting) { 14131 // If this connection is waiting for the provider, then we don't 14132 // need to mess with its process unless we are always removing 14133 // or for some reason the provider is not currently launching. 14134 if (inLaunching && !always) { 14135 continue; 14136 } 14137 } 14138 ProcessRecord capp = conn.client; 14139 conn.dead = true; 14140 if (conn.stableCount > 0) { 14141 if (!capp.persistent && capp.thread != null 14142 && capp.pid != 0 14143 && capp.pid != MY_PID) { 14144 capp.kill("depends on provider " 14145 + cpr.name.flattenToShortString() 14146 + " in dying proc " + (proc != null ? proc.processName : "??"), true); 14147 } 14148 } else if (capp.thread != null && conn.provider.provider != null) { 14149 try { 14150 capp.thread.unstableProviderDied(conn.provider.provider.asBinder()); 14151 } catch (RemoteException e) { 14152 } 14153 // In the protocol here, we don't expect the client to correctly 14154 // clean up this connection, we'll just remove it. 14155 cpr.connections.remove(i); 14156 conn.client.conProviders.remove(conn); 14157 } 14158 } 14159 14160 if (inLaunching && always) { 14161 mLaunchingProviders.remove(cpr); 14162 } 14163 return inLaunching; 14164 } 14165 14166 /** 14167 * Main code for cleaning up a process when it has gone away. This is 14168 * called both as a result of the process dying, or directly when stopping 14169 * a process when running in single process mode. 14170 */ 14171 private final void cleanUpApplicationRecordLocked(ProcessRecord app, 14172 boolean restarting, boolean allowRestart, int index) { 14173 if (index >= 0) { 14174 removeLruProcessLocked(app); 14175 ProcessList.remove(app.pid); 14176 } 14177 14178 mProcessesToGc.remove(app); 14179 mPendingPssProcesses.remove(app); 14180 14181 // Dismiss any open dialogs. 14182 if (app.crashDialog != null && !app.forceCrashReport) { 14183 app.crashDialog.dismiss(); 14184 app.crashDialog = null; 14185 } 14186 if (app.anrDialog != null) { 14187 app.anrDialog.dismiss(); 14188 app.anrDialog = null; 14189 } 14190 if (app.waitDialog != null) { 14191 app.waitDialog.dismiss(); 14192 app.waitDialog = null; 14193 } 14194 14195 app.crashing = false; 14196 app.notResponding = false; 14197 14198 app.resetPackageList(mProcessStats); 14199 app.unlinkDeathRecipient(); 14200 app.makeInactive(mProcessStats); 14201 app.waitingToKill = null; 14202 app.forcingToForeground = null; 14203 updateProcessForegroundLocked(app, false, false); 14204 app.foregroundActivities = false; 14205 app.hasShownUi = false; 14206 app.treatLikeActivity = false; 14207 app.hasAboveClient = false; 14208 app.hasClientActivities = false; 14209 14210 mServices.killServicesLocked(app, allowRestart); 14211 14212 boolean restart = false; 14213 14214 // Remove published content providers. 14215 for (int i=app.pubProviders.size()-1; i>=0; i--) { 14216 ContentProviderRecord cpr = app.pubProviders.valueAt(i); 14217 final boolean always = app.bad || !allowRestart; 14218 if (removeDyingProviderLocked(app, cpr, always) || always) { 14219 // We left the provider in the launching list, need to 14220 // restart it. 14221 restart = true; 14222 } 14223 14224 cpr.provider = null; 14225 cpr.proc = null; 14226 } 14227 app.pubProviders.clear(); 14228 14229 // Take care of any launching providers waiting for this process. 14230 if (checkAppInLaunchingProvidersLocked(app, false)) { 14231 restart = true; 14232 } 14233 14234 // Unregister from connected content providers. 14235 if (!app.conProviders.isEmpty()) { 14236 for (int i=0; i<app.conProviders.size(); i++) { 14237 ContentProviderConnection conn = app.conProviders.get(i); 14238 conn.provider.connections.remove(conn); 14239 } 14240 app.conProviders.clear(); 14241 } 14242 14243 // At this point there may be remaining entries in mLaunchingProviders 14244 // where we were the only one waiting, so they are no longer of use. 14245 // Look for these and clean up if found. 14246 // XXX Commented out for now. Trying to figure out a way to reproduce 14247 // the actual situation to identify what is actually going on. 14248 if (false) { 14249 for (int i=0; i<mLaunchingProviders.size(); i++) { 14250 ContentProviderRecord cpr = (ContentProviderRecord) 14251 mLaunchingProviders.get(i); 14252 if (cpr.connections.size() <= 0 && !cpr.hasExternalProcessHandles()) { 14253 synchronized (cpr) { 14254 cpr.launchingApp = null; 14255 cpr.notifyAll(); 14256 } 14257 } 14258 } 14259 } 14260 14261 skipCurrentReceiverLocked(app); 14262 14263 // Unregister any receivers. 14264 for (int i=app.receivers.size()-1; i>=0; i--) { 14265 removeReceiverLocked(app.receivers.valueAt(i)); 14266 } 14267 app.receivers.clear(); 14268 14269 // If the app is undergoing backup, tell the backup manager about it 14270 if (mBackupTarget != null && app.pid == mBackupTarget.app.pid) { 14271 if (DEBUG_BACKUP || DEBUG_CLEANUP) Slog.d(TAG, "App " 14272 + mBackupTarget.appInfo + " died during backup"); 14273 try { 14274 IBackupManager bm = IBackupManager.Stub.asInterface( 14275 ServiceManager.getService(Context.BACKUP_SERVICE)); 14276 bm.agentDisconnected(app.info.packageName); 14277 } catch (RemoteException e) { 14278 // can't happen; backup manager is local 14279 } 14280 } 14281 14282 for (int i = mPendingProcessChanges.size()-1; i>=0; i--) { 14283 ProcessChangeItem item = mPendingProcessChanges.get(i); 14284 if (item.pid == app.pid) { 14285 mPendingProcessChanges.remove(i); 14286 mAvailProcessChanges.add(item); 14287 } 14288 } 14289 mHandler.obtainMessage(DISPATCH_PROCESS_DIED, app.pid, app.info.uid, null).sendToTarget(); 14290 14291 // If the caller is restarting this app, then leave it in its 14292 // current lists and let the caller take care of it. 14293 if (restarting) { 14294 return; 14295 } 14296 14297 if (!app.persistent || app.isolated) { 14298 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, 14299 "Removing non-persistent process during cleanup: " + app); 14300 mProcessNames.remove(app.processName, app.uid); 14301 mIsolatedProcesses.remove(app.uid); 14302 if (mHeavyWeightProcess == app) { 14303 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 14304 mHeavyWeightProcess.userId, 0)); 14305 mHeavyWeightProcess = null; 14306 } 14307 } else if (!app.removed) { 14308 // This app is persistent, so we need to keep its record around. 14309 // If it is not already on the pending app list, add it there 14310 // and start a new process for it. 14311 if (mPersistentStartingProcesses.indexOf(app) < 0) { 14312 mPersistentStartingProcesses.add(app); 14313 restart = true; 14314 } 14315 } 14316 if ((DEBUG_PROCESSES || DEBUG_CLEANUP) && mProcessesOnHold.contains(app)) Slog.v(TAG, 14317 "Clean-up removing on hold: " + app); 14318 mProcessesOnHold.remove(app); 14319 14320 if (app == mHomeProcess) { 14321 mHomeProcess = null; 14322 } 14323 if (app == mPreviousProcess) { 14324 mPreviousProcess = null; 14325 } 14326 14327 if (restart && !app.isolated) { 14328 // We have components that still need to be running in the 14329 // process, so re-launch it. 14330 mProcessNames.put(app.processName, app.uid, app); 14331 startProcessLocked(app, "restart", app.processName); 14332 } else if (app.pid > 0 && app.pid != MY_PID) { 14333 // Goodbye! 14334 boolean removed; 14335 synchronized (mPidsSelfLocked) { 14336 mPidsSelfLocked.remove(app.pid); 14337 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 14338 } 14339 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 14340 if (app.isolated) { 14341 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 14342 } 14343 app.setPid(0); 14344 } 14345 } 14346 14347 boolean checkAppInLaunchingProvidersLocked(ProcessRecord app, boolean alwaysBad) { 14348 // Look through the content providers we are waiting to have launched, 14349 // and if any run in this process then either schedule a restart of 14350 // the process or kill the client waiting for it if this process has 14351 // gone bad. 14352 int NL = mLaunchingProviders.size(); 14353 boolean restart = false; 14354 for (int i=0; i<NL; i++) { 14355 ContentProviderRecord cpr = mLaunchingProviders.get(i); 14356 if (cpr.launchingApp == app) { 14357 if (!alwaysBad && !app.bad) { 14358 restart = true; 14359 } else { 14360 removeDyingProviderLocked(app, cpr, true); 14361 // cpr should have been removed from mLaunchingProviders 14362 NL = mLaunchingProviders.size(); 14363 i--; 14364 } 14365 } 14366 } 14367 return restart; 14368 } 14369 14370 // ========================================================= 14371 // SERVICES 14372 // ========================================================= 14373 14374 @Override 14375 public List<ActivityManager.RunningServiceInfo> getServices(int maxNum, 14376 int flags) { 14377 enforceNotIsolatedCaller("getServices"); 14378 synchronized (this) { 14379 return mServices.getRunningServiceInfoLocked(maxNum, flags); 14380 } 14381 } 14382 14383 @Override 14384 public PendingIntent getRunningServiceControlPanel(ComponentName name) { 14385 enforceNotIsolatedCaller("getRunningServiceControlPanel"); 14386 synchronized (this) { 14387 return mServices.getRunningServiceControlPanelLocked(name); 14388 } 14389 } 14390 14391 @Override 14392 public ComponentName startService(IApplicationThread caller, Intent service, 14393 String resolvedType, int userId) { 14394 enforceNotIsolatedCaller("startService"); 14395 // Refuse possible leaked file descriptors 14396 if (service != null && service.hasFileDescriptors() == true) { 14397 throw new IllegalArgumentException("File descriptors passed in Intent"); 14398 } 14399 14400 if (DEBUG_SERVICE) 14401 Slog.v(TAG, "startService: " + service + " type=" + resolvedType); 14402 synchronized(this) { 14403 final int callingPid = Binder.getCallingPid(); 14404 final int callingUid = Binder.getCallingUid(); 14405 final long origId = Binder.clearCallingIdentity(); 14406 ComponentName res = mServices.startServiceLocked(caller, service, 14407 resolvedType, callingPid, callingUid, userId); 14408 Binder.restoreCallingIdentity(origId); 14409 return res; 14410 } 14411 } 14412 14413 ComponentName startServiceInPackage(int uid, 14414 Intent service, String resolvedType, int userId) { 14415 synchronized(this) { 14416 if (DEBUG_SERVICE) 14417 Slog.v(TAG, "startServiceInPackage: " + service + " type=" + resolvedType); 14418 final long origId = Binder.clearCallingIdentity(); 14419 ComponentName res = mServices.startServiceLocked(null, service, 14420 resolvedType, -1, uid, userId); 14421 Binder.restoreCallingIdentity(origId); 14422 return res; 14423 } 14424 } 14425 14426 @Override 14427 public int stopService(IApplicationThread caller, Intent service, 14428 String resolvedType, int userId) { 14429 enforceNotIsolatedCaller("stopService"); 14430 // Refuse possible leaked file descriptors 14431 if (service != null && service.hasFileDescriptors() == true) { 14432 throw new IllegalArgumentException("File descriptors passed in Intent"); 14433 } 14434 14435 synchronized(this) { 14436 return mServices.stopServiceLocked(caller, service, resolvedType, userId); 14437 } 14438 } 14439 14440 @Override 14441 public IBinder peekService(Intent service, String resolvedType) { 14442 enforceNotIsolatedCaller("peekService"); 14443 // Refuse possible leaked file descriptors 14444 if (service != null && service.hasFileDescriptors() == true) { 14445 throw new IllegalArgumentException("File descriptors passed in Intent"); 14446 } 14447 synchronized(this) { 14448 return mServices.peekServiceLocked(service, resolvedType); 14449 } 14450 } 14451 14452 @Override 14453 public boolean stopServiceToken(ComponentName className, IBinder token, 14454 int startId) { 14455 synchronized(this) { 14456 return mServices.stopServiceTokenLocked(className, token, startId); 14457 } 14458 } 14459 14460 @Override 14461 public void setServiceForeground(ComponentName className, IBinder token, 14462 int id, Notification notification, boolean removeNotification) { 14463 synchronized(this) { 14464 mServices.setServiceForegroundLocked(className, token, id, notification, 14465 removeNotification); 14466 } 14467 } 14468 14469 @Override 14470 public int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 14471 boolean requireFull, String name, String callerPackage) { 14472 return handleIncomingUser(callingPid, callingUid, userId, allowAll, 14473 requireFull ? ALLOW_FULL_ONLY : ALLOW_NON_FULL, name, callerPackage); 14474 } 14475 14476 int unsafeConvertIncomingUser(int userId) { 14477 return (userId == UserHandle.USER_CURRENT || userId == UserHandle.USER_CURRENT_OR_SELF) 14478 ? mCurrentUserId : userId; 14479 } 14480 14481 int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 14482 int allowMode, String name, String callerPackage) { 14483 final int callingUserId = UserHandle.getUserId(callingUid); 14484 if (callingUserId == userId) { 14485 return userId; 14486 } 14487 14488 // Note that we may be accessing mCurrentUserId outside of a lock... 14489 // shouldn't be a big deal, if this is being called outside 14490 // of a locked context there is intrinsically a race with 14491 // the value the caller will receive and someone else changing it. 14492 // We assume that USER_CURRENT_OR_SELF will use the current user; later 14493 // we will switch to the calling user if access to the current user fails. 14494 int targetUserId = unsafeConvertIncomingUser(userId); 14495 14496 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 14497 final boolean allow; 14498 if (checkComponentPermission(INTERACT_ACROSS_USERS_FULL, callingPid, 14499 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED) { 14500 // If the caller has this permission, they always pass go. And collect $200. 14501 allow = true; 14502 } else if (allowMode == ALLOW_FULL_ONLY) { 14503 // We require full access, sucks to be you. 14504 allow = false; 14505 } else if (checkComponentPermission(INTERACT_ACROSS_USERS, callingPid, 14506 callingUid, -1, true) != PackageManager.PERMISSION_GRANTED) { 14507 // If the caller does not have either permission, they are always doomed. 14508 allow = false; 14509 } else if (allowMode == ALLOW_NON_FULL) { 14510 // We are blanket allowing non-full access, you lucky caller! 14511 allow = true; 14512 } else if (allowMode == ALLOW_NON_FULL_IN_PROFILE) { 14513 // We may or may not allow this depending on whether the two users are 14514 // in the same profile. 14515 synchronized (mUserProfileGroupIdsSelfLocked) { 14516 int callingProfile = mUserProfileGroupIdsSelfLocked.get(callingUserId, 14517 UserInfo.NO_PROFILE_GROUP_ID); 14518 int targetProfile = mUserProfileGroupIdsSelfLocked.get(targetUserId, 14519 UserInfo.NO_PROFILE_GROUP_ID); 14520 allow = callingProfile != UserInfo.NO_PROFILE_GROUP_ID 14521 && callingProfile == targetProfile; 14522 } 14523 } else { 14524 throw new IllegalArgumentException("Unknown mode: " + allowMode); 14525 } 14526 if (!allow) { 14527 if (userId == UserHandle.USER_CURRENT_OR_SELF) { 14528 // In this case, they would like to just execute as their 14529 // owner user instead of failing. 14530 targetUserId = callingUserId; 14531 } else { 14532 StringBuilder builder = new StringBuilder(128); 14533 builder.append("Permission Denial: "); 14534 builder.append(name); 14535 if (callerPackage != null) { 14536 builder.append(" from "); 14537 builder.append(callerPackage); 14538 } 14539 builder.append(" asks to run as user "); 14540 builder.append(userId); 14541 builder.append(" but is calling from user "); 14542 builder.append(UserHandle.getUserId(callingUid)); 14543 builder.append("; this requires "); 14544 builder.append(INTERACT_ACROSS_USERS_FULL); 14545 if (allowMode != ALLOW_FULL_ONLY) { 14546 builder.append(" or "); 14547 builder.append(INTERACT_ACROSS_USERS); 14548 } 14549 String msg = builder.toString(); 14550 Slog.w(TAG, msg); 14551 throw new SecurityException(msg); 14552 } 14553 } 14554 } 14555 if (!allowAll && targetUserId < 0) { 14556 throw new IllegalArgumentException( 14557 "Call does not support special user #" + targetUserId); 14558 } 14559 return targetUserId; 14560 } 14561 14562 boolean isSingleton(String componentProcessName, ApplicationInfo aInfo, 14563 String className, int flags) { 14564 boolean result = false; 14565 // For apps that don't have pre-defined UIDs, check for permission 14566 if (UserHandle.getAppId(aInfo.uid) >= Process.FIRST_APPLICATION_UID) { 14567 if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 14568 if (ActivityManager.checkUidPermission( 14569 INTERACT_ACROSS_USERS, 14570 aInfo.uid) != PackageManager.PERMISSION_GRANTED) { 14571 ComponentName comp = new ComponentName(aInfo.packageName, className); 14572 String msg = "Permission Denial: Component " + comp.flattenToShortString() 14573 + " requests FLAG_SINGLE_USER, but app does not hold " 14574 + INTERACT_ACROSS_USERS; 14575 Slog.w(TAG, msg); 14576 throw new SecurityException(msg); 14577 } 14578 // Permission passed 14579 result = true; 14580 } 14581 } else if ("system".equals(componentProcessName)) { 14582 result = true; 14583 } else if (UserHandle.isSameApp(aInfo.uid, Process.PHONE_UID) 14584 && (flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 14585 // Phone app is allowed to export singleuser providers. 14586 result = true; 14587 } else { 14588 // App with pre-defined UID, check if it's a persistent app 14589 result = (aInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0; 14590 } 14591 if (DEBUG_MU) { 14592 Slog.v(TAG, "isSingleton(" + componentProcessName + ", " + aInfo 14593 + ", " + className + ", 0x" + Integer.toHexString(flags) + ") = " + result); 14594 } 14595 return result; 14596 } 14597 14598 /** 14599 * Checks to see if the caller is in the same app as the singleton 14600 * component, or the component is in a special app. It allows special apps 14601 * to export singleton components but prevents exporting singleton 14602 * components for regular apps. 14603 */ 14604 boolean isValidSingletonCall(int callingUid, int componentUid) { 14605 int componentAppId = UserHandle.getAppId(componentUid); 14606 return UserHandle.isSameApp(callingUid, componentUid) 14607 || componentAppId == Process.SYSTEM_UID 14608 || componentAppId == Process.PHONE_UID 14609 || ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, componentUid) 14610 == PackageManager.PERMISSION_GRANTED; 14611 } 14612 14613 public int bindService(IApplicationThread caller, IBinder token, 14614 Intent service, String resolvedType, 14615 IServiceConnection connection, int flags, int userId) { 14616 enforceNotIsolatedCaller("bindService"); 14617 // Refuse possible leaked file descriptors 14618 if (service != null && service.hasFileDescriptors() == true) { 14619 throw new IllegalArgumentException("File descriptors passed in Intent"); 14620 } 14621 14622 synchronized(this) { 14623 return mServices.bindServiceLocked(caller, token, service, resolvedType, 14624 connection, flags, userId); 14625 } 14626 } 14627 14628 public boolean unbindService(IServiceConnection connection) { 14629 synchronized (this) { 14630 return mServices.unbindServiceLocked(connection); 14631 } 14632 } 14633 14634 public void publishService(IBinder token, Intent intent, IBinder service) { 14635 // Refuse possible leaked file descriptors 14636 if (intent != null && intent.hasFileDescriptors() == true) { 14637 throw new IllegalArgumentException("File descriptors passed in Intent"); 14638 } 14639 14640 synchronized(this) { 14641 if (!(token instanceof ServiceRecord)) { 14642 throw new IllegalArgumentException("Invalid service token"); 14643 } 14644 mServices.publishServiceLocked((ServiceRecord)token, intent, service); 14645 } 14646 } 14647 14648 public void unbindFinished(IBinder token, Intent intent, boolean doRebind) { 14649 // Refuse possible leaked file descriptors 14650 if (intent != null && intent.hasFileDescriptors() == true) { 14651 throw new IllegalArgumentException("File descriptors passed in Intent"); 14652 } 14653 14654 synchronized(this) { 14655 mServices.unbindFinishedLocked((ServiceRecord)token, intent, doRebind); 14656 } 14657 } 14658 14659 public void serviceDoneExecuting(IBinder token, int type, int startId, int res) { 14660 synchronized(this) { 14661 if (!(token instanceof ServiceRecord)) { 14662 throw new IllegalArgumentException("Invalid service token"); 14663 } 14664 mServices.serviceDoneExecutingLocked((ServiceRecord)token, type, startId, res); 14665 } 14666 } 14667 14668 // ========================================================= 14669 // BACKUP AND RESTORE 14670 // ========================================================= 14671 14672 // Cause the target app to be launched if necessary and its backup agent 14673 // instantiated. The backup agent will invoke backupAgentCreated() on the 14674 // activity manager to announce its creation. 14675 public boolean bindBackupAgent(ApplicationInfo app, int backupMode) { 14676 if (DEBUG_BACKUP) Slog.v(TAG, "bindBackupAgent: app=" + app + " mode=" + backupMode); 14677 enforceCallingPermission("android.permission.CONFIRM_FULL_BACKUP", "bindBackupAgent"); 14678 14679 synchronized(this) { 14680 // !!! TODO: currently no check here that we're already bound 14681 BatteryStatsImpl.Uid.Pkg.Serv ss = null; 14682 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 14683 synchronized (stats) { 14684 ss = stats.getServiceStatsLocked(app.uid, app.packageName, app.name); 14685 } 14686 14687 // Backup agent is now in use, its package can't be stopped. 14688 try { 14689 AppGlobals.getPackageManager().setPackageStoppedState( 14690 app.packageName, false, UserHandle.getUserId(app.uid)); 14691 } catch (RemoteException e) { 14692 } catch (IllegalArgumentException e) { 14693 Slog.w(TAG, "Failed trying to unstop package " 14694 + app.packageName + ": " + e); 14695 } 14696 14697 BackupRecord r = new BackupRecord(ss, app, backupMode); 14698 ComponentName hostingName = (backupMode == IApplicationThread.BACKUP_MODE_INCREMENTAL) 14699 ? new ComponentName(app.packageName, app.backupAgentName) 14700 : new ComponentName("android", "FullBackupAgent"); 14701 // startProcessLocked() returns existing proc's record if it's already running 14702 ProcessRecord proc = startProcessLocked(app.processName, app, 14703 false, 0, "backup", hostingName, false, false, false); 14704 if (proc == null) { 14705 Slog.e(TAG, "Unable to start backup agent process " + r); 14706 return false; 14707 } 14708 14709 r.app = proc; 14710 mBackupTarget = r; 14711 mBackupAppName = app.packageName; 14712 14713 // Try not to kill the process during backup 14714 updateOomAdjLocked(proc); 14715 14716 // If the process is already attached, schedule the creation of the backup agent now. 14717 // If it is not yet live, this will be done when it attaches to the framework. 14718 if (proc.thread != null) { 14719 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc already running: " + proc); 14720 try { 14721 proc.thread.scheduleCreateBackupAgent(app, 14722 compatibilityInfoForPackageLocked(app), backupMode); 14723 } catch (RemoteException e) { 14724 // Will time out on the backup manager side 14725 } 14726 } else { 14727 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc not running, waiting for attach"); 14728 } 14729 // Invariants: at this point, the target app process exists and the application 14730 // is either already running or in the process of coming up. mBackupTarget and 14731 // mBackupAppName describe the app, so that when it binds back to the AM we 14732 // know that it's scheduled for a backup-agent operation. 14733 } 14734 14735 return true; 14736 } 14737 14738 @Override 14739 public void clearPendingBackup() { 14740 if (DEBUG_BACKUP) Slog.v(TAG, "clearPendingBackup"); 14741 enforceCallingPermission("android.permission.BACKUP", "clearPendingBackup"); 14742 14743 synchronized (this) { 14744 mBackupTarget = null; 14745 mBackupAppName = null; 14746 } 14747 } 14748 14749 // A backup agent has just come up 14750 public void backupAgentCreated(String agentPackageName, IBinder agent) { 14751 if (DEBUG_BACKUP) Slog.v(TAG, "backupAgentCreated: " + agentPackageName 14752 + " = " + agent); 14753 14754 synchronized(this) { 14755 if (!agentPackageName.equals(mBackupAppName)) { 14756 Slog.e(TAG, "Backup agent created for " + agentPackageName + " but not requested!"); 14757 return; 14758 } 14759 } 14760 14761 long oldIdent = Binder.clearCallingIdentity(); 14762 try { 14763 IBackupManager bm = IBackupManager.Stub.asInterface( 14764 ServiceManager.getService(Context.BACKUP_SERVICE)); 14765 bm.agentConnected(agentPackageName, agent); 14766 } catch (RemoteException e) { 14767 // can't happen; the backup manager service is local 14768 } catch (Exception e) { 14769 Slog.w(TAG, "Exception trying to deliver BackupAgent binding: "); 14770 e.printStackTrace(); 14771 } finally { 14772 Binder.restoreCallingIdentity(oldIdent); 14773 } 14774 } 14775 14776 // done with this agent 14777 public void unbindBackupAgent(ApplicationInfo appInfo) { 14778 if (DEBUG_BACKUP) Slog.v(TAG, "unbindBackupAgent: " + appInfo); 14779 if (appInfo == null) { 14780 Slog.w(TAG, "unbind backup agent for null app"); 14781 return; 14782 } 14783 14784 synchronized(this) { 14785 try { 14786 if (mBackupAppName == null) { 14787 Slog.w(TAG, "Unbinding backup agent with no active backup"); 14788 return; 14789 } 14790 14791 if (!mBackupAppName.equals(appInfo.packageName)) { 14792 Slog.e(TAG, "Unbind of " + appInfo + " but is not the current backup target"); 14793 return; 14794 } 14795 14796 // Not backing this app up any more; reset its OOM adjustment 14797 final ProcessRecord proc = mBackupTarget.app; 14798 updateOomAdjLocked(proc); 14799 14800 // If the app crashed during backup, 'thread' will be null here 14801 if (proc.thread != null) { 14802 try { 14803 proc.thread.scheduleDestroyBackupAgent(appInfo, 14804 compatibilityInfoForPackageLocked(appInfo)); 14805 } catch (Exception e) { 14806 Slog.e(TAG, "Exception when unbinding backup agent:"); 14807 e.printStackTrace(); 14808 } 14809 } 14810 } finally { 14811 mBackupTarget = null; 14812 mBackupAppName = null; 14813 } 14814 } 14815 } 14816 // ========================================================= 14817 // BROADCASTS 14818 // ========================================================= 14819 14820 private final List getStickiesLocked(String action, IntentFilter filter, 14821 List cur, int userId) { 14822 final ContentResolver resolver = mContext.getContentResolver(); 14823 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 14824 if (stickies == null) { 14825 return cur; 14826 } 14827 final ArrayList<Intent> list = stickies.get(action); 14828 if (list == null) { 14829 return cur; 14830 } 14831 int N = list.size(); 14832 for (int i=0; i<N; i++) { 14833 Intent intent = list.get(i); 14834 if (filter.match(resolver, intent, true, TAG) >= 0) { 14835 if (cur == null) { 14836 cur = new ArrayList<Intent>(); 14837 } 14838 cur.add(intent); 14839 } 14840 } 14841 return cur; 14842 } 14843 14844 boolean isPendingBroadcastProcessLocked(int pid) { 14845 return mFgBroadcastQueue.isPendingBroadcastProcessLocked(pid) 14846 || mBgBroadcastQueue.isPendingBroadcastProcessLocked(pid); 14847 } 14848 14849 void skipPendingBroadcastLocked(int pid) { 14850 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 14851 for (BroadcastQueue queue : mBroadcastQueues) { 14852 queue.skipPendingBroadcastLocked(pid); 14853 } 14854 } 14855 14856 // The app just attached; send any pending broadcasts that it should receive 14857 boolean sendPendingBroadcastsLocked(ProcessRecord app) { 14858 boolean didSomething = false; 14859 for (BroadcastQueue queue : mBroadcastQueues) { 14860 didSomething |= queue.sendPendingBroadcastsLocked(app); 14861 } 14862 return didSomething; 14863 } 14864 14865 public Intent registerReceiver(IApplicationThread caller, String callerPackage, 14866 IIntentReceiver receiver, IntentFilter filter, String permission, int userId) { 14867 enforceNotIsolatedCaller("registerReceiver"); 14868 int callingUid; 14869 int callingPid; 14870 synchronized(this) { 14871 ProcessRecord callerApp = null; 14872 if (caller != null) { 14873 callerApp = getRecordForAppLocked(caller); 14874 if (callerApp == null) { 14875 throw new SecurityException( 14876 "Unable to find app for caller " + caller 14877 + " (pid=" + Binder.getCallingPid() 14878 + ") when registering receiver " + receiver); 14879 } 14880 if (callerApp.info.uid != Process.SYSTEM_UID && 14881 !callerApp.pkgList.containsKey(callerPackage) && 14882 !"android".equals(callerPackage)) { 14883 throw new SecurityException("Given caller package " + callerPackage 14884 + " is not running in process " + callerApp); 14885 } 14886 callingUid = callerApp.info.uid; 14887 callingPid = callerApp.pid; 14888 } else { 14889 callerPackage = null; 14890 callingUid = Binder.getCallingUid(); 14891 callingPid = Binder.getCallingPid(); 14892 } 14893 14894 userId = this.handleIncomingUser(callingPid, callingUid, userId, 14895 true, ALLOW_FULL_ONLY, "registerReceiver", callerPackage); 14896 14897 List allSticky = null; 14898 14899 // Look for any matching sticky broadcasts... 14900 Iterator actions = filter.actionsIterator(); 14901 if (actions != null) { 14902 while (actions.hasNext()) { 14903 String action = (String)actions.next(); 14904 allSticky = getStickiesLocked(action, filter, allSticky, 14905 UserHandle.USER_ALL); 14906 allSticky = getStickiesLocked(action, filter, allSticky, 14907 UserHandle.getUserId(callingUid)); 14908 } 14909 } else { 14910 allSticky = getStickiesLocked(null, filter, allSticky, 14911 UserHandle.USER_ALL); 14912 allSticky = getStickiesLocked(null, filter, allSticky, 14913 UserHandle.getUserId(callingUid)); 14914 } 14915 14916 // The first sticky in the list is returned directly back to 14917 // the client. 14918 Intent sticky = allSticky != null ? (Intent)allSticky.get(0) : null; 14919 14920 if (DEBUG_BROADCAST) Slog.v(TAG, "Register receiver " + filter 14921 + ": " + sticky); 14922 14923 if (receiver == null) { 14924 return sticky; 14925 } 14926 14927 ReceiverList rl 14928 = (ReceiverList)mRegisteredReceivers.get(receiver.asBinder()); 14929 if (rl == null) { 14930 rl = new ReceiverList(this, callerApp, callingPid, callingUid, 14931 userId, receiver); 14932 if (rl.app != null) { 14933 rl.app.receivers.add(rl); 14934 } else { 14935 try { 14936 receiver.asBinder().linkToDeath(rl, 0); 14937 } catch (RemoteException e) { 14938 return sticky; 14939 } 14940 rl.linkedToDeath = true; 14941 } 14942 mRegisteredReceivers.put(receiver.asBinder(), rl); 14943 } else if (rl.uid != callingUid) { 14944 throw new IllegalArgumentException( 14945 "Receiver requested to register for uid " + callingUid 14946 + " was previously registered for uid " + rl.uid); 14947 } else if (rl.pid != callingPid) { 14948 throw new IllegalArgumentException( 14949 "Receiver requested to register for pid " + callingPid 14950 + " was previously registered for pid " + rl.pid); 14951 } else if (rl.userId != userId) { 14952 throw new IllegalArgumentException( 14953 "Receiver requested to register for user " + userId 14954 + " was previously registered for user " + rl.userId); 14955 } 14956 BroadcastFilter bf = new BroadcastFilter(filter, rl, callerPackage, 14957 permission, callingUid, userId); 14958 rl.add(bf); 14959 if (!bf.debugCheck()) { 14960 Slog.w(TAG, "==> For Dynamic broadast"); 14961 } 14962 mReceiverResolver.addFilter(bf); 14963 14964 // Enqueue broadcasts for all existing stickies that match 14965 // this filter. 14966 if (allSticky != null) { 14967 ArrayList receivers = new ArrayList(); 14968 receivers.add(bf); 14969 14970 int N = allSticky.size(); 14971 for (int i=0; i<N; i++) { 14972 Intent intent = (Intent)allSticky.get(i); 14973 BroadcastQueue queue = broadcastQueueForIntent(intent); 14974 BroadcastRecord r = new BroadcastRecord(queue, intent, null, 14975 null, -1, -1, null, null, AppOpsManager.OP_NONE, receivers, null, 0, 14976 null, null, false, true, true, -1); 14977 queue.enqueueParallelBroadcastLocked(r); 14978 queue.scheduleBroadcastsLocked(); 14979 } 14980 } 14981 14982 return sticky; 14983 } 14984 } 14985 14986 public void unregisterReceiver(IIntentReceiver receiver) { 14987 if (DEBUG_BROADCAST) Slog.v(TAG, "Unregister receiver: " + receiver); 14988 14989 final long origId = Binder.clearCallingIdentity(); 14990 try { 14991 boolean doTrim = false; 14992 14993 synchronized(this) { 14994 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder()); 14995 if (rl != null) { 14996 if (rl.curBroadcast != null) { 14997 BroadcastRecord r = rl.curBroadcast; 14998 final boolean doNext = finishReceiverLocked( 14999 receiver.asBinder(), r.resultCode, r.resultData, 15000 r.resultExtras, r.resultAbort); 15001 if (doNext) { 15002 doTrim = true; 15003 r.queue.processNextBroadcast(false); 15004 } 15005 } 15006 15007 if (rl.app != null) { 15008 rl.app.receivers.remove(rl); 15009 } 15010 removeReceiverLocked(rl); 15011 if (rl.linkedToDeath) { 15012 rl.linkedToDeath = false; 15013 rl.receiver.asBinder().unlinkToDeath(rl, 0); 15014 } 15015 } 15016 } 15017 15018 // If we actually concluded any broadcasts, we might now be able 15019 // to trim the recipients' apps from our working set 15020 if (doTrim) { 15021 trimApplications(); 15022 return; 15023 } 15024 15025 } finally { 15026 Binder.restoreCallingIdentity(origId); 15027 } 15028 } 15029 15030 void removeReceiverLocked(ReceiverList rl) { 15031 mRegisteredReceivers.remove(rl.receiver.asBinder()); 15032 int N = rl.size(); 15033 for (int i=0; i<N; i++) { 15034 mReceiverResolver.removeFilter(rl.get(i)); 15035 } 15036 } 15037 15038 private final void sendPackageBroadcastLocked(int cmd, String[] packages, int userId) { 15039 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 15040 ProcessRecord r = mLruProcesses.get(i); 15041 if (r.thread != null && (userId == UserHandle.USER_ALL || r.userId == userId)) { 15042 try { 15043 r.thread.dispatchPackageBroadcast(cmd, packages); 15044 } catch (RemoteException ex) { 15045 } 15046 } 15047 } 15048 } 15049 15050 private List<ResolveInfo> collectReceiverComponents(Intent intent, String resolvedType, 15051 int[] users) { 15052 List<ResolveInfo> receivers = null; 15053 try { 15054 HashSet<ComponentName> singleUserReceivers = null; 15055 boolean scannedFirstReceivers = false; 15056 for (int user : users) { 15057 List<ResolveInfo> newReceivers = AppGlobals.getPackageManager() 15058 .queryIntentReceivers(intent, resolvedType, STOCK_PM_FLAGS, user); 15059 if (user != 0 && newReceivers != null) { 15060 // If this is not the primary user, we need to check for 15061 // any receivers that should be filtered out. 15062 for (int i=0; i<newReceivers.size(); i++) { 15063 ResolveInfo ri = newReceivers.get(i); 15064 if ((ri.activityInfo.flags&ActivityInfo.FLAG_PRIMARY_USER_ONLY) != 0) { 15065 newReceivers.remove(i); 15066 i--; 15067 } 15068 } 15069 } 15070 if (newReceivers != null && newReceivers.size() == 0) { 15071 newReceivers = null; 15072 } 15073 if (receivers == null) { 15074 receivers = newReceivers; 15075 } else if (newReceivers != null) { 15076 // We need to concatenate the additional receivers 15077 // found with what we have do far. This would be easy, 15078 // but we also need to de-dup any receivers that are 15079 // singleUser. 15080 if (!scannedFirstReceivers) { 15081 // Collect any single user receivers we had already retrieved. 15082 scannedFirstReceivers = true; 15083 for (int i=0; i<receivers.size(); i++) { 15084 ResolveInfo ri = receivers.get(i); 15085 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 15086 ComponentName cn = new ComponentName( 15087 ri.activityInfo.packageName, ri.activityInfo.name); 15088 if (singleUserReceivers == null) { 15089 singleUserReceivers = new HashSet<ComponentName>(); 15090 } 15091 singleUserReceivers.add(cn); 15092 } 15093 } 15094 } 15095 // Add the new results to the existing results, tracking 15096 // and de-dupping single user receivers. 15097 for (int i=0; i<newReceivers.size(); i++) { 15098 ResolveInfo ri = newReceivers.get(i); 15099 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 15100 ComponentName cn = new ComponentName( 15101 ri.activityInfo.packageName, ri.activityInfo.name); 15102 if (singleUserReceivers == null) { 15103 singleUserReceivers = new HashSet<ComponentName>(); 15104 } 15105 if (!singleUserReceivers.contains(cn)) { 15106 singleUserReceivers.add(cn); 15107 receivers.add(ri); 15108 } 15109 } else { 15110 receivers.add(ri); 15111 } 15112 } 15113 } 15114 } 15115 } catch (RemoteException ex) { 15116 // pm is in same process, this will never happen. 15117 } 15118 return receivers; 15119 } 15120 15121 private final int broadcastIntentLocked(ProcessRecord callerApp, 15122 String callerPackage, Intent intent, String resolvedType, 15123 IIntentReceiver resultTo, int resultCode, String resultData, 15124 Bundle map, String requiredPermission, int appOp, 15125 boolean ordered, boolean sticky, int callingPid, int callingUid, 15126 int userId) { 15127 intent = new Intent(intent); 15128 15129 // By default broadcasts do not go to stopped apps. 15130 intent.addFlags(Intent.FLAG_EXCLUDE_STOPPED_PACKAGES); 15131 15132 if (DEBUG_BROADCAST_LIGHT) Slog.v( 15133 TAG, (sticky ? "Broadcast sticky: ": "Broadcast: ") + intent 15134 + " ordered=" + ordered + " userid=" + userId); 15135 if ((resultTo != null) && !ordered) { 15136 Slog.w(TAG, "Broadcast " + intent + " not ordered but result callback requested!"); 15137 } 15138 15139 userId = handleIncomingUser(callingPid, callingUid, userId, 15140 true, ALLOW_NON_FULL, "broadcast", callerPackage); 15141 15142 // Make sure that the user who is receiving this broadcast is started. 15143 // If not, we will just skip it. 15144 15145 15146 if (userId != UserHandle.USER_ALL && mStartedUsers.get(userId) == null) { 15147 if (callingUid != Process.SYSTEM_UID || (intent.getFlags() 15148 & Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) { 15149 Slog.w(TAG, "Skipping broadcast of " + intent 15150 + ": user " + userId + " is stopped"); 15151 return ActivityManager.BROADCAST_SUCCESS; 15152 } 15153 } 15154 15155 /* 15156 * Prevent non-system code (defined here to be non-persistent 15157 * processes) from sending protected broadcasts. 15158 */ 15159 int callingAppId = UserHandle.getAppId(callingUid); 15160 if (callingAppId == Process.SYSTEM_UID || callingAppId == Process.PHONE_UID 15161 || callingAppId == Process.SHELL_UID || callingAppId == Process.BLUETOOTH_UID 15162 || callingAppId == Process.NFC_UID || callingUid == 0) { 15163 // Always okay. 15164 } else if (callerApp == null || !callerApp.persistent) { 15165 try { 15166 if (AppGlobals.getPackageManager().isProtectedBroadcast( 15167 intent.getAction())) { 15168 String msg = "Permission Denial: not allowed to send broadcast " 15169 + intent.getAction() + " from pid=" 15170 + callingPid + ", uid=" + callingUid; 15171 Slog.w(TAG, msg); 15172 throw new SecurityException(msg); 15173 } else if (AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(intent.getAction())) { 15174 // Special case for compatibility: we don't want apps to send this, 15175 // but historically it has not been protected and apps may be using it 15176 // to poke their own app widget. So, instead of making it protected, 15177 // just limit it to the caller. 15178 if (callerApp == null) { 15179 String msg = "Permission Denial: not allowed to send broadcast " 15180 + intent.getAction() + " from unknown caller."; 15181 Slog.w(TAG, msg); 15182 throw new SecurityException(msg); 15183 } else if (intent.getComponent() != null) { 15184 // They are good enough to send to an explicit component... verify 15185 // it is being sent to the calling app. 15186 if (!intent.getComponent().getPackageName().equals( 15187 callerApp.info.packageName)) { 15188 String msg = "Permission Denial: not allowed to send broadcast " 15189 + intent.getAction() + " to " 15190 + intent.getComponent().getPackageName() + " from " 15191 + callerApp.info.packageName; 15192 Slog.w(TAG, msg); 15193 throw new SecurityException(msg); 15194 } 15195 } else { 15196 // Limit broadcast to their own package. 15197 intent.setPackage(callerApp.info.packageName); 15198 } 15199 } 15200 } catch (RemoteException e) { 15201 Slog.w(TAG, "Remote exception", e); 15202 return ActivityManager.BROADCAST_SUCCESS; 15203 } 15204 } 15205 15206 // Handle special intents: if this broadcast is from the package 15207 // manager about a package being removed, we need to remove all of 15208 // its activities from the history stack. 15209 final boolean uidRemoved = Intent.ACTION_UID_REMOVED.equals( 15210 intent.getAction()); 15211 if (Intent.ACTION_PACKAGE_REMOVED.equals(intent.getAction()) 15212 || Intent.ACTION_PACKAGE_CHANGED.equals(intent.getAction()) 15213 || Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction()) 15214 || Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction()) 15215 || uidRemoved) { 15216 if (checkComponentPermission( 15217 android.Manifest.permission.BROADCAST_PACKAGE_REMOVED, 15218 callingPid, callingUid, -1, true) 15219 == PackageManager.PERMISSION_GRANTED) { 15220 if (uidRemoved) { 15221 final Bundle intentExtras = intent.getExtras(); 15222 final int uid = intentExtras != null 15223 ? intentExtras.getInt(Intent.EXTRA_UID) : -1; 15224 if (uid >= 0) { 15225 BatteryStatsImpl bs = mBatteryStatsService.getActiveStatistics(); 15226 synchronized (bs) { 15227 bs.removeUidStatsLocked(uid); 15228 } 15229 mAppOpsService.uidRemoved(uid); 15230 } 15231 } else { 15232 // If resources are unavailable just force stop all 15233 // those packages and flush the attribute cache as well. 15234 if (Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction())) { 15235 String list[] = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 15236 if (list != null && (list.length > 0)) { 15237 for (String pkg : list) { 15238 forceStopPackageLocked(pkg, -1, false, true, true, false, false, userId, 15239 "storage unmount"); 15240 } 15241 cleanupRecentTasksLocked(UserHandle.USER_ALL); 15242 sendPackageBroadcastLocked( 15243 IApplicationThread.EXTERNAL_STORAGE_UNAVAILABLE, list, userId); 15244 } 15245 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals( 15246 intent.getAction())) { 15247 cleanupRecentTasksLocked(UserHandle.USER_ALL); 15248 } else { 15249 Uri data = intent.getData(); 15250 String ssp; 15251 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 15252 boolean removed = Intent.ACTION_PACKAGE_REMOVED.equals( 15253 intent.getAction()); 15254 boolean fullUninstall = removed && 15255 !intent.getBooleanExtra(Intent.EXTRA_REPLACING, false); 15256 if (!intent.getBooleanExtra(Intent.EXTRA_DONT_KILL_APP, false)) { 15257 forceStopPackageLocked(ssp, UserHandle.getAppId( 15258 intent.getIntExtra(Intent.EXTRA_UID, -1)), false, true, true, 15259 false, fullUninstall, userId, 15260 removed ? "pkg removed" : "pkg changed"); 15261 } 15262 if (removed) { 15263 sendPackageBroadcastLocked(IApplicationThread.PACKAGE_REMOVED, 15264 new String[] {ssp}, userId); 15265 if (!intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)) { 15266 mAppOpsService.packageRemoved( 15267 intent.getIntExtra(Intent.EXTRA_UID, -1), ssp); 15268 15269 // Remove all permissions granted from/to this package 15270 removeUriPermissionsForPackageLocked(ssp, userId, true); 15271 } 15272 } 15273 } 15274 } 15275 } 15276 } else { 15277 String msg = "Permission Denial: " + intent.getAction() 15278 + " broadcast from " + callerPackage + " (pid=" + callingPid 15279 + ", uid=" + callingUid + ")" 15280 + " requires " 15281 + android.Manifest.permission.BROADCAST_PACKAGE_REMOVED; 15282 Slog.w(TAG, msg); 15283 throw new SecurityException(msg); 15284 } 15285 15286 // Special case for adding a package: by default turn on compatibility 15287 // mode. 15288 } else if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction())) { 15289 Uri data = intent.getData(); 15290 String ssp; 15291 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 15292 mCompatModePackages.handlePackageAddedLocked(ssp, 15293 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)); 15294 } 15295 } 15296 15297 /* 15298 * If this is the time zone changed action, queue up a message that will reset the timezone 15299 * of all currently running processes. This message will get queued up before the broadcast 15300 * happens. 15301 */ 15302 if (Intent.ACTION_TIMEZONE_CHANGED.equals(intent.getAction())) { 15303 mHandler.sendEmptyMessage(UPDATE_TIME_ZONE); 15304 } 15305 15306 /* 15307 * If the user set the time, let all running processes know. 15308 */ 15309 if (Intent.ACTION_TIME_CHANGED.equals(intent.getAction())) { 15310 final int is24Hour = intent.getBooleanExtra( 15311 Intent.EXTRA_TIME_PREF_24_HOUR_FORMAT, false) ? 1 : 0; 15312 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_TIME, is24Hour, 0)); 15313 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 15314 synchronized (stats) { 15315 stats.noteCurrentTimeChangedLocked(); 15316 } 15317 } 15318 15319 if (Intent.ACTION_CLEAR_DNS_CACHE.equals(intent.getAction())) { 15320 mHandler.sendEmptyMessage(CLEAR_DNS_CACHE_MSG); 15321 } 15322 15323 if (Proxy.PROXY_CHANGE_ACTION.equals(intent.getAction())) { 15324 ProxyInfo proxy = intent.getParcelableExtra(Proxy.EXTRA_PROXY_INFO); 15325 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_HTTP_PROXY_MSG, proxy)); 15326 } 15327 15328 // Add to the sticky list if requested. 15329 if (sticky) { 15330 if (checkPermission(android.Manifest.permission.BROADCAST_STICKY, 15331 callingPid, callingUid) 15332 != PackageManager.PERMISSION_GRANTED) { 15333 String msg = "Permission Denial: broadcastIntent() requesting a sticky broadcast from pid=" 15334 + callingPid + ", uid=" + callingUid 15335 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 15336 Slog.w(TAG, msg); 15337 throw new SecurityException(msg); 15338 } 15339 if (requiredPermission != null) { 15340 Slog.w(TAG, "Can't broadcast sticky intent " + intent 15341 + " and enforce permission " + requiredPermission); 15342 return ActivityManager.BROADCAST_STICKY_CANT_HAVE_PERMISSION; 15343 } 15344 if (intent.getComponent() != null) { 15345 throw new SecurityException( 15346 "Sticky broadcasts can't target a specific component"); 15347 } 15348 // We use userId directly here, since the "all" target is maintained 15349 // as a separate set of sticky broadcasts. 15350 if (userId != UserHandle.USER_ALL) { 15351 // But first, if this is not a broadcast to all users, then 15352 // make sure it doesn't conflict with an existing broadcast to 15353 // all users. 15354 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get( 15355 UserHandle.USER_ALL); 15356 if (stickies != null) { 15357 ArrayList<Intent> list = stickies.get(intent.getAction()); 15358 if (list != null) { 15359 int N = list.size(); 15360 int i; 15361 for (i=0; i<N; i++) { 15362 if (intent.filterEquals(list.get(i))) { 15363 throw new IllegalArgumentException( 15364 "Sticky broadcast " + intent + " for user " 15365 + userId + " conflicts with existing global broadcast"); 15366 } 15367 } 15368 } 15369 } 15370 } 15371 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 15372 if (stickies == null) { 15373 stickies = new ArrayMap<String, ArrayList<Intent>>(); 15374 mStickyBroadcasts.put(userId, stickies); 15375 } 15376 ArrayList<Intent> list = stickies.get(intent.getAction()); 15377 if (list == null) { 15378 list = new ArrayList<Intent>(); 15379 stickies.put(intent.getAction(), list); 15380 } 15381 int N = list.size(); 15382 int i; 15383 for (i=0; i<N; i++) { 15384 if (intent.filterEquals(list.get(i))) { 15385 // This sticky already exists, replace it. 15386 list.set(i, new Intent(intent)); 15387 break; 15388 } 15389 } 15390 if (i >= N) { 15391 list.add(new Intent(intent)); 15392 } 15393 } 15394 15395 int[] users; 15396 if (userId == UserHandle.USER_ALL) { 15397 // Caller wants broadcast to go to all started users. 15398 users = mStartedUserArray; 15399 } else { 15400 // Caller wants broadcast to go to one specific user. 15401 users = new int[] {userId}; 15402 } 15403 15404 // Figure out who all will receive this broadcast. 15405 List receivers = null; 15406 List<BroadcastFilter> registeredReceivers = null; 15407 // Need to resolve the intent to interested receivers... 15408 if ((intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) 15409 == 0) { 15410 receivers = collectReceiverComponents(intent, resolvedType, users); 15411 } 15412 if (intent.getComponent() == null) { 15413 registeredReceivers = mReceiverResolver.queryIntent(intent, 15414 resolvedType, false, userId); 15415 } 15416 15417 final boolean replacePending = 15418 (intent.getFlags()&Intent.FLAG_RECEIVER_REPLACE_PENDING) != 0; 15419 15420 if (DEBUG_BROADCAST) Slog.v(TAG, "Enqueing broadcast: " + intent.getAction() 15421 + " replacePending=" + replacePending); 15422 15423 int NR = registeredReceivers != null ? registeredReceivers.size() : 0; 15424 if (!ordered && NR > 0) { 15425 // If we are not serializing this broadcast, then send the 15426 // registered receivers separately so they don't wait for the 15427 // components to be launched. 15428 final BroadcastQueue queue = broadcastQueueForIntent(intent); 15429 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 15430 callerPackage, callingPid, callingUid, resolvedType, requiredPermission, 15431 appOp, registeredReceivers, resultTo, resultCode, resultData, map, 15432 ordered, sticky, false, userId); 15433 if (DEBUG_BROADCAST) Slog.v( 15434 TAG, "Enqueueing parallel broadcast " + r); 15435 final boolean replaced = replacePending && queue.replaceParallelBroadcastLocked(r); 15436 if (!replaced) { 15437 queue.enqueueParallelBroadcastLocked(r); 15438 queue.scheduleBroadcastsLocked(); 15439 } 15440 registeredReceivers = null; 15441 NR = 0; 15442 } 15443 15444 // Merge into one list. 15445 int ir = 0; 15446 if (receivers != null) { 15447 // A special case for PACKAGE_ADDED: do not allow the package 15448 // being added to see this broadcast. This prevents them from 15449 // using this as a back door to get run as soon as they are 15450 // installed. Maybe in the future we want to have a special install 15451 // broadcast or such for apps, but we'd like to deliberately make 15452 // this decision. 15453 String skipPackages[] = null; 15454 if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction()) 15455 || Intent.ACTION_PACKAGE_RESTARTED.equals(intent.getAction()) 15456 || Intent.ACTION_PACKAGE_DATA_CLEARED.equals(intent.getAction())) { 15457 Uri data = intent.getData(); 15458 if (data != null) { 15459 String pkgName = data.getSchemeSpecificPart(); 15460 if (pkgName != null) { 15461 skipPackages = new String[] { pkgName }; 15462 } 15463 } 15464 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction())) { 15465 skipPackages = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 15466 } 15467 if (skipPackages != null && (skipPackages.length > 0)) { 15468 for (String skipPackage : skipPackages) { 15469 if (skipPackage != null) { 15470 int NT = receivers.size(); 15471 for (int it=0; it<NT; it++) { 15472 ResolveInfo curt = (ResolveInfo)receivers.get(it); 15473 if (curt.activityInfo.packageName.equals(skipPackage)) { 15474 receivers.remove(it); 15475 it--; 15476 NT--; 15477 } 15478 } 15479 } 15480 } 15481 } 15482 15483 int NT = receivers != null ? receivers.size() : 0; 15484 int it = 0; 15485 ResolveInfo curt = null; 15486 BroadcastFilter curr = null; 15487 while (it < NT && ir < NR) { 15488 if (curt == null) { 15489 curt = (ResolveInfo)receivers.get(it); 15490 } 15491 if (curr == null) { 15492 curr = registeredReceivers.get(ir); 15493 } 15494 if (curr.getPriority() >= curt.priority) { 15495 // Insert this broadcast record into the final list. 15496 receivers.add(it, curr); 15497 ir++; 15498 curr = null; 15499 it++; 15500 NT++; 15501 } else { 15502 // Skip to the next ResolveInfo in the final list. 15503 it++; 15504 curt = null; 15505 } 15506 } 15507 } 15508 while (ir < NR) { 15509 if (receivers == null) { 15510 receivers = new ArrayList(); 15511 } 15512 receivers.add(registeredReceivers.get(ir)); 15513 ir++; 15514 } 15515 15516 if ((receivers != null && receivers.size() > 0) 15517 || resultTo != null) { 15518 BroadcastQueue queue = broadcastQueueForIntent(intent); 15519 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 15520 callerPackage, callingPid, callingUid, resolvedType, 15521 requiredPermission, appOp, receivers, resultTo, resultCode, 15522 resultData, map, ordered, sticky, false, userId); 15523 if (DEBUG_BROADCAST) Slog.v( 15524 TAG, "Enqueueing ordered broadcast " + r 15525 + ": prev had " + queue.mOrderedBroadcasts.size()); 15526 if (DEBUG_BROADCAST) { 15527 int seq = r.intent.getIntExtra("seq", -1); 15528 Slog.i(TAG, "Enqueueing broadcast " + r.intent.getAction() + " seq=" + seq); 15529 } 15530 boolean replaced = replacePending && queue.replaceOrderedBroadcastLocked(r); 15531 if (!replaced) { 15532 queue.enqueueOrderedBroadcastLocked(r); 15533 queue.scheduleBroadcastsLocked(); 15534 } 15535 } 15536 15537 return ActivityManager.BROADCAST_SUCCESS; 15538 } 15539 15540 final Intent verifyBroadcastLocked(Intent intent) { 15541 // Refuse possible leaked file descriptors 15542 if (intent != null && intent.hasFileDescriptors() == true) { 15543 throw new IllegalArgumentException("File descriptors passed in Intent"); 15544 } 15545 15546 int flags = intent.getFlags(); 15547 15548 if (!mProcessesReady) { 15549 // if the caller really truly claims to know what they're doing, go 15550 // ahead and allow the broadcast without launching any receivers 15551 if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT) != 0) { 15552 intent = new Intent(intent); 15553 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 15554 } else if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) { 15555 Slog.e(TAG, "Attempt to launch receivers of broadcast intent " + intent 15556 + " before boot completion"); 15557 throw new IllegalStateException("Cannot broadcast before boot completed"); 15558 } 15559 } 15560 15561 if ((flags&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 15562 throw new IllegalArgumentException( 15563 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 15564 } 15565 15566 return intent; 15567 } 15568 15569 public final int broadcastIntent(IApplicationThread caller, 15570 Intent intent, String resolvedType, IIntentReceiver resultTo, 15571 int resultCode, String resultData, Bundle map, 15572 String requiredPermission, int appOp, boolean serialized, boolean sticky, int userId) { 15573 enforceNotIsolatedCaller("broadcastIntent"); 15574 synchronized(this) { 15575 intent = verifyBroadcastLocked(intent); 15576 15577 final ProcessRecord callerApp = getRecordForAppLocked(caller); 15578 final int callingPid = Binder.getCallingPid(); 15579 final int callingUid = Binder.getCallingUid(); 15580 final long origId = Binder.clearCallingIdentity(); 15581 int res = broadcastIntentLocked(callerApp, 15582 callerApp != null ? callerApp.info.packageName : null, 15583 intent, resolvedType, resultTo, 15584 resultCode, resultData, map, requiredPermission, appOp, serialized, sticky, 15585 callingPid, callingUid, userId); 15586 Binder.restoreCallingIdentity(origId); 15587 return res; 15588 } 15589 } 15590 15591 int broadcastIntentInPackage(String packageName, int uid, 15592 Intent intent, String resolvedType, IIntentReceiver resultTo, 15593 int resultCode, String resultData, Bundle map, 15594 String requiredPermission, boolean serialized, boolean sticky, int userId) { 15595 synchronized(this) { 15596 intent = verifyBroadcastLocked(intent); 15597 15598 final long origId = Binder.clearCallingIdentity(); 15599 int res = broadcastIntentLocked(null, packageName, intent, resolvedType, 15600 resultTo, resultCode, resultData, map, requiredPermission, 15601 AppOpsManager.OP_NONE, serialized, sticky, -1, uid, userId); 15602 Binder.restoreCallingIdentity(origId); 15603 return res; 15604 } 15605 } 15606 15607 public final void unbroadcastIntent(IApplicationThread caller, Intent intent, int userId) { 15608 // Refuse possible leaked file descriptors 15609 if (intent != null && intent.hasFileDescriptors() == true) { 15610 throw new IllegalArgumentException("File descriptors passed in Intent"); 15611 } 15612 15613 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 15614 userId, true, ALLOW_NON_FULL, "removeStickyBroadcast", null); 15615 15616 synchronized(this) { 15617 if (checkCallingPermission(android.Manifest.permission.BROADCAST_STICKY) 15618 != PackageManager.PERMISSION_GRANTED) { 15619 String msg = "Permission Denial: unbroadcastIntent() from pid=" 15620 + Binder.getCallingPid() 15621 + ", uid=" + Binder.getCallingUid() 15622 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 15623 Slog.w(TAG, msg); 15624 throw new SecurityException(msg); 15625 } 15626 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 15627 if (stickies != null) { 15628 ArrayList<Intent> list = stickies.get(intent.getAction()); 15629 if (list != null) { 15630 int N = list.size(); 15631 int i; 15632 for (i=0; i<N; i++) { 15633 if (intent.filterEquals(list.get(i))) { 15634 list.remove(i); 15635 break; 15636 } 15637 } 15638 if (list.size() <= 0) { 15639 stickies.remove(intent.getAction()); 15640 } 15641 } 15642 if (stickies.size() <= 0) { 15643 mStickyBroadcasts.remove(userId); 15644 } 15645 } 15646 } 15647 } 15648 15649 private final boolean finishReceiverLocked(IBinder receiver, int resultCode, 15650 String resultData, Bundle resultExtras, boolean resultAbort) { 15651 final BroadcastRecord r = broadcastRecordForReceiverLocked(receiver); 15652 if (r == null) { 15653 Slog.w(TAG, "finishReceiver called but not found on queue"); 15654 return false; 15655 } 15656 15657 return r.queue.finishReceiverLocked(r, resultCode, resultData, resultExtras, resultAbort, false); 15658 } 15659 15660 void backgroundServicesFinishedLocked(int userId) { 15661 for (BroadcastQueue queue : mBroadcastQueues) { 15662 queue.backgroundServicesFinishedLocked(userId); 15663 } 15664 } 15665 15666 public void finishReceiver(IBinder who, int resultCode, String resultData, 15667 Bundle resultExtras, boolean resultAbort) { 15668 if (DEBUG_BROADCAST) Slog.v(TAG, "Finish receiver: " + who); 15669 15670 // Refuse possible leaked file descriptors 15671 if (resultExtras != null && resultExtras.hasFileDescriptors()) { 15672 throw new IllegalArgumentException("File descriptors passed in Bundle"); 15673 } 15674 15675 final long origId = Binder.clearCallingIdentity(); 15676 try { 15677 boolean doNext = false; 15678 BroadcastRecord r; 15679 15680 synchronized(this) { 15681 r = broadcastRecordForReceiverLocked(who); 15682 if (r != null) { 15683 doNext = r.queue.finishReceiverLocked(r, resultCode, 15684 resultData, resultExtras, resultAbort, true); 15685 } 15686 } 15687 15688 if (doNext) { 15689 r.queue.processNextBroadcast(false); 15690 } 15691 trimApplications(); 15692 } finally { 15693 Binder.restoreCallingIdentity(origId); 15694 } 15695 } 15696 15697 // ========================================================= 15698 // INSTRUMENTATION 15699 // ========================================================= 15700 15701 public boolean startInstrumentation(ComponentName className, 15702 String profileFile, int flags, Bundle arguments, 15703 IInstrumentationWatcher watcher, IUiAutomationConnection uiAutomationConnection, 15704 int userId, String abiOverride) { 15705 enforceNotIsolatedCaller("startInstrumentation"); 15706 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 15707 userId, false, ALLOW_FULL_ONLY, "startInstrumentation", null); 15708 // Refuse possible leaked file descriptors 15709 if (arguments != null && arguments.hasFileDescriptors()) { 15710 throw new IllegalArgumentException("File descriptors passed in Bundle"); 15711 } 15712 15713 synchronized(this) { 15714 InstrumentationInfo ii = null; 15715 ApplicationInfo ai = null; 15716 try { 15717 ii = mContext.getPackageManager().getInstrumentationInfo( 15718 className, STOCK_PM_FLAGS); 15719 ai = AppGlobals.getPackageManager().getApplicationInfo( 15720 ii.targetPackage, STOCK_PM_FLAGS, userId); 15721 } catch (PackageManager.NameNotFoundException e) { 15722 } catch (RemoteException e) { 15723 } 15724 if (ii == null) { 15725 reportStartInstrumentationFailure(watcher, className, 15726 "Unable to find instrumentation info for: " + className); 15727 return false; 15728 } 15729 if (ai == null) { 15730 reportStartInstrumentationFailure(watcher, className, 15731 "Unable to find instrumentation target package: " + ii.targetPackage); 15732 return false; 15733 } 15734 15735 int match = mContext.getPackageManager().checkSignatures( 15736 ii.targetPackage, ii.packageName); 15737 if (match < 0 && match != PackageManager.SIGNATURE_FIRST_NOT_SIGNED) { 15738 String msg = "Permission Denial: starting instrumentation " 15739 + className + " from pid=" 15740 + Binder.getCallingPid() 15741 + ", uid=" + Binder.getCallingPid() 15742 + " not allowed because package " + ii.packageName 15743 + " does not have a signature matching the target " 15744 + ii.targetPackage; 15745 reportStartInstrumentationFailure(watcher, className, msg); 15746 throw new SecurityException(msg); 15747 } 15748 15749 final long origId = Binder.clearCallingIdentity(); 15750 // Instrumentation can kill and relaunch even persistent processes 15751 forceStopPackageLocked(ii.targetPackage, -1, true, false, true, true, false, userId, 15752 "start instr"); 15753 ProcessRecord app = addAppLocked(ai, false, abiOverride); 15754 app.instrumentationClass = className; 15755 app.instrumentationInfo = ai; 15756 app.instrumentationProfileFile = profileFile; 15757 app.instrumentationArguments = arguments; 15758 app.instrumentationWatcher = watcher; 15759 app.instrumentationUiAutomationConnection = uiAutomationConnection; 15760 app.instrumentationResultClass = className; 15761 Binder.restoreCallingIdentity(origId); 15762 } 15763 15764 return true; 15765 } 15766 15767 /** 15768 * Report errors that occur while attempting to start Instrumentation. Always writes the 15769 * error to the logs, but if somebody is watching, send the report there too. This enables 15770 * the "am" command to report errors with more information. 15771 * 15772 * @param watcher The IInstrumentationWatcher. Null if there isn't one. 15773 * @param cn The component name of the instrumentation. 15774 * @param report The error report. 15775 */ 15776 private void reportStartInstrumentationFailure(IInstrumentationWatcher watcher, 15777 ComponentName cn, String report) { 15778 Slog.w(TAG, report); 15779 try { 15780 if (watcher != null) { 15781 Bundle results = new Bundle(); 15782 results.putString(Instrumentation.REPORT_KEY_IDENTIFIER, "ActivityManagerService"); 15783 results.putString("Error", report); 15784 watcher.instrumentationStatus(cn, -1, results); 15785 } 15786 } catch (RemoteException e) { 15787 Slog.w(TAG, e); 15788 } 15789 } 15790 15791 void finishInstrumentationLocked(ProcessRecord app, int resultCode, Bundle results) { 15792 if (app.instrumentationWatcher != null) { 15793 try { 15794 // NOTE: IInstrumentationWatcher *must* be oneway here 15795 app.instrumentationWatcher.instrumentationFinished( 15796 app.instrumentationClass, 15797 resultCode, 15798 results); 15799 } catch (RemoteException e) { 15800 } 15801 } 15802 if (app.instrumentationUiAutomationConnection != null) { 15803 try { 15804 app.instrumentationUiAutomationConnection.shutdown(); 15805 } catch (RemoteException re) { 15806 /* ignore */ 15807 } 15808 // Only a UiAutomation can set this flag and now that 15809 // it is finished we make sure it is reset to its default. 15810 mUserIsMonkey = false; 15811 } 15812 app.instrumentationWatcher = null; 15813 app.instrumentationUiAutomationConnection = null; 15814 app.instrumentationClass = null; 15815 app.instrumentationInfo = null; 15816 app.instrumentationProfileFile = null; 15817 app.instrumentationArguments = null; 15818 15819 forceStopPackageLocked(app.info.packageName, -1, false, false, true, true, false, app.userId, 15820 "finished inst"); 15821 } 15822 15823 public void finishInstrumentation(IApplicationThread target, 15824 int resultCode, Bundle results) { 15825 int userId = UserHandle.getCallingUserId(); 15826 // Refuse possible leaked file descriptors 15827 if (results != null && results.hasFileDescriptors()) { 15828 throw new IllegalArgumentException("File descriptors passed in Intent"); 15829 } 15830 15831 synchronized(this) { 15832 ProcessRecord app = getRecordForAppLocked(target); 15833 if (app == null) { 15834 Slog.w(TAG, "finishInstrumentation: no app for " + target); 15835 return; 15836 } 15837 final long origId = Binder.clearCallingIdentity(); 15838 finishInstrumentationLocked(app, resultCode, results); 15839 Binder.restoreCallingIdentity(origId); 15840 } 15841 } 15842 15843 // ========================================================= 15844 // CONFIGURATION 15845 // ========================================================= 15846 15847 public ConfigurationInfo getDeviceConfigurationInfo() { 15848 ConfigurationInfo config = new ConfigurationInfo(); 15849 synchronized (this) { 15850 config.reqTouchScreen = mConfiguration.touchscreen; 15851 config.reqKeyboardType = mConfiguration.keyboard; 15852 config.reqNavigation = mConfiguration.navigation; 15853 if (mConfiguration.navigation == Configuration.NAVIGATION_DPAD 15854 || mConfiguration.navigation == Configuration.NAVIGATION_TRACKBALL) { 15855 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_FIVE_WAY_NAV; 15856 } 15857 if (mConfiguration.keyboard != Configuration.KEYBOARD_UNDEFINED 15858 && mConfiguration.keyboard != Configuration.KEYBOARD_NOKEYS) { 15859 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_HARD_KEYBOARD; 15860 } 15861 config.reqGlEsVersion = GL_ES_VERSION; 15862 } 15863 return config; 15864 } 15865 15866 ActivityStack getFocusedStack() { 15867 return mStackSupervisor.getFocusedStack(); 15868 } 15869 15870 public Configuration getConfiguration() { 15871 Configuration ci; 15872 synchronized(this) { 15873 ci = new Configuration(mConfiguration); 15874 } 15875 return ci; 15876 } 15877 15878 public void updatePersistentConfiguration(Configuration values) { 15879 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 15880 "updateConfiguration()"); 15881 enforceCallingPermission(android.Manifest.permission.WRITE_SETTINGS, 15882 "updateConfiguration()"); 15883 if (values == null) { 15884 throw new NullPointerException("Configuration must not be null"); 15885 } 15886 15887 synchronized(this) { 15888 final long origId = Binder.clearCallingIdentity(); 15889 updateConfigurationLocked(values, null, true, false); 15890 Binder.restoreCallingIdentity(origId); 15891 } 15892 } 15893 15894 public void updateConfiguration(Configuration values) { 15895 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 15896 "updateConfiguration()"); 15897 15898 synchronized(this) { 15899 if (values == null && mWindowManager != null) { 15900 // sentinel: fetch the current configuration from the window manager 15901 values = mWindowManager.computeNewConfiguration(); 15902 } 15903 15904 if (mWindowManager != null) { 15905 mProcessList.applyDisplaySize(mWindowManager); 15906 } 15907 15908 final long origId = Binder.clearCallingIdentity(); 15909 if (values != null) { 15910 Settings.System.clearConfiguration(values); 15911 } 15912 updateConfigurationLocked(values, null, false, false); 15913 Binder.restoreCallingIdentity(origId); 15914 } 15915 } 15916 15917 /** 15918 * Do either or both things: (1) change the current configuration, and (2) 15919 * make sure the given activity is running with the (now) current 15920 * configuration. Returns true if the activity has been left running, or 15921 * false if <var>starting</var> is being destroyed to match the new 15922 * configuration. 15923 * @param persistent TODO 15924 */ 15925 boolean updateConfigurationLocked(Configuration values, 15926 ActivityRecord starting, boolean persistent, boolean initLocale) { 15927 int changes = 0; 15928 15929 if (values != null) { 15930 Configuration newConfig = new Configuration(mConfiguration); 15931 changes = newConfig.updateFrom(values); 15932 if (changes != 0) { 15933 if (DEBUG_SWITCH || DEBUG_CONFIGURATION) { 15934 Slog.i(TAG, "Updating configuration to: " + values); 15935 } 15936 15937 EventLog.writeEvent(EventLogTags.CONFIGURATION_CHANGED, changes); 15938 15939 if (values.locale != null && !initLocale) { 15940 saveLocaleLocked(values.locale, 15941 !values.locale.equals(mConfiguration.locale), 15942 values.userSetLocale); 15943 } 15944 15945 mConfigurationSeq++; 15946 if (mConfigurationSeq <= 0) { 15947 mConfigurationSeq = 1; 15948 } 15949 newConfig.seq = mConfigurationSeq; 15950 mConfiguration = newConfig; 15951 Slog.i(TAG, "Config changes=" + Integer.toHexString(changes) + " " + newConfig); 15952 mUsageStatsService.reportConfigurationChange(newConfig, mCurrentUserId); 15953 //mUsageStatsService.noteStartConfig(newConfig); 15954 15955 final Configuration configCopy = new Configuration(mConfiguration); 15956 15957 // TODO: If our config changes, should we auto dismiss any currently 15958 // showing dialogs? 15959 mShowDialogs = shouldShowDialogs(newConfig); 15960 15961 AttributeCache ac = AttributeCache.instance(); 15962 if (ac != null) { 15963 ac.updateConfiguration(configCopy); 15964 } 15965 15966 // Make sure all resources in our process are updated 15967 // right now, so that anyone who is going to retrieve 15968 // resource values after we return will be sure to get 15969 // the new ones. This is especially important during 15970 // boot, where the first config change needs to guarantee 15971 // all resources have that config before following boot 15972 // code is executed. 15973 mSystemThread.applyConfigurationToResources(configCopy); 15974 15975 if (persistent && Settings.System.hasInterestingConfigurationChanges(changes)) { 15976 Message msg = mHandler.obtainMessage(UPDATE_CONFIGURATION_MSG); 15977 msg.obj = new Configuration(configCopy); 15978 mHandler.sendMessage(msg); 15979 } 15980 15981 for (int i=mLruProcesses.size()-1; i>=0; i--) { 15982 ProcessRecord app = mLruProcesses.get(i); 15983 try { 15984 if (app.thread != null) { 15985 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Sending to proc " 15986 + app.processName + " new config " + mConfiguration); 15987 app.thread.scheduleConfigurationChanged(configCopy); 15988 } 15989 } catch (Exception e) { 15990 } 15991 } 15992 Intent intent = new Intent(Intent.ACTION_CONFIGURATION_CHANGED); 15993 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 15994 | Intent.FLAG_RECEIVER_REPLACE_PENDING 15995 | Intent.FLAG_RECEIVER_FOREGROUND); 15996 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, 15997 null, AppOpsManager.OP_NONE, false, false, MY_PID, 15998 Process.SYSTEM_UID, UserHandle.USER_ALL); 15999 if ((changes&ActivityInfo.CONFIG_LOCALE) != 0) { 16000 intent = new Intent(Intent.ACTION_LOCALE_CHANGED); 16001 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 16002 broadcastIntentLocked(null, null, intent, 16003 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 16004 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 16005 } 16006 } 16007 } 16008 16009 boolean kept = true; 16010 final ActivityStack mainStack = mStackSupervisor.getFocusedStack(); 16011 // mainStack is null during startup. 16012 if (mainStack != null) { 16013 if (changes != 0 && starting == null) { 16014 // If the configuration changed, and the caller is not already 16015 // in the process of starting an activity, then find the top 16016 // activity to check if its configuration needs to change. 16017 starting = mainStack.topRunningActivityLocked(null); 16018 } 16019 16020 if (starting != null) { 16021 kept = mainStack.ensureActivityConfigurationLocked(starting, changes); 16022 // And we need to make sure at this point that all other activities 16023 // are made visible with the correct configuration. 16024 mStackSupervisor.ensureActivitiesVisibleLocked(starting, changes); 16025 } 16026 } 16027 16028 if (values != null && mWindowManager != null) { 16029 mWindowManager.setNewConfiguration(mConfiguration); 16030 } 16031 16032 return kept; 16033 } 16034 16035 /** 16036 * Decide based on the configuration whether we should shouw the ANR, 16037 * crash, etc dialogs. The idea is that if there is no affordnace to 16038 * press the on-screen buttons, we shouldn't show the dialog. 16039 * 16040 * A thought: SystemUI might also want to get told about this, the Power 16041 * dialog / global actions also might want different behaviors. 16042 */ 16043 private static final boolean shouldShowDialogs(Configuration config) { 16044 return !(config.keyboard == Configuration.KEYBOARD_NOKEYS 16045 && config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH); 16046 } 16047 16048 /** 16049 * Save the locale. You must be inside a synchronized (this) block. 16050 */ 16051 private void saveLocaleLocked(Locale l, boolean isDiff, boolean isPersist) { 16052 if(isDiff) { 16053 SystemProperties.set("user.language", l.getLanguage()); 16054 SystemProperties.set("user.region", l.getCountry()); 16055 } 16056 16057 if(isPersist) { 16058 SystemProperties.set("persist.sys.language", l.getLanguage()); 16059 SystemProperties.set("persist.sys.country", l.getCountry()); 16060 SystemProperties.set("persist.sys.localevar", l.getVariant()); 16061 } 16062 } 16063 16064 @Override 16065 public boolean shouldUpRecreateTask(IBinder token, String destAffinity) { 16066 synchronized (this) { 16067 ActivityRecord srec = ActivityRecord.forToken(token); 16068 if (srec.task != null && srec.task.stack != null) { 16069 return srec.task.stack.shouldUpRecreateTaskLocked(srec, destAffinity); 16070 } 16071 } 16072 return false; 16073 } 16074 16075 public boolean navigateUpTo(IBinder token, Intent destIntent, int resultCode, 16076 Intent resultData) { 16077 16078 synchronized (this) { 16079 final ActivityStack stack = ActivityRecord.getStackLocked(token); 16080 if (stack != null) { 16081 return stack.navigateUpToLocked(token, destIntent, resultCode, resultData); 16082 } 16083 return false; 16084 } 16085 } 16086 16087 public int getLaunchedFromUid(IBinder activityToken) { 16088 ActivityRecord srec = ActivityRecord.forToken(activityToken); 16089 if (srec == null) { 16090 return -1; 16091 } 16092 return srec.launchedFromUid; 16093 } 16094 16095 public String getLaunchedFromPackage(IBinder activityToken) { 16096 ActivityRecord srec = ActivityRecord.forToken(activityToken); 16097 if (srec == null) { 16098 return null; 16099 } 16100 return srec.launchedFromPackage; 16101 } 16102 16103 // ========================================================= 16104 // LIFETIME MANAGEMENT 16105 // ========================================================= 16106 16107 // Returns which broadcast queue the app is the current [or imminent] receiver 16108 // on, or 'null' if the app is not an active broadcast recipient. 16109 private BroadcastQueue isReceivingBroadcast(ProcessRecord app) { 16110 BroadcastRecord r = app.curReceiver; 16111 if (r != null) { 16112 return r.queue; 16113 } 16114 16115 // It's not the current receiver, but it might be starting up to become one 16116 synchronized (this) { 16117 for (BroadcastQueue queue : mBroadcastQueues) { 16118 r = queue.mPendingBroadcast; 16119 if (r != null && r.curApp == app) { 16120 // found it; report which queue it's in 16121 return queue; 16122 } 16123 } 16124 } 16125 16126 return null; 16127 } 16128 16129 private final int computeOomAdjLocked(ProcessRecord app, int cachedAdj, ProcessRecord TOP_APP, 16130 boolean doingAll, long now) { 16131 if (mAdjSeq == app.adjSeq) { 16132 // This adjustment has already been computed. 16133 return app.curRawAdj; 16134 } 16135 16136 if (app.thread == null) { 16137 app.adjSeq = mAdjSeq; 16138 app.curSchedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16139 app.curProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16140 return (app.curAdj=app.curRawAdj=ProcessList.CACHED_APP_MAX_ADJ); 16141 } 16142 16143 app.adjTypeCode = ActivityManager.RunningAppProcessInfo.REASON_UNKNOWN; 16144 app.adjSource = null; 16145 app.adjTarget = null; 16146 app.empty = false; 16147 app.cached = false; 16148 16149 final int activitiesSize = app.activities.size(); 16150 16151 if (app.maxAdj <= ProcessList.FOREGROUND_APP_ADJ) { 16152 // The max adjustment doesn't allow this app to be anything 16153 // below foreground, so it is not worth doing work for it. 16154 app.adjType = "fixed"; 16155 app.adjSeq = mAdjSeq; 16156 app.curRawAdj = app.maxAdj; 16157 app.foregroundActivities = false; 16158 app.curSchedGroup = Process.THREAD_GROUP_DEFAULT; 16159 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT; 16160 // System processes can do UI, and when they do we want to have 16161 // them trim their memory after the user leaves the UI. To 16162 // facilitate this, here we need to determine whether or not it 16163 // is currently showing UI. 16164 app.systemNoUi = true; 16165 if (app == TOP_APP) { 16166 app.systemNoUi = false; 16167 } else if (activitiesSize > 0) { 16168 for (int j = 0; j < activitiesSize; j++) { 16169 final ActivityRecord r = app.activities.get(j); 16170 if (r.visible) { 16171 app.systemNoUi = false; 16172 } 16173 } 16174 } 16175 if (!app.systemNoUi) { 16176 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT_UI; 16177 } 16178 return (app.curAdj=app.maxAdj); 16179 } 16180 16181 app.systemNoUi = false; 16182 16183 // Determine the importance of the process, starting with most 16184 // important to least, and assign an appropriate OOM adjustment. 16185 int adj; 16186 int schedGroup; 16187 int procState; 16188 boolean foregroundActivities = false; 16189 BroadcastQueue queue; 16190 if (app == TOP_APP) { 16191 // The last app on the list is the foreground app. 16192 adj = ProcessList.FOREGROUND_APP_ADJ; 16193 schedGroup = Process.THREAD_GROUP_DEFAULT; 16194 app.adjType = "top-activity"; 16195 foregroundActivities = true; 16196 procState = ActivityManager.PROCESS_STATE_TOP; 16197 } else if (app.instrumentationClass != null) { 16198 // Don't want to kill running instrumentation. 16199 adj = ProcessList.FOREGROUND_APP_ADJ; 16200 schedGroup = Process.THREAD_GROUP_DEFAULT; 16201 app.adjType = "instrumentation"; 16202 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16203 } else if ((queue = isReceivingBroadcast(app)) != null) { 16204 // An app that is currently receiving a broadcast also 16205 // counts as being in the foreground for OOM killer purposes. 16206 // It's placed in a sched group based on the nature of the 16207 // broadcast as reflected by which queue it's active in. 16208 adj = ProcessList.FOREGROUND_APP_ADJ; 16209 schedGroup = (queue == mFgBroadcastQueue) 16210 ? Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 16211 app.adjType = "broadcast"; 16212 procState = ActivityManager.PROCESS_STATE_RECEIVER; 16213 } else if (app.executingServices.size() > 0) { 16214 // An app that is currently executing a service callback also 16215 // counts as being in the foreground. 16216 adj = ProcessList.FOREGROUND_APP_ADJ; 16217 schedGroup = app.execServicesFg ? 16218 Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 16219 app.adjType = "exec-service"; 16220 procState = ActivityManager.PROCESS_STATE_SERVICE; 16221 //Slog.i(TAG, "EXEC " + (app.execServicesFg ? "FG" : "BG") + ": " + app); 16222 } else { 16223 // As far as we know the process is empty. We may change our mind later. 16224 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16225 // At this point we don't actually know the adjustment. Use the cached adj 16226 // value that the caller wants us to. 16227 adj = cachedAdj; 16228 procState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16229 app.cached = true; 16230 app.empty = true; 16231 app.adjType = "cch-empty"; 16232 } 16233 16234 // Examine all activities if not already foreground. 16235 if (!foregroundActivities && activitiesSize > 0) { 16236 for (int j = 0; j < activitiesSize; j++) { 16237 final ActivityRecord r = app.activities.get(j); 16238 if (r.app != app) { 16239 Slog.w(TAG, "Wtf, activity " + r + " in proc activity list not using proc " 16240 + app + "?!?"); 16241 continue; 16242 } 16243 if (r.visible) { 16244 // App has a visible activity; only upgrade adjustment. 16245 if (adj > ProcessList.VISIBLE_APP_ADJ) { 16246 adj = ProcessList.VISIBLE_APP_ADJ; 16247 app.adjType = "visible"; 16248 } 16249 if (procState > ActivityManager.PROCESS_STATE_TOP) { 16250 procState = ActivityManager.PROCESS_STATE_TOP; 16251 } 16252 schedGroup = Process.THREAD_GROUP_DEFAULT; 16253 app.cached = false; 16254 app.empty = false; 16255 foregroundActivities = true; 16256 break; 16257 } else if (r.state == ActivityState.PAUSING || r.state == ActivityState.PAUSED) { 16258 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16259 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16260 app.adjType = "pausing"; 16261 } 16262 if (procState > ActivityManager.PROCESS_STATE_TOP) { 16263 procState = ActivityManager.PROCESS_STATE_TOP; 16264 } 16265 schedGroup = Process.THREAD_GROUP_DEFAULT; 16266 app.cached = false; 16267 app.empty = false; 16268 foregroundActivities = true; 16269 } else if (r.state == ActivityState.STOPPING) { 16270 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16271 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16272 app.adjType = "stopping"; 16273 } 16274 // For the process state, we will at this point consider the 16275 // process to be cached. It will be cached either as an activity 16276 // or empty depending on whether the activity is finishing. We do 16277 // this so that we can treat the process as cached for purposes of 16278 // memory trimming (determing current memory level, trim command to 16279 // send to process) since there can be an arbitrary number of stopping 16280 // processes and they should soon all go into the cached state. 16281 if (!r.finishing) { 16282 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 16283 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 16284 } 16285 } 16286 app.cached = false; 16287 app.empty = false; 16288 foregroundActivities = true; 16289 } else { 16290 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 16291 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 16292 app.adjType = "cch-act"; 16293 } 16294 } 16295 } 16296 } 16297 16298 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16299 if (app.foregroundServices) { 16300 // The user is aware of this app, so make it visible. 16301 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16302 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16303 app.cached = false; 16304 app.adjType = "fg-service"; 16305 schedGroup = Process.THREAD_GROUP_DEFAULT; 16306 } else if (app.forcingToForeground != null) { 16307 // The user is aware of this app, so make it visible. 16308 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16309 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16310 app.cached = false; 16311 app.adjType = "force-fg"; 16312 app.adjSource = app.forcingToForeground; 16313 schedGroup = Process.THREAD_GROUP_DEFAULT; 16314 } 16315 } 16316 16317 if (app == mHeavyWeightProcess) { 16318 if (adj > ProcessList.HEAVY_WEIGHT_APP_ADJ) { 16319 // We don't want to kill the current heavy-weight process. 16320 adj = ProcessList.HEAVY_WEIGHT_APP_ADJ; 16321 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16322 app.cached = false; 16323 app.adjType = "heavy"; 16324 } 16325 if (procState > ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 16326 procState = ActivityManager.PROCESS_STATE_HEAVY_WEIGHT; 16327 } 16328 } 16329 16330 if (app == mHomeProcess) { 16331 if (adj > ProcessList.HOME_APP_ADJ) { 16332 // This process is hosting what we currently consider to be the 16333 // home app, so we don't want to let it go into the background. 16334 adj = ProcessList.HOME_APP_ADJ; 16335 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16336 app.cached = false; 16337 app.adjType = "home"; 16338 } 16339 if (procState > ActivityManager.PROCESS_STATE_HOME) { 16340 procState = ActivityManager.PROCESS_STATE_HOME; 16341 } 16342 } 16343 16344 if (app == mPreviousProcess && app.activities.size() > 0) { 16345 if (adj > ProcessList.PREVIOUS_APP_ADJ) { 16346 // This was the previous process that showed UI to the user. 16347 // We want to try to keep it around more aggressively, to give 16348 // a good experience around switching between two apps. 16349 adj = ProcessList.PREVIOUS_APP_ADJ; 16350 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16351 app.cached = false; 16352 app.adjType = "previous"; 16353 } 16354 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 16355 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 16356 } 16357 } 16358 16359 if (false) Slog.i(TAG, "OOM " + app + ": initial adj=" + adj 16360 + " reason=" + app.adjType); 16361 16362 // By default, we use the computed adjustment. It may be changed if 16363 // there are applications dependent on our services or providers, but 16364 // this gives us a baseline and makes sure we don't get into an 16365 // infinite recursion. 16366 app.adjSeq = mAdjSeq; 16367 app.curRawAdj = adj; 16368 app.hasStartedServices = false; 16369 16370 if (mBackupTarget != null && app == mBackupTarget.app) { 16371 // If possible we want to avoid killing apps while they're being backed up 16372 if (adj > ProcessList.BACKUP_APP_ADJ) { 16373 if (DEBUG_BACKUP) Slog.v(TAG, "oom BACKUP_APP_ADJ for " + app); 16374 adj = ProcessList.BACKUP_APP_ADJ; 16375 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 16376 procState = ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 16377 } 16378 app.adjType = "backup"; 16379 app.cached = false; 16380 } 16381 if (procState > ActivityManager.PROCESS_STATE_BACKUP) { 16382 procState = ActivityManager.PROCESS_STATE_BACKUP; 16383 } 16384 } 16385 16386 boolean mayBeTop = false; 16387 16388 for (int is = app.services.size()-1; 16389 is >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 16390 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16391 || procState > ActivityManager.PROCESS_STATE_TOP); 16392 is--) { 16393 ServiceRecord s = app.services.valueAt(is); 16394 if (s.startRequested) { 16395 app.hasStartedServices = true; 16396 if (procState > ActivityManager.PROCESS_STATE_SERVICE) { 16397 procState = ActivityManager.PROCESS_STATE_SERVICE; 16398 } 16399 if (app.hasShownUi && app != mHomeProcess) { 16400 // If this process has shown some UI, let it immediately 16401 // go to the LRU list because it may be pretty heavy with 16402 // UI stuff. We'll tag it with a label just to help 16403 // debug and understand what is going on. 16404 if (adj > ProcessList.SERVICE_ADJ) { 16405 app.adjType = "cch-started-ui-services"; 16406 } 16407 } else { 16408 if (now < (s.lastActivity + ActiveServices.MAX_SERVICE_INACTIVITY)) { 16409 // This service has seen some activity within 16410 // recent memory, so we will keep its process ahead 16411 // of the background processes. 16412 if (adj > ProcessList.SERVICE_ADJ) { 16413 adj = ProcessList.SERVICE_ADJ; 16414 app.adjType = "started-services"; 16415 app.cached = false; 16416 } 16417 } 16418 // If we have let the service slide into the background 16419 // state, still have some text describing what it is doing 16420 // even though the service no longer has an impact. 16421 if (adj > ProcessList.SERVICE_ADJ) { 16422 app.adjType = "cch-started-services"; 16423 } 16424 } 16425 } 16426 for (int conni = s.connections.size()-1; 16427 conni >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 16428 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16429 || procState > ActivityManager.PROCESS_STATE_TOP); 16430 conni--) { 16431 ArrayList<ConnectionRecord> clist = s.connections.valueAt(conni); 16432 for (int i = 0; 16433 i < clist.size() && (adj > ProcessList.FOREGROUND_APP_ADJ 16434 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16435 || procState > ActivityManager.PROCESS_STATE_TOP); 16436 i++) { 16437 // XXX should compute this based on the max of 16438 // all connected clients. 16439 ConnectionRecord cr = clist.get(i); 16440 if (cr.binding.client == app) { 16441 // Binding to ourself is not interesting. 16442 continue; 16443 } 16444 if ((cr.flags&Context.BIND_WAIVE_PRIORITY) == 0) { 16445 ProcessRecord client = cr.binding.client; 16446 int clientAdj = computeOomAdjLocked(client, cachedAdj, 16447 TOP_APP, doingAll, now); 16448 int clientProcState = client.curProcState; 16449 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 16450 // If the other app is cached for any reason, for purposes here 16451 // we are going to consider it empty. The specific cached state 16452 // doesn't propagate except under certain conditions. 16453 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16454 } 16455 String adjType = null; 16456 if ((cr.flags&Context.BIND_ALLOW_OOM_MANAGEMENT) != 0) { 16457 // Not doing bind OOM management, so treat 16458 // this guy more like a started service. 16459 if (app.hasShownUi && app != mHomeProcess) { 16460 // If this process has shown some UI, let it immediately 16461 // go to the LRU list because it may be pretty heavy with 16462 // UI stuff. We'll tag it with a label just to help 16463 // debug and understand what is going on. 16464 if (adj > clientAdj) { 16465 adjType = "cch-bound-ui-services"; 16466 } 16467 app.cached = false; 16468 clientAdj = adj; 16469 clientProcState = procState; 16470 } else { 16471 if (now >= (s.lastActivity 16472 + ActiveServices.MAX_SERVICE_INACTIVITY)) { 16473 // This service has not seen activity within 16474 // recent memory, so allow it to drop to the 16475 // LRU list if there is no other reason to keep 16476 // it around. We'll also tag it with a label just 16477 // to help debug and undertand what is going on. 16478 if (adj > clientAdj) { 16479 adjType = "cch-bound-services"; 16480 } 16481 clientAdj = adj; 16482 } 16483 } 16484 } 16485 if (adj > clientAdj) { 16486 // If this process has recently shown UI, and 16487 // the process that is binding to it is less 16488 // important than being visible, then we don't 16489 // care about the binding as much as we care 16490 // about letting this process get into the LRU 16491 // list to be killed and restarted if needed for 16492 // memory. 16493 if (app.hasShownUi && app != mHomeProcess 16494 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16495 adjType = "cch-bound-ui-services"; 16496 } else { 16497 if ((cr.flags&(Context.BIND_ABOVE_CLIENT 16498 |Context.BIND_IMPORTANT)) != 0) { 16499 adj = clientAdj; 16500 } else if ((cr.flags&Context.BIND_NOT_VISIBLE) != 0 16501 && clientAdj < ProcessList.PERCEPTIBLE_APP_ADJ 16502 && adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16503 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16504 } else if (clientAdj > ProcessList.VISIBLE_APP_ADJ) { 16505 adj = clientAdj; 16506 } else { 16507 if (adj > ProcessList.VISIBLE_APP_ADJ) { 16508 adj = ProcessList.VISIBLE_APP_ADJ; 16509 } 16510 } 16511 if (!client.cached) { 16512 app.cached = false; 16513 } 16514 adjType = "service"; 16515 } 16516 } 16517 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 16518 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 16519 schedGroup = Process.THREAD_GROUP_DEFAULT; 16520 } 16521 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 16522 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 16523 // Special handling of clients who are in the top state. 16524 // We *may* want to consider this process to be in the 16525 // top state as well, but only if there is not another 16526 // reason for it to be running. Being on the top is a 16527 // special state, meaning you are specifically running 16528 // for the current top app. If the process is already 16529 // running in the background for some other reason, it 16530 // is more important to continue considering it to be 16531 // in the background state. 16532 mayBeTop = true; 16533 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16534 } else { 16535 // Special handling for above-top states (persistent 16536 // processes). These should not bring the current process 16537 // into the top state, since they are not on top. Instead 16538 // give them the best state after that. 16539 clientProcState = 16540 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16541 } 16542 } 16543 } else { 16544 if (clientProcState < 16545 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 16546 clientProcState = 16547 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 16548 } 16549 } 16550 if (procState > clientProcState) { 16551 procState = clientProcState; 16552 } 16553 if (procState < ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 16554 && (cr.flags&Context.BIND_SHOWING_UI) != 0) { 16555 app.pendingUiClean = true; 16556 } 16557 if (adjType != null) { 16558 app.adjType = adjType; 16559 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 16560 .REASON_SERVICE_IN_USE; 16561 app.adjSource = cr.binding.client; 16562 app.adjSourceProcState = clientProcState; 16563 app.adjTarget = s.name; 16564 } 16565 } 16566 if ((cr.flags&Context.BIND_TREAT_LIKE_ACTIVITY) != 0) { 16567 app.treatLikeActivity = true; 16568 } 16569 final ActivityRecord a = cr.activity; 16570 if ((cr.flags&Context.BIND_ADJUST_WITH_ACTIVITY) != 0) { 16571 if (a != null && adj > ProcessList.FOREGROUND_APP_ADJ && 16572 (a.visible || a.state == ActivityState.RESUMED 16573 || a.state == ActivityState.PAUSING)) { 16574 adj = ProcessList.FOREGROUND_APP_ADJ; 16575 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 16576 schedGroup = Process.THREAD_GROUP_DEFAULT; 16577 } 16578 app.cached = false; 16579 app.adjType = "service"; 16580 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 16581 .REASON_SERVICE_IN_USE; 16582 app.adjSource = a; 16583 app.adjSourceProcState = procState; 16584 app.adjTarget = s.name; 16585 } 16586 } 16587 } 16588 } 16589 } 16590 16591 for (int provi = app.pubProviders.size()-1; 16592 provi >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 16593 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16594 || procState > ActivityManager.PROCESS_STATE_TOP); 16595 provi--) { 16596 ContentProviderRecord cpr = app.pubProviders.valueAt(provi); 16597 for (int i = cpr.connections.size()-1; 16598 i >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 16599 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16600 || procState > ActivityManager.PROCESS_STATE_TOP); 16601 i--) { 16602 ContentProviderConnection conn = cpr.connections.get(i); 16603 ProcessRecord client = conn.client; 16604 if (client == app) { 16605 // Being our own client is not interesting. 16606 continue; 16607 } 16608 int clientAdj = computeOomAdjLocked(client, cachedAdj, TOP_APP, doingAll, now); 16609 int clientProcState = client.curProcState; 16610 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 16611 // If the other app is cached for any reason, for purposes here 16612 // we are going to consider it empty. 16613 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16614 } 16615 if (adj > clientAdj) { 16616 if (app.hasShownUi && app != mHomeProcess 16617 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16618 app.adjType = "cch-ui-provider"; 16619 } else { 16620 adj = clientAdj > ProcessList.FOREGROUND_APP_ADJ 16621 ? clientAdj : ProcessList.FOREGROUND_APP_ADJ; 16622 app.adjType = "provider"; 16623 } 16624 app.cached &= client.cached; 16625 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 16626 .REASON_PROVIDER_IN_USE; 16627 app.adjSource = client; 16628 app.adjSourceProcState = clientProcState; 16629 app.adjTarget = cpr.name; 16630 } 16631 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 16632 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 16633 // Special handling of clients who are in the top state. 16634 // We *may* want to consider this process to be in the 16635 // top state as well, but only if there is not another 16636 // reason for it to be running. Being on the top is a 16637 // special state, meaning you are specifically running 16638 // for the current top app. If the process is already 16639 // running in the background for some other reason, it 16640 // is more important to continue considering it to be 16641 // in the background state. 16642 mayBeTop = true; 16643 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16644 } else { 16645 // Special handling for above-top states (persistent 16646 // processes). These should not bring the current process 16647 // into the top state, since they are not on top. Instead 16648 // give them the best state after that. 16649 clientProcState = 16650 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16651 } 16652 } 16653 if (procState > clientProcState) { 16654 procState = clientProcState; 16655 } 16656 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 16657 schedGroup = Process.THREAD_GROUP_DEFAULT; 16658 } 16659 } 16660 // If the provider has external (non-framework) process 16661 // dependencies, ensure that its adjustment is at least 16662 // FOREGROUND_APP_ADJ. 16663 if (cpr.hasExternalProcessHandles()) { 16664 if (adj > ProcessList.FOREGROUND_APP_ADJ) { 16665 adj = ProcessList.FOREGROUND_APP_ADJ; 16666 schedGroup = Process.THREAD_GROUP_DEFAULT; 16667 app.cached = false; 16668 app.adjType = "provider"; 16669 app.adjTarget = cpr.name; 16670 } 16671 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) { 16672 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16673 } 16674 } 16675 } 16676 16677 if (mayBeTop && procState > ActivityManager.PROCESS_STATE_TOP) { 16678 // A client of one of our services or providers is in the top state. We 16679 // *may* want to be in the top state, but not if we are already running in 16680 // the background for some other reason. For the decision here, we are going 16681 // to pick out a few specific states that we want to remain in when a client 16682 // is top (states that tend to be longer-term) and otherwise allow it to go 16683 // to the top state. 16684 switch (procState) { 16685 case ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND: 16686 case ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND: 16687 case ActivityManager.PROCESS_STATE_SERVICE: 16688 // These all are longer-term states, so pull them up to the top 16689 // of the background states, but not all the way to the top state. 16690 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16691 break; 16692 default: 16693 // Otherwise, top is a better choice, so take it. 16694 procState = ActivityManager.PROCESS_STATE_TOP; 16695 break; 16696 } 16697 } 16698 16699 if (procState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 16700 if (app.hasClientActivities) { 16701 // This is a cached process, but with client activities. Mark it so. 16702 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT; 16703 app.adjType = "cch-client-act"; 16704 } else if (app.treatLikeActivity) { 16705 // This is a cached process, but somebody wants us to treat it like it has 16706 // an activity, okay! 16707 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 16708 app.adjType = "cch-as-act"; 16709 } 16710 } 16711 16712 if (adj == ProcessList.SERVICE_ADJ) { 16713 if (doingAll) { 16714 app.serviceb = mNewNumAServiceProcs > (mNumServiceProcs/3); 16715 mNewNumServiceProcs++; 16716 //Slog.i(TAG, "ADJ " + app + " serviceb=" + app.serviceb); 16717 if (!app.serviceb) { 16718 // This service isn't far enough down on the LRU list to 16719 // normally be a B service, but if we are low on RAM and it 16720 // is large we want to force it down since we would prefer to 16721 // keep launcher over it. 16722 if (mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 16723 && app.lastPss >= mProcessList.getCachedRestoreThresholdKb()) { 16724 app.serviceHighRam = true; 16725 app.serviceb = true; 16726 //Slog.i(TAG, "ADJ " + app + " high ram!"); 16727 } else { 16728 mNewNumAServiceProcs++; 16729 //Slog.i(TAG, "ADJ " + app + " not high ram!"); 16730 } 16731 } else { 16732 app.serviceHighRam = false; 16733 } 16734 } 16735 if (app.serviceb) { 16736 adj = ProcessList.SERVICE_B_ADJ; 16737 } 16738 } 16739 16740 app.curRawAdj = adj; 16741 16742 //Slog.i(TAG, "OOM ADJ " + app + ": pid=" + app.pid + 16743 // " adj=" + adj + " curAdj=" + app.curAdj + " maxAdj=" + app.maxAdj); 16744 if (adj > app.maxAdj) { 16745 adj = app.maxAdj; 16746 if (app.maxAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 16747 schedGroup = Process.THREAD_GROUP_DEFAULT; 16748 } 16749 } 16750 16751 // Do final modification to adj. Everything we do between here and applying 16752 // the final setAdj must be done in this function, because we will also use 16753 // it when computing the final cached adj later. Note that we don't need to 16754 // worry about this for max adj above, since max adj will always be used to 16755 // keep it out of the cached vaues. 16756 app.curAdj = app.modifyRawOomAdj(adj); 16757 app.curSchedGroup = schedGroup; 16758 app.curProcState = procState; 16759 app.foregroundActivities = foregroundActivities; 16760 16761 return app.curRawAdj; 16762 } 16763 16764 /** 16765 * Schedule PSS collection of a process. 16766 */ 16767 void requestPssLocked(ProcessRecord proc, int procState) { 16768 if (mPendingPssProcesses.contains(proc)) { 16769 return; 16770 } 16771 if (mPendingPssProcesses.size() == 0) { 16772 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 16773 } 16774 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of: " + proc); 16775 proc.pssProcState = procState; 16776 mPendingPssProcesses.add(proc); 16777 } 16778 16779 /** 16780 * Schedule PSS collection of all processes. 16781 */ 16782 void requestPssAllProcsLocked(long now, boolean always, boolean memLowered) { 16783 if (!always) { 16784 if (now < (mLastFullPssTime + 16785 (memLowered ? FULL_PSS_LOWERED_INTERVAL : FULL_PSS_MIN_INTERVAL))) { 16786 return; 16787 } 16788 } 16789 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of all procs! memLowered=" + memLowered); 16790 mLastFullPssTime = now; 16791 mFullPssPending = true; 16792 mPendingPssProcesses.ensureCapacity(mLruProcesses.size()); 16793 mPendingPssProcesses.clear(); 16794 for (int i=mLruProcesses.size()-1; i>=0; i--) { 16795 ProcessRecord app = mLruProcesses.get(i); 16796 if (memLowered || now > (app.lastStateTime+ProcessList.PSS_ALL_INTERVAL)) { 16797 app.pssProcState = app.setProcState; 16798 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 16799 isSleeping(), now); 16800 mPendingPssProcesses.add(app); 16801 } 16802 } 16803 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 16804 } 16805 16806 /** 16807 * Ask a given process to GC right now. 16808 */ 16809 final void performAppGcLocked(ProcessRecord app) { 16810 try { 16811 app.lastRequestedGc = SystemClock.uptimeMillis(); 16812 if (app.thread != null) { 16813 if (app.reportLowMemory) { 16814 app.reportLowMemory = false; 16815 app.thread.scheduleLowMemory(); 16816 } else { 16817 app.thread.processInBackground(); 16818 } 16819 } 16820 } catch (Exception e) { 16821 // whatever. 16822 } 16823 } 16824 16825 /** 16826 * Returns true if things are idle enough to perform GCs. 16827 */ 16828 private final boolean canGcNowLocked() { 16829 boolean processingBroadcasts = false; 16830 for (BroadcastQueue q : mBroadcastQueues) { 16831 if (q.mParallelBroadcasts.size() != 0 || q.mOrderedBroadcasts.size() != 0) { 16832 processingBroadcasts = true; 16833 } 16834 } 16835 return !processingBroadcasts 16836 && (isSleeping() || mStackSupervisor.allResumedActivitiesIdle()); 16837 } 16838 16839 /** 16840 * Perform GCs on all processes that are waiting for it, but only 16841 * if things are idle. 16842 */ 16843 final void performAppGcsLocked() { 16844 final int N = mProcessesToGc.size(); 16845 if (N <= 0) { 16846 return; 16847 } 16848 if (canGcNowLocked()) { 16849 while (mProcessesToGc.size() > 0) { 16850 ProcessRecord proc = mProcessesToGc.remove(0); 16851 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ || proc.reportLowMemory) { 16852 if ((proc.lastRequestedGc+GC_MIN_INTERVAL) 16853 <= SystemClock.uptimeMillis()) { 16854 // To avoid spamming the system, we will GC processes one 16855 // at a time, waiting a few seconds between each. 16856 performAppGcLocked(proc); 16857 scheduleAppGcsLocked(); 16858 return; 16859 } else { 16860 // It hasn't been long enough since we last GCed this 16861 // process... put it in the list to wait for its time. 16862 addProcessToGcListLocked(proc); 16863 break; 16864 } 16865 } 16866 } 16867 16868 scheduleAppGcsLocked(); 16869 } 16870 } 16871 16872 /** 16873 * If all looks good, perform GCs on all processes waiting for them. 16874 */ 16875 final void performAppGcsIfAppropriateLocked() { 16876 if (canGcNowLocked()) { 16877 performAppGcsLocked(); 16878 return; 16879 } 16880 // Still not idle, wait some more. 16881 scheduleAppGcsLocked(); 16882 } 16883 16884 /** 16885 * Schedule the execution of all pending app GCs. 16886 */ 16887 final void scheduleAppGcsLocked() { 16888 mHandler.removeMessages(GC_BACKGROUND_PROCESSES_MSG); 16889 16890 if (mProcessesToGc.size() > 0) { 16891 // Schedule a GC for the time to the next process. 16892 ProcessRecord proc = mProcessesToGc.get(0); 16893 Message msg = mHandler.obtainMessage(GC_BACKGROUND_PROCESSES_MSG); 16894 16895 long when = proc.lastRequestedGc + GC_MIN_INTERVAL; 16896 long now = SystemClock.uptimeMillis(); 16897 if (when < (now+GC_TIMEOUT)) { 16898 when = now + GC_TIMEOUT; 16899 } 16900 mHandler.sendMessageAtTime(msg, when); 16901 } 16902 } 16903 16904 /** 16905 * Add a process to the array of processes waiting to be GCed. Keeps the 16906 * list in sorted order by the last GC time. The process can't already be 16907 * on the list. 16908 */ 16909 final void addProcessToGcListLocked(ProcessRecord proc) { 16910 boolean added = false; 16911 for (int i=mProcessesToGc.size()-1; i>=0; i--) { 16912 if (mProcessesToGc.get(i).lastRequestedGc < 16913 proc.lastRequestedGc) { 16914 added = true; 16915 mProcessesToGc.add(i+1, proc); 16916 break; 16917 } 16918 } 16919 if (!added) { 16920 mProcessesToGc.add(0, proc); 16921 } 16922 } 16923 16924 /** 16925 * Set up to ask a process to GC itself. This will either do it 16926 * immediately, or put it on the list of processes to gc the next 16927 * time things are idle. 16928 */ 16929 final void scheduleAppGcLocked(ProcessRecord app) { 16930 long now = SystemClock.uptimeMillis(); 16931 if ((app.lastRequestedGc+GC_MIN_INTERVAL) > now) { 16932 return; 16933 } 16934 if (!mProcessesToGc.contains(app)) { 16935 addProcessToGcListLocked(app); 16936 scheduleAppGcsLocked(); 16937 } 16938 } 16939 16940 final void checkExcessivePowerUsageLocked(boolean doKills) { 16941 updateCpuStatsNow(); 16942 16943 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 16944 boolean doWakeKills = doKills; 16945 boolean doCpuKills = doKills; 16946 if (mLastPowerCheckRealtime == 0) { 16947 doWakeKills = false; 16948 } 16949 if (mLastPowerCheckUptime == 0) { 16950 doCpuKills = false; 16951 } 16952 if (stats.isScreenOn()) { 16953 doWakeKills = false; 16954 } 16955 final long curRealtime = SystemClock.elapsedRealtime(); 16956 final long realtimeSince = curRealtime - mLastPowerCheckRealtime; 16957 final long curUptime = SystemClock.uptimeMillis(); 16958 final long uptimeSince = curUptime - mLastPowerCheckUptime; 16959 mLastPowerCheckRealtime = curRealtime; 16960 mLastPowerCheckUptime = curUptime; 16961 if (realtimeSince < WAKE_LOCK_MIN_CHECK_DURATION) { 16962 doWakeKills = false; 16963 } 16964 if (uptimeSince < CPU_MIN_CHECK_DURATION) { 16965 doCpuKills = false; 16966 } 16967 int i = mLruProcesses.size(); 16968 while (i > 0) { 16969 i--; 16970 ProcessRecord app = mLruProcesses.get(i); 16971 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 16972 long wtime; 16973 synchronized (stats) { 16974 wtime = stats.getProcessWakeTime(app.info.uid, 16975 app.pid, curRealtime); 16976 } 16977 long wtimeUsed = wtime - app.lastWakeTime; 16978 long cputimeUsed = app.curCpuTime - app.lastCpuTime; 16979 if (DEBUG_POWER) { 16980 StringBuilder sb = new StringBuilder(128); 16981 sb.append("Wake for "); 16982 app.toShortString(sb); 16983 sb.append(": over "); 16984 TimeUtils.formatDuration(realtimeSince, sb); 16985 sb.append(" used "); 16986 TimeUtils.formatDuration(wtimeUsed, sb); 16987 sb.append(" ("); 16988 sb.append((wtimeUsed*100)/realtimeSince); 16989 sb.append("%)"); 16990 Slog.i(TAG, sb.toString()); 16991 sb.setLength(0); 16992 sb.append("CPU for "); 16993 app.toShortString(sb); 16994 sb.append(": over "); 16995 TimeUtils.formatDuration(uptimeSince, sb); 16996 sb.append(" used "); 16997 TimeUtils.formatDuration(cputimeUsed, sb); 16998 sb.append(" ("); 16999 sb.append((cputimeUsed*100)/uptimeSince); 17000 sb.append("%)"); 17001 Slog.i(TAG, sb.toString()); 17002 } 17003 // If a process has held a wake lock for more 17004 // than 50% of the time during this period, 17005 // that sounds bad. Kill! 17006 if (doWakeKills && realtimeSince > 0 17007 && ((wtimeUsed*100)/realtimeSince) >= 50) { 17008 synchronized (stats) { 17009 stats.reportExcessiveWakeLocked(app.info.uid, app.processName, 17010 realtimeSince, wtimeUsed); 17011 } 17012 app.kill("excessive wake held " + wtimeUsed + " during " + realtimeSince, true); 17013 app.baseProcessTracker.reportExcessiveWake(app.pkgList); 17014 } else if (doCpuKills && uptimeSince > 0 17015 && ((cputimeUsed*100)/uptimeSince) >= 25) { 17016 synchronized (stats) { 17017 stats.reportExcessiveCpuLocked(app.info.uid, app.processName, 17018 uptimeSince, cputimeUsed); 17019 } 17020 app.kill("excessive cpu " + cputimeUsed + " during " + uptimeSince, true); 17021 app.baseProcessTracker.reportExcessiveCpu(app.pkgList); 17022 } else { 17023 app.lastWakeTime = wtime; 17024 app.lastCpuTime = app.curCpuTime; 17025 } 17026 } 17027 } 17028 } 17029 17030 private final boolean applyOomAdjLocked(ProcessRecord app, 17031 ProcessRecord TOP_APP, boolean doingAll, long now) { 17032 boolean success = true; 17033 17034 if (app.curRawAdj != app.setRawAdj) { 17035 app.setRawAdj = app.curRawAdj; 17036 } 17037 17038 int changes = 0; 17039 17040 if (app.curAdj != app.setAdj) { 17041 ProcessList.setOomAdj(app.pid, app.info.uid, app.curAdj); 17042 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v( 17043 TAG, "Set " + app.pid + " " + app.processName + 17044 " adj " + app.curAdj + ": " + app.adjType); 17045 app.setAdj = app.curAdj; 17046 } 17047 17048 if (app.setSchedGroup != app.curSchedGroup) { 17049 app.setSchedGroup = app.curSchedGroup; 17050 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17051 "Setting process group of " + app.processName 17052 + " to " + app.curSchedGroup); 17053 if (app.waitingToKill != null && 17054 app.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 17055 app.kill(app.waitingToKill, true); 17056 success = false; 17057 } else { 17058 if (true) { 17059 long oldId = Binder.clearCallingIdentity(); 17060 try { 17061 Process.setProcessGroup(app.pid, app.curSchedGroup); 17062 } catch (Exception e) { 17063 Slog.w(TAG, "Failed setting process group of " + app.pid 17064 + " to " + app.curSchedGroup); 17065 e.printStackTrace(); 17066 } finally { 17067 Binder.restoreCallingIdentity(oldId); 17068 } 17069 } else { 17070 if (app.thread != null) { 17071 try { 17072 app.thread.setSchedulingGroup(app.curSchedGroup); 17073 } catch (RemoteException e) { 17074 } 17075 } 17076 } 17077 Process.setSwappiness(app.pid, 17078 app.curSchedGroup <= Process.THREAD_GROUP_BG_NONINTERACTIVE); 17079 } 17080 } 17081 if (app.repForegroundActivities != app.foregroundActivities) { 17082 app.repForegroundActivities = app.foregroundActivities; 17083 changes |= ProcessChangeItem.CHANGE_ACTIVITIES; 17084 } 17085 if (app.repProcState != app.curProcState) { 17086 app.repProcState = app.curProcState; 17087 changes |= ProcessChangeItem.CHANGE_PROCESS_STATE; 17088 if (app.thread != null) { 17089 try { 17090 if (false) { 17091 //RuntimeException h = new RuntimeException("here"); 17092 Slog.i(TAG, "Sending new process state " + app.repProcState 17093 + " to " + app /*, h*/); 17094 } 17095 app.thread.setProcessState(app.repProcState); 17096 } catch (RemoteException e) { 17097 } 17098 } 17099 } 17100 if (app.setProcState < 0 || ProcessList.procStatesDifferForMem(app.curProcState, 17101 app.setProcState)) { 17102 app.lastStateTime = now; 17103 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 17104 isSleeping(), now); 17105 if (DEBUG_PSS) Slog.d(TAG, "Process state change from " 17106 + ProcessList.makeProcStateString(app.setProcState) + " to " 17107 + ProcessList.makeProcStateString(app.curProcState) + " next pss in " 17108 + (app.nextPssTime-now) + ": " + app); 17109 } else { 17110 if (now > app.nextPssTime || (now > (app.lastPssTime+ProcessList.PSS_MAX_INTERVAL) 17111 && now > (app.lastStateTime+ProcessList.PSS_MIN_TIME_FROM_STATE_CHANGE))) { 17112 requestPssLocked(app, app.setProcState); 17113 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, false, 17114 isSleeping(), now); 17115 } else if (false && DEBUG_PSS) { 17116 Slog.d(TAG, "Not requesting PSS of " + app + ": next=" + (app.nextPssTime-now)); 17117 } 17118 } 17119 if (app.setProcState != app.curProcState) { 17120 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17121 "Proc state change of " + app.processName 17122 + " to " + app.curProcState); 17123 boolean setImportant = app.setProcState < ActivityManager.PROCESS_STATE_SERVICE; 17124 boolean curImportant = app.curProcState < ActivityManager.PROCESS_STATE_SERVICE; 17125 if (setImportant && !curImportant) { 17126 // This app is no longer something we consider important enough to allow to 17127 // use arbitrary amounts of battery power. Note 17128 // its current wake lock time to later know to kill it if 17129 // it is not behaving well. 17130 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 17131 synchronized (stats) { 17132 app.lastWakeTime = stats.getProcessWakeTime(app.info.uid, 17133 app.pid, SystemClock.elapsedRealtime()); 17134 } 17135 app.lastCpuTime = app.curCpuTime; 17136 17137 } 17138 app.setProcState = app.curProcState; 17139 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 17140 app.notCachedSinceIdle = false; 17141 } 17142 if (!doingAll) { 17143 setProcessTrackerStateLocked(app, mProcessStats.getMemFactorLocked(), now); 17144 } else { 17145 app.procStateChanged = true; 17146 } 17147 } 17148 17149 if (changes != 0) { 17150 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Changes in " + app + ": " + changes); 17151 int i = mPendingProcessChanges.size()-1; 17152 ProcessChangeItem item = null; 17153 while (i >= 0) { 17154 item = mPendingProcessChanges.get(i); 17155 if (item.pid == app.pid) { 17156 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Re-using existing item: " + item); 17157 break; 17158 } 17159 i--; 17160 } 17161 if (i < 0) { 17162 // No existing item in pending changes; need a new one. 17163 final int NA = mAvailProcessChanges.size(); 17164 if (NA > 0) { 17165 item = mAvailProcessChanges.remove(NA-1); 17166 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Retreiving available item: " + item); 17167 } else { 17168 item = new ProcessChangeItem(); 17169 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Allocating new item: " + item); 17170 } 17171 item.changes = 0; 17172 item.pid = app.pid; 17173 item.uid = app.info.uid; 17174 if (mPendingProcessChanges.size() == 0) { 17175 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, 17176 "*** Enqueueing dispatch processes changed!"); 17177 mHandler.obtainMessage(DISPATCH_PROCESSES_CHANGED).sendToTarget(); 17178 } 17179 mPendingProcessChanges.add(item); 17180 } 17181 item.changes |= changes; 17182 item.processState = app.repProcState; 17183 item.foregroundActivities = app.repForegroundActivities; 17184 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Item " 17185 + Integer.toHexString(System.identityHashCode(item)) 17186 + " " + app.toShortString() + ": changes=" + item.changes 17187 + " procState=" + item.processState 17188 + " foreground=" + item.foregroundActivities 17189 + " type=" + app.adjType + " source=" + app.adjSource 17190 + " target=" + app.adjTarget); 17191 } 17192 17193 return success; 17194 } 17195 17196 private final void setProcessTrackerStateLocked(ProcessRecord proc, int memFactor, long now) { 17197 if (proc.thread != null) { 17198 if (proc.baseProcessTracker != null) { 17199 proc.baseProcessTracker.setState(proc.repProcState, memFactor, now, proc.pkgList); 17200 } 17201 if (proc.repProcState >= 0) { 17202 mBatteryStatsService.noteProcessState(proc.processName, proc.info.uid, 17203 proc.repProcState); 17204 } 17205 } 17206 } 17207 17208 private final boolean updateOomAdjLocked(ProcessRecord app, int cachedAdj, 17209 ProcessRecord TOP_APP, boolean doingAll, long now) { 17210 if (app.thread == null) { 17211 return false; 17212 } 17213 17214 computeOomAdjLocked(app, cachedAdj, TOP_APP, doingAll, now); 17215 17216 return applyOomAdjLocked(app, TOP_APP, doingAll, now); 17217 } 17218 17219 final void updateProcessForegroundLocked(ProcessRecord proc, boolean isForeground, 17220 boolean oomAdj) { 17221 if (isForeground != proc.foregroundServices) { 17222 proc.foregroundServices = isForeground; 17223 ArrayList<ProcessRecord> curProcs = mForegroundPackages.get(proc.info.packageName, 17224 proc.info.uid); 17225 if (isForeground) { 17226 if (curProcs == null) { 17227 curProcs = new ArrayList<ProcessRecord>(); 17228 mForegroundPackages.put(proc.info.packageName, proc.info.uid, curProcs); 17229 } 17230 if (!curProcs.contains(proc)) { 17231 curProcs.add(proc); 17232 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_FOREGROUND_START, 17233 proc.info.packageName, proc.info.uid); 17234 } 17235 } else { 17236 if (curProcs != null) { 17237 if (curProcs.remove(proc)) { 17238 mBatteryStatsService.noteEvent( 17239 BatteryStats.HistoryItem.EVENT_FOREGROUND_FINISH, 17240 proc.info.packageName, proc.info.uid); 17241 if (curProcs.size() <= 0) { 17242 mForegroundPackages.remove(proc.info.packageName, proc.info.uid); 17243 } 17244 } 17245 } 17246 } 17247 if (oomAdj) { 17248 updateOomAdjLocked(); 17249 } 17250 } 17251 } 17252 17253 private final ActivityRecord resumedAppLocked() { 17254 ActivityRecord act = mStackSupervisor.resumedAppLocked(); 17255 String pkg; 17256 int uid; 17257 if (act != null) { 17258 pkg = act.packageName; 17259 uid = act.info.applicationInfo.uid; 17260 } else { 17261 pkg = null; 17262 uid = -1; 17263 } 17264 // Has the UID or resumed package name changed? 17265 if (uid != mCurResumedUid || (pkg != mCurResumedPackage 17266 && (pkg == null || !pkg.equals(mCurResumedPackage)))) { 17267 if (mCurResumedPackage != null) { 17268 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_FINISH, 17269 mCurResumedPackage, mCurResumedUid); 17270 } 17271 mCurResumedPackage = pkg; 17272 mCurResumedUid = uid; 17273 if (mCurResumedPackage != null) { 17274 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_START, 17275 mCurResumedPackage, mCurResumedUid); 17276 } 17277 } 17278 return act; 17279 } 17280 17281 final boolean updateOomAdjLocked(ProcessRecord app) { 17282 final ActivityRecord TOP_ACT = resumedAppLocked(); 17283 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 17284 final boolean wasCached = app.cached; 17285 17286 mAdjSeq++; 17287 17288 // This is the desired cached adjusment we want to tell it to use. 17289 // If our app is currently cached, we know it, and that is it. Otherwise, 17290 // we don't know it yet, and it needs to now be cached we will then 17291 // need to do a complete oom adj. 17292 final int cachedAdj = app.curRawAdj >= ProcessList.CACHED_APP_MIN_ADJ 17293 ? app.curRawAdj : ProcessList.UNKNOWN_ADJ; 17294 boolean success = updateOomAdjLocked(app, cachedAdj, TOP_APP, false, 17295 SystemClock.uptimeMillis()); 17296 if (wasCached != app.cached || app.curRawAdj == ProcessList.UNKNOWN_ADJ) { 17297 // Changed to/from cached state, so apps after it in the LRU 17298 // list may also be changed. 17299 updateOomAdjLocked(); 17300 } 17301 return success; 17302 } 17303 17304 final void updateOomAdjLocked() { 17305 final ActivityRecord TOP_ACT = resumedAppLocked(); 17306 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 17307 final long now = SystemClock.uptimeMillis(); 17308 final long oldTime = now - ProcessList.MAX_EMPTY_TIME; 17309 final int N = mLruProcesses.size(); 17310 17311 if (false) { 17312 RuntimeException e = new RuntimeException(); 17313 e.fillInStackTrace(); 17314 Slog.i(TAG, "updateOomAdj: top=" + TOP_ACT, e); 17315 } 17316 17317 mAdjSeq++; 17318 mNewNumServiceProcs = 0; 17319 mNewNumAServiceProcs = 0; 17320 17321 final int emptyProcessLimit; 17322 final int cachedProcessLimit; 17323 if (mProcessLimit <= 0) { 17324 emptyProcessLimit = cachedProcessLimit = 0; 17325 } else if (mProcessLimit == 1) { 17326 emptyProcessLimit = 1; 17327 cachedProcessLimit = 0; 17328 } else { 17329 emptyProcessLimit = ProcessList.computeEmptyProcessLimit(mProcessLimit); 17330 cachedProcessLimit = mProcessLimit - emptyProcessLimit; 17331 } 17332 17333 // Let's determine how many processes we have running vs. 17334 // how many slots we have for background processes; we may want 17335 // to put multiple processes in a slot of there are enough of 17336 // them. 17337 int numSlots = (ProcessList.CACHED_APP_MAX_ADJ 17338 - ProcessList.CACHED_APP_MIN_ADJ + 1) / 2; 17339 int numEmptyProcs = N - mNumNonCachedProcs - mNumCachedHiddenProcs; 17340 if (numEmptyProcs > cachedProcessLimit) { 17341 // If there are more empty processes than our limit on cached 17342 // processes, then use the cached process limit for the factor. 17343 // This ensures that the really old empty processes get pushed 17344 // down to the bottom, so if we are running low on memory we will 17345 // have a better chance at keeping around more cached processes 17346 // instead of a gazillion empty processes. 17347 numEmptyProcs = cachedProcessLimit; 17348 } 17349 int emptyFactor = numEmptyProcs/numSlots; 17350 if (emptyFactor < 1) emptyFactor = 1; 17351 int cachedFactor = (mNumCachedHiddenProcs > 0 ? mNumCachedHiddenProcs : 1)/numSlots; 17352 if (cachedFactor < 1) cachedFactor = 1; 17353 int stepCached = 0; 17354 int stepEmpty = 0; 17355 int numCached = 0; 17356 int numEmpty = 0; 17357 int numTrimming = 0; 17358 17359 mNumNonCachedProcs = 0; 17360 mNumCachedHiddenProcs = 0; 17361 17362 // First update the OOM adjustment for each of the 17363 // application processes based on their current state. 17364 int curCachedAdj = ProcessList.CACHED_APP_MIN_ADJ; 17365 int nextCachedAdj = curCachedAdj+1; 17366 int curEmptyAdj = ProcessList.CACHED_APP_MIN_ADJ; 17367 int nextEmptyAdj = curEmptyAdj+2; 17368 for (int i=N-1; i>=0; i--) { 17369 ProcessRecord app = mLruProcesses.get(i); 17370 if (!app.killedByAm && app.thread != null) { 17371 app.procStateChanged = false; 17372 computeOomAdjLocked(app, ProcessList.UNKNOWN_ADJ, TOP_APP, true, now); 17373 17374 // If we haven't yet assigned the final cached adj 17375 // to the process, do that now. 17376 if (app.curAdj >= ProcessList.UNKNOWN_ADJ) { 17377 switch (app.curProcState) { 17378 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 17379 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 17380 // This process is a cached process holding activities... 17381 // assign it the next cached value for that type, and then 17382 // step that cached level. 17383 app.curRawAdj = curCachedAdj; 17384 app.curAdj = app.modifyRawOomAdj(curCachedAdj); 17385 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning activity LRU #" + i 17386 + " adj: " + app.curAdj + " (curCachedAdj=" + curCachedAdj 17387 + ")"); 17388 if (curCachedAdj != nextCachedAdj) { 17389 stepCached++; 17390 if (stepCached >= cachedFactor) { 17391 stepCached = 0; 17392 curCachedAdj = nextCachedAdj; 17393 nextCachedAdj += 2; 17394 if (nextCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) { 17395 nextCachedAdj = ProcessList.CACHED_APP_MAX_ADJ; 17396 } 17397 } 17398 } 17399 break; 17400 default: 17401 // For everything else, assign next empty cached process 17402 // level and bump that up. Note that this means that 17403 // long-running services that have dropped down to the 17404 // cached level will be treated as empty (since their process 17405 // state is still as a service), which is what we want. 17406 app.curRawAdj = curEmptyAdj; 17407 app.curAdj = app.modifyRawOomAdj(curEmptyAdj); 17408 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning empty LRU #" + i 17409 + " adj: " + app.curAdj + " (curEmptyAdj=" + curEmptyAdj 17410 + ")"); 17411 if (curEmptyAdj != nextEmptyAdj) { 17412 stepEmpty++; 17413 if (stepEmpty >= emptyFactor) { 17414 stepEmpty = 0; 17415 curEmptyAdj = nextEmptyAdj; 17416 nextEmptyAdj += 2; 17417 if (nextEmptyAdj > ProcessList.CACHED_APP_MAX_ADJ) { 17418 nextEmptyAdj = ProcessList.CACHED_APP_MAX_ADJ; 17419 } 17420 } 17421 } 17422 break; 17423 } 17424 } 17425 17426 applyOomAdjLocked(app, TOP_APP, true, now); 17427 17428 // Count the number of process types. 17429 switch (app.curProcState) { 17430 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 17431 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 17432 mNumCachedHiddenProcs++; 17433 numCached++; 17434 if (numCached > cachedProcessLimit) { 17435 app.kill("cached #" + numCached, true); 17436 } 17437 break; 17438 case ActivityManager.PROCESS_STATE_CACHED_EMPTY: 17439 if (numEmpty > ProcessList.TRIM_EMPTY_APPS 17440 && app.lastActivityTime < oldTime) { 17441 app.kill("empty for " 17442 + ((oldTime + ProcessList.MAX_EMPTY_TIME - app.lastActivityTime) 17443 / 1000) + "s", true); 17444 } else { 17445 numEmpty++; 17446 if (numEmpty > emptyProcessLimit) { 17447 app.kill("empty #" + numEmpty, true); 17448 } 17449 } 17450 break; 17451 default: 17452 mNumNonCachedProcs++; 17453 break; 17454 } 17455 17456 if (app.isolated && app.services.size() <= 0) { 17457 // If this is an isolated process, and there are no 17458 // services running in it, then the process is no longer 17459 // needed. We agressively kill these because we can by 17460 // definition not re-use the same process again, and it is 17461 // good to avoid having whatever code was running in them 17462 // left sitting around after no longer needed. 17463 app.kill("isolated not needed", true); 17464 } 17465 17466 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 17467 && !app.killedByAm) { 17468 numTrimming++; 17469 } 17470 } 17471 } 17472 17473 mNumServiceProcs = mNewNumServiceProcs; 17474 17475 // Now determine the memory trimming level of background processes. 17476 // Unfortunately we need to start at the back of the list to do this 17477 // properly. We only do this if the number of background apps we 17478 // are managing to keep around is less than half the maximum we desire; 17479 // if we are keeping a good number around, we'll let them use whatever 17480 // memory they want. 17481 final int numCachedAndEmpty = numCached + numEmpty; 17482 int memFactor; 17483 if (numCached <= ProcessList.TRIM_CACHED_APPS 17484 && numEmpty <= ProcessList.TRIM_EMPTY_APPS) { 17485 if (numCachedAndEmpty <= ProcessList.TRIM_CRITICAL_THRESHOLD) { 17486 memFactor = ProcessStats.ADJ_MEM_FACTOR_CRITICAL; 17487 } else if (numCachedAndEmpty <= ProcessList.TRIM_LOW_THRESHOLD) { 17488 memFactor = ProcessStats.ADJ_MEM_FACTOR_LOW; 17489 } else { 17490 memFactor = ProcessStats.ADJ_MEM_FACTOR_MODERATE; 17491 } 17492 } else { 17493 memFactor = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 17494 } 17495 // We always allow the memory level to go up (better). We only allow it to go 17496 // down if we are in a state where that is allowed, *and* the total number of processes 17497 // has gone down since last time. 17498 if (DEBUG_OOM_ADJ) Slog.d(TAG, "oom: memFactor=" + memFactor + " last=" + mLastMemoryLevel 17499 + " allowLow=" + mAllowLowerMemLevel + " numProcs=" + mLruProcesses.size() 17500 + " last=" + mLastNumProcesses); 17501 if (memFactor > mLastMemoryLevel) { 17502 if (!mAllowLowerMemLevel || mLruProcesses.size() >= mLastNumProcesses) { 17503 memFactor = mLastMemoryLevel; 17504 if (DEBUG_OOM_ADJ) Slog.d(TAG, "Keeping last mem factor!"); 17505 } 17506 } 17507 mLastMemoryLevel = memFactor; 17508 mLastNumProcesses = mLruProcesses.size(); 17509 boolean allChanged = mProcessStats.setMemFactorLocked(memFactor, !isSleeping(), now); 17510 final int trackerMemFactor = mProcessStats.getMemFactorLocked(); 17511 if (memFactor != ProcessStats.ADJ_MEM_FACTOR_NORMAL) { 17512 if (mLowRamStartTime == 0) { 17513 mLowRamStartTime = now; 17514 } 17515 int step = 0; 17516 int fgTrimLevel; 17517 switch (memFactor) { 17518 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 17519 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_CRITICAL; 17520 break; 17521 case ProcessStats.ADJ_MEM_FACTOR_LOW: 17522 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_LOW; 17523 break; 17524 default: 17525 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_MODERATE; 17526 break; 17527 } 17528 int factor = numTrimming/3; 17529 int minFactor = 2; 17530 if (mHomeProcess != null) minFactor++; 17531 if (mPreviousProcess != null) minFactor++; 17532 if (factor < minFactor) factor = minFactor; 17533 int curLevel = ComponentCallbacks2.TRIM_MEMORY_COMPLETE; 17534 for (int i=N-1; i>=0; i--) { 17535 ProcessRecord app = mLruProcesses.get(i); 17536 if (allChanged || app.procStateChanged) { 17537 setProcessTrackerStateLocked(app, trackerMemFactor, now); 17538 app.procStateChanged = false; 17539 } 17540 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 17541 && !app.killedByAm) { 17542 if (app.trimMemoryLevel < curLevel && app.thread != null) { 17543 try { 17544 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17545 "Trimming memory of " + app.processName 17546 + " to " + curLevel); 17547 app.thread.scheduleTrimMemory(curLevel); 17548 } catch (RemoteException e) { 17549 } 17550 if (false) { 17551 // For now we won't do this; our memory trimming seems 17552 // to be good enough at this point that destroying 17553 // activities causes more harm than good. 17554 if (curLevel >= ComponentCallbacks2.TRIM_MEMORY_COMPLETE 17555 && app != mHomeProcess && app != mPreviousProcess) { 17556 // Need to do this on its own message because the stack may not 17557 // be in a consistent state at this point. 17558 // For these apps we will also finish their activities 17559 // to help them free memory. 17560 mStackSupervisor.scheduleDestroyAllActivities(app, "trim"); 17561 } 17562 } 17563 } 17564 app.trimMemoryLevel = curLevel; 17565 step++; 17566 if (step >= factor) { 17567 step = 0; 17568 switch (curLevel) { 17569 case ComponentCallbacks2.TRIM_MEMORY_COMPLETE: 17570 curLevel = ComponentCallbacks2.TRIM_MEMORY_MODERATE; 17571 break; 17572 case ComponentCallbacks2.TRIM_MEMORY_MODERATE: 17573 curLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 17574 break; 17575 } 17576 } 17577 } else if (app.curProcState == ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 17578 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_BACKGROUND 17579 && app.thread != null) { 17580 try { 17581 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17582 "Trimming memory of heavy-weight " + app.processName 17583 + " to " + ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 17584 app.thread.scheduleTrimMemory( 17585 ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 17586 } catch (RemoteException e) { 17587 } 17588 } 17589 app.trimMemoryLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 17590 } else { 17591 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 17592 || app.systemNoUi) && app.pendingUiClean) { 17593 // If this application is now in the background and it 17594 // had done UI, then give it the special trim level to 17595 // have it free UI resources. 17596 final int level = ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN; 17597 if (app.trimMemoryLevel < level && app.thread != null) { 17598 try { 17599 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17600 "Trimming memory of bg-ui " + app.processName 17601 + " to " + level); 17602 app.thread.scheduleTrimMemory(level); 17603 } catch (RemoteException e) { 17604 } 17605 } 17606 app.pendingUiClean = false; 17607 } 17608 if (app.trimMemoryLevel < fgTrimLevel && app.thread != null) { 17609 try { 17610 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17611 "Trimming memory of fg " + app.processName 17612 + " to " + fgTrimLevel); 17613 app.thread.scheduleTrimMemory(fgTrimLevel); 17614 } catch (RemoteException e) { 17615 } 17616 } 17617 app.trimMemoryLevel = fgTrimLevel; 17618 } 17619 } 17620 } else { 17621 if (mLowRamStartTime != 0) { 17622 mLowRamTimeSinceLastIdle += now - mLowRamStartTime; 17623 mLowRamStartTime = 0; 17624 } 17625 for (int i=N-1; i>=0; i--) { 17626 ProcessRecord app = mLruProcesses.get(i); 17627 if (allChanged || app.procStateChanged) { 17628 setProcessTrackerStateLocked(app, trackerMemFactor, now); 17629 app.procStateChanged = false; 17630 } 17631 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 17632 || app.systemNoUi) && app.pendingUiClean) { 17633 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN 17634 && app.thread != null) { 17635 try { 17636 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17637 "Trimming memory of ui hidden " + app.processName 17638 + " to " + ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 17639 app.thread.scheduleTrimMemory( 17640 ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 17641 } catch (RemoteException e) { 17642 } 17643 } 17644 app.pendingUiClean = false; 17645 } 17646 app.trimMemoryLevel = 0; 17647 } 17648 } 17649 17650 if (mAlwaysFinishActivities) { 17651 // Need to do this on its own message because the stack may not 17652 // be in a consistent state at this point. 17653 mStackSupervisor.scheduleDestroyAllActivities(null, "always-finish"); 17654 } 17655 17656 if (allChanged) { 17657 requestPssAllProcsLocked(now, false, mProcessStats.isMemFactorLowered()); 17658 } 17659 17660 if (mProcessStats.shouldWriteNowLocked(now)) { 17661 mHandler.post(new Runnable() { 17662 @Override public void run() { 17663 synchronized (ActivityManagerService.this) { 17664 mProcessStats.writeStateAsyncLocked(); 17665 } 17666 } 17667 }); 17668 } 17669 17670 if (DEBUG_OOM_ADJ) { 17671 Slog.d(TAG, "Did OOM ADJ in " + (SystemClock.uptimeMillis()-now) + "ms"); 17672 } 17673 } 17674 17675 final void trimApplications() { 17676 synchronized (this) { 17677 int i; 17678 17679 // First remove any unused application processes whose package 17680 // has been removed. 17681 for (i=mRemovedProcesses.size()-1; i>=0; i--) { 17682 final ProcessRecord app = mRemovedProcesses.get(i); 17683 if (app.activities.size() == 0 17684 && app.curReceiver == null && app.services.size() == 0) { 17685 Slog.i( 17686 TAG, "Exiting empty application process " 17687 + app.processName + " (" 17688 + (app.thread != null ? app.thread.asBinder() : null) 17689 + ")\n"); 17690 if (app.pid > 0 && app.pid != MY_PID) { 17691 app.kill("empty", false); 17692 } else { 17693 try { 17694 app.thread.scheduleExit(); 17695 } catch (Exception e) { 17696 // Ignore exceptions. 17697 } 17698 } 17699 cleanUpApplicationRecordLocked(app, false, true, -1); 17700 mRemovedProcesses.remove(i); 17701 17702 if (app.persistent) { 17703 addAppLocked(app.info, false, null /* ABI override */); 17704 } 17705 } 17706 } 17707 17708 // Now update the oom adj for all processes. 17709 updateOomAdjLocked(); 17710 } 17711 } 17712 17713 /** This method sends the specified signal to each of the persistent apps */ 17714 public void signalPersistentProcesses(int sig) throws RemoteException { 17715 if (sig != Process.SIGNAL_USR1) { 17716 throw new SecurityException("Only SIGNAL_USR1 is allowed"); 17717 } 17718 17719 synchronized (this) { 17720 if (checkCallingPermission(android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES) 17721 != PackageManager.PERMISSION_GRANTED) { 17722 throw new SecurityException("Requires permission " 17723 + android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES); 17724 } 17725 17726 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 17727 ProcessRecord r = mLruProcesses.get(i); 17728 if (r.thread != null && r.persistent) { 17729 Process.sendSignal(r.pid, sig); 17730 } 17731 } 17732 } 17733 } 17734 17735 private void stopProfilerLocked(ProcessRecord proc, int profileType) { 17736 if (proc == null || proc == mProfileProc) { 17737 proc = mProfileProc; 17738 profileType = mProfileType; 17739 clearProfilerLocked(); 17740 } 17741 if (proc == null) { 17742 return; 17743 } 17744 try { 17745 proc.thread.profilerControl(false, null, profileType); 17746 } catch (RemoteException e) { 17747 throw new IllegalStateException("Process disappeared"); 17748 } 17749 } 17750 17751 private void clearProfilerLocked() { 17752 if (mProfileFd != null) { 17753 try { 17754 mProfileFd.close(); 17755 } catch (IOException e) { 17756 } 17757 } 17758 mProfileApp = null; 17759 mProfileProc = null; 17760 mProfileFile = null; 17761 mProfileType = 0; 17762 mAutoStopProfiler = false; 17763 mSamplingInterval = 0; 17764 } 17765 17766 public boolean profileControl(String process, int userId, boolean start, 17767 ProfilerInfo profilerInfo, int profileType) throws RemoteException { 17768 17769 try { 17770 synchronized (this) { 17771 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 17772 // its own permission. 17773 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 17774 != PackageManager.PERMISSION_GRANTED) { 17775 throw new SecurityException("Requires permission " 17776 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 17777 } 17778 17779 if (start && (profilerInfo == null || profilerInfo.profileFd == null)) { 17780 throw new IllegalArgumentException("null profile info or fd"); 17781 } 17782 17783 ProcessRecord proc = null; 17784 if (process != null) { 17785 proc = findProcessLocked(process, userId, "profileControl"); 17786 } 17787 17788 if (start && (proc == null || proc.thread == null)) { 17789 throw new IllegalArgumentException("Unknown process: " + process); 17790 } 17791 17792 if (start) { 17793 stopProfilerLocked(null, 0); 17794 setProfileApp(proc.info, proc.processName, profilerInfo); 17795 mProfileProc = proc; 17796 mProfileType = profileType; 17797 ParcelFileDescriptor fd = profilerInfo.profileFd; 17798 try { 17799 fd = fd.dup(); 17800 } catch (IOException e) { 17801 fd = null; 17802 } 17803 profilerInfo.profileFd = fd; 17804 proc.thread.profilerControl(start, profilerInfo, profileType); 17805 fd = null; 17806 mProfileFd = null; 17807 } else { 17808 stopProfilerLocked(proc, profileType); 17809 if (profilerInfo != null && profilerInfo.profileFd != null) { 17810 try { 17811 profilerInfo.profileFd.close(); 17812 } catch (IOException e) { 17813 } 17814 } 17815 } 17816 17817 return true; 17818 } 17819 } catch (RemoteException e) { 17820 throw new IllegalStateException("Process disappeared"); 17821 } finally { 17822 if (profilerInfo != null && profilerInfo.profileFd != null) { 17823 try { 17824 profilerInfo.profileFd.close(); 17825 } catch (IOException e) { 17826 } 17827 } 17828 } 17829 } 17830 17831 private ProcessRecord findProcessLocked(String process, int userId, String callName) { 17832 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 17833 userId, true, ALLOW_FULL_ONLY, callName, null); 17834 ProcessRecord proc = null; 17835 try { 17836 int pid = Integer.parseInt(process); 17837 synchronized (mPidsSelfLocked) { 17838 proc = mPidsSelfLocked.get(pid); 17839 } 17840 } catch (NumberFormatException e) { 17841 } 17842 17843 if (proc == null) { 17844 ArrayMap<String, SparseArray<ProcessRecord>> all 17845 = mProcessNames.getMap(); 17846 SparseArray<ProcessRecord> procs = all.get(process); 17847 if (procs != null && procs.size() > 0) { 17848 proc = procs.valueAt(0); 17849 if (userId != UserHandle.USER_ALL && proc.userId != userId) { 17850 for (int i=1; i<procs.size(); i++) { 17851 ProcessRecord thisProc = procs.valueAt(i); 17852 if (thisProc.userId == userId) { 17853 proc = thisProc; 17854 break; 17855 } 17856 } 17857 } 17858 } 17859 } 17860 17861 return proc; 17862 } 17863 17864 public boolean dumpHeap(String process, int userId, boolean managed, 17865 String path, ParcelFileDescriptor fd) throws RemoteException { 17866 17867 try { 17868 synchronized (this) { 17869 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 17870 // its own permission (same as profileControl). 17871 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 17872 != PackageManager.PERMISSION_GRANTED) { 17873 throw new SecurityException("Requires permission " 17874 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 17875 } 17876 17877 if (fd == null) { 17878 throw new IllegalArgumentException("null fd"); 17879 } 17880 17881 ProcessRecord proc = findProcessLocked(process, userId, "dumpHeap"); 17882 if (proc == null || proc.thread == null) { 17883 throw new IllegalArgumentException("Unknown process: " + process); 17884 } 17885 17886 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 17887 if (!isDebuggable) { 17888 if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 17889 throw new SecurityException("Process not debuggable: " + proc); 17890 } 17891 } 17892 17893 proc.thread.dumpHeap(managed, path, fd); 17894 fd = null; 17895 return true; 17896 } 17897 } catch (RemoteException e) { 17898 throw new IllegalStateException("Process disappeared"); 17899 } finally { 17900 if (fd != null) { 17901 try { 17902 fd.close(); 17903 } catch (IOException e) { 17904 } 17905 } 17906 } 17907 } 17908 17909 /** In this method we try to acquire our lock to make sure that we have not deadlocked */ 17910 public void monitor() { 17911 synchronized (this) { } 17912 } 17913 17914 void onCoreSettingsChange(Bundle settings) { 17915 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 17916 ProcessRecord processRecord = mLruProcesses.get(i); 17917 try { 17918 if (processRecord.thread != null) { 17919 processRecord.thread.setCoreSettings(settings); 17920 } 17921 } catch (RemoteException re) { 17922 /* ignore */ 17923 } 17924 } 17925 } 17926 17927 // Multi-user methods 17928 17929 /** 17930 * Start user, if its not already running, but don't bring it to foreground. 17931 */ 17932 @Override 17933 public boolean startUserInBackground(final int userId) { 17934 return startUser(userId, /* foreground */ false); 17935 } 17936 17937 /** 17938 * Start user, if its not already running, and bring it to foreground. 17939 */ 17940 boolean startUserInForeground(final int userId, Dialog dlg) { 17941 boolean result = startUser(userId, /* foreground */ true); 17942 dlg.dismiss(); 17943 return result; 17944 } 17945 17946 /** 17947 * Refreshes the list of users related to the current user when either a 17948 * user switch happens or when a new related user is started in the 17949 * background. 17950 */ 17951 private void updateCurrentProfileIdsLocked() { 17952 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17953 mCurrentUserId, false /* enabledOnly */); 17954 int[] currentProfileIds = new int[profiles.size()]; // profiles will not be null 17955 for (int i = 0; i < currentProfileIds.length; i++) { 17956 currentProfileIds[i] = profiles.get(i).id; 17957 } 17958 mCurrentProfileIds = currentProfileIds; 17959 17960 synchronized (mUserProfileGroupIdsSelfLocked) { 17961 mUserProfileGroupIdsSelfLocked.clear(); 17962 final List<UserInfo> users = getUserManagerLocked().getUsers(false); 17963 for (int i = 0; i < users.size(); i++) { 17964 UserInfo user = users.get(i); 17965 if (user.profileGroupId != UserInfo.NO_PROFILE_GROUP_ID) { 17966 mUserProfileGroupIdsSelfLocked.put(user.id, user.profileGroupId); 17967 } 17968 } 17969 } 17970 } 17971 17972 private Set getProfileIdsLocked(int userId) { 17973 Set userIds = new HashSet<Integer>(); 17974 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17975 userId, false /* enabledOnly */); 17976 for (UserInfo user : profiles) { 17977 userIds.add(Integer.valueOf(user.id)); 17978 } 17979 return userIds; 17980 } 17981 17982 @Override 17983 public boolean switchUser(final int userId) { 17984 String userName; 17985 synchronized (this) { 17986 UserInfo userInfo = getUserManagerLocked().getUserInfo(userId); 17987 if (userInfo == null) { 17988 Slog.w(TAG, "No user info for user #" + userId); 17989 return false; 17990 } 17991 if (userInfo.isManagedProfile()) { 17992 Slog.w(TAG, "Cannot switch to User #" + userId + ": not a full user"); 17993 return false; 17994 } 17995 userName = userInfo.name; 17996 mTargetUserId = userId; 17997 } 17998 mHandler.removeMessages(START_USER_SWITCH_MSG); 17999 mHandler.sendMessage(mHandler.obtainMessage(START_USER_SWITCH_MSG, userId, 0, userName)); 18000 return true; 18001 } 18002 18003 private void showUserSwitchDialog(int userId, String userName) { 18004 // The dialog will show and then initiate the user switch by calling startUserInForeground 18005 Dialog d = new UserSwitchingDialog(this, mContext, userId, userName, 18006 true /* above system */); 18007 d.show(); 18008 } 18009 18010 private boolean startUser(final int userId, final boolean foreground) { 18011 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 18012 != PackageManager.PERMISSION_GRANTED) { 18013 String msg = "Permission Denial: switchUser() from pid=" 18014 + Binder.getCallingPid() 18015 + ", uid=" + Binder.getCallingUid() 18016 + " requires " + INTERACT_ACROSS_USERS_FULL; 18017 Slog.w(TAG, msg); 18018 throw new SecurityException(msg); 18019 } 18020 18021 if (DEBUG_MU) Slog.i(TAG_MU, "starting userid:" + userId + " fore:" + foreground); 18022 18023 final long ident = Binder.clearCallingIdentity(); 18024 try { 18025 synchronized (this) { 18026 final int oldUserId = mCurrentUserId; 18027 if (oldUserId == userId) { 18028 return true; 18029 } 18030 18031 mStackSupervisor.setLockTaskModeLocked(null, false); 18032 18033 final UserInfo userInfo = getUserManagerLocked().getUserInfo(userId); 18034 if (userInfo == null) { 18035 Slog.w(TAG, "No user info for user #" + userId); 18036 return false; 18037 } 18038 if (foreground && userInfo.isManagedProfile()) { 18039 Slog.w(TAG, "Cannot switch to User #" + userId + ": not a full user"); 18040 return false; 18041 } 18042 18043 if (foreground) { 18044 mWindowManager.startFreezingScreen(R.anim.screen_user_exit, 18045 R.anim.screen_user_enter); 18046 } 18047 18048 boolean needStart = false; 18049 18050 // If the user we are switching to is not currently started, then 18051 // we need to start it now. 18052 if (mStartedUsers.get(userId) == null) { 18053 mStartedUsers.put(userId, new UserStartedState(new UserHandle(userId), false)); 18054 updateStartedUserArrayLocked(); 18055 needStart = true; 18056 } 18057 18058 final Integer userIdInt = Integer.valueOf(userId); 18059 mUserLru.remove(userIdInt); 18060 mUserLru.add(userIdInt); 18061 18062 if (foreground) { 18063 mCurrentUserId = userId; 18064 mTargetUserId = UserHandle.USER_NULL; // reset, mCurrentUserId has caught up 18065 updateCurrentProfileIdsLocked(); 18066 mWindowManager.setCurrentUser(userId, mCurrentProfileIds); 18067 // Once the internal notion of the active user has switched, we lock the device 18068 // with the option to show the user switcher on the keyguard. 18069 mWindowManager.lockNow(null); 18070 } else { 18071 final Integer currentUserIdInt = Integer.valueOf(mCurrentUserId); 18072 updateCurrentProfileIdsLocked(); 18073 mWindowManager.setCurrentProfileIds(mCurrentProfileIds); 18074 mUserLru.remove(currentUserIdInt); 18075 mUserLru.add(currentUserIdInt); 18076 } 18077 18078 final UserStartedState uss = mStartedUsers.get(userId); 18079 18080 // Make sure user is in the started state. If it is currently 18081 // stopping, we need to knock that off. 18082 if (uss.mState == UserStartedState.STATE_STOPPING) { 18083 // If we are stopping, we haven't sent ACTION_SHUTDOWN, 18084 // so we can just fairly silently bring the user back from 18085 // the almost-dead. 18086 uss.mState = UserStartedState.STATE_RUNNING; 18087 updateStartedUserArrayLocked(); 18088 needStart = true; 18089 } else if (uss.mState == UserStartedState.STATE_SHUTDOWN) { 18090 // This means ACTION_SHUTDOWN has been sent, so we will 18091 // need to treat this as a new boot of the user. 18092 uss.mState = UserStartedState.STATE_BOOTING; 18093 updateStartedUserArrayLocked(); 18094 needStart = true; 18095 } 18096 18097 if (uss.mState == UserStartedState.STATE_BOOTING) { 18098 // Booting up a new user, need to tell system services about it. 18099 // Note that this is on the same handler as scheduling of broadcasts, 18100 // which is important because it needs to go first. 18101 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_START_MSG, userId, 0)); 18102 } 18103 18104 if (foreground) { 18105 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_CURRENT_MSG, userId, 18106 oldUserId)); 18107 mHandler.removeMessages(REPORT_USER_SWITCH_MSG); 18108 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 18109 mHandler.sendMessage(mHandler.obtainMessage(REPORT_USER_SWITCH_MSG, 18110 oldUserId, userId, uss)); 18111 mHandler.sendMessageDelayed(mHandler.obtainMessage(USER_SWITCH_TIMEOUT_MSG, 18112 oldUserId, userId, uss), USER_SWITCH_TIMEOUT); 18113 } 18114 18115 if (needStart) { 18116 // Send USER_STARTED broadcast 18117 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 18118 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 18119 | Intent.FLAG_RECEIVER_FOREGROUND); 18120 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 18121 broadcastIntentLocked(null, null, intent, 18122 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 18123 false, false, MY_PID, Process.SYSTEM_UID, userId); 18124 } 18125 18126 if ((userInfo.flags&UserInfo.FLAG_INITIALIZED) == 0) { 18127 if (userId != UserHandle.USER_OWNER) { 18128 Intent intent = new Intent(Intent.ACTION_USER_INITIALIZE); 18129 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 18130 broadcastIntentLocked(null, null, intent, null, 18131 new IIntentReceiver.Stub() { 18132 public void performReceive(Intent intent, int resultCode, 18133 String data, Bundle extras, boolean ordered, 18134 boolean sticky, int sendingUser) { 18135 onUserInitialized(uss, foreground, oldUserId, userId); 18136 } 18137 }, 0, null, null, null, AppOpsManager.OP_NONE, 18138 true, false, MY_PID, Process.SYSTEM_UID, 18139 userId); 18140 uss.initializing = true; 18141 } else { 18142 getUserManagerLocked().makeInitialized(userInfo.id); 18143 } 18144 } 18145 18146 if (foreground) { 18147 if (!uss.initializing) { 18148 moveUserToForeground(uss, oldUserId, userId); 18149 } 18150 } else { 18151 mStackSupervisor.startBackgroundUserLocked(userId, uss); 18152 } 18153 18154 if (needStart) { 18155 Intent intent = new Intent(Intent.ACTION_USER_STARTING); 18156 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 18157 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 18158 broadcastIntentLocked(null, null, intent, 18159 null, new IIntentReceiver.Stub() { 18160 @Override 18161 public void performReceive(Intent intent, int resultCode, String data, 18162 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 18163 throws RemoteException { 18164 } 18165 }, 0, null, null, 18166 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 18167 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 18168 } 18169 } 18170 } finally { 18171 Binder.restoreCallingIdentity(ident); 18172 } 18173 18174 return true; 18175 } 18176 18177 void sendUserSwitchBroadcastsLocked(int oldUserId, int newUserId) { 18178 long ident = Binder.clearCallingIdentity(); 18179 try { 18180 Intent intent; 18181 if (oldUserId >= 0) { 18182 // Send USER_BACKGROUND broadcast to all profiles of the outgoing user 18183 List<UserInfo> profiles = mUserManager.getProfiles(oldUserId, false); 18184 int count = profiles.size(); 18185 for (int i = 0; i < count; i++) { 18186 int profileUserId = profiles.get(i).id; 18187 intent = new Intent(Intent.ACTION_USER_BACKGROUND); 18188 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 18189 | Intent.FLAG_RECEIVER_FOREGROUND); 18190 intent.putExtra(Intent.EXTRA_USER_HANDLE, profileUserId); 18191 broadcastIntentLocked(null, null, intent, 18192 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 18193 false, false, MY_PID, Process.SYSTEM_UID, profileUserId); 18194 } 18195 } 18196 if (newUserId >= 0) { 18197 // Send USER_FOREGROUND broadcast to all profiles of the incoming user 18198 List<UserInfo> profiles = mUserManager.getProfiles(newUserId, false); 18199 int count = profiles.size(); 18200 for (int i = 0; i < count; i++) { 18201 int profileUserId = profiles.get(i).id; 18202 intent = new Intent(Intent.ACTION_USER_FOREGROUND); 18203 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 18204 | Intent.FLAG_RECEIVER_FOREGROUND); 18205 intent.putExtra(Intent.EXTRA_USER_HANDLE, profileUserId); 18206 broadcastIntentLocked(null, null, intent, 18207 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 18208 false, false, MY_PID, Process.SYSTEM_UID, profileUserId); 18209 } 18210 intent = new Intent(Intent.ACTION_USER_SWITCHED); 18211 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 18212 | Intent.FLAG_RECEIVER_FOREGROUND); 18213 intent.putExtra(Intent.EXTRA_USER_HANDLE, newUserId); 18214 broadcastIntentLocked(null, null, intent, 18215 null, null, 0, null, null, 18216 android.Manifest.permission.MANAGE_USERS, AppOpsManager.OP_NONE, 18217 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 18218 } 18219 } finally { 18220 Binder.restoreCallingIdentity(ident); 18221 } 18222 } 18223 18224 void dispatchUserSwitch(final UserStartedState uss, final int oldUserId, 18225 final int newUserId) { 18226 final int N = mUserSwitchObservers.beginBroadcast(); 18227 if (N > 0) { 18228 final IRemoteCallback callback = new IRemoteCallback.Stub() { 18229 int mCount = 0; 18230 @Override 18231 public void sendResult(Bundle data) throws RemoteException { 18232 synchronized (ActivityManagerService.this) { 18233 if (mCurUserSwitchCallback == this) { 18234 mCount++; 18235 if (mCount == N) { 18236 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 18237 } 18238 } 18239 } 18240 } 18241 }; 18242 synchronized (this) { 18243 uss.switching = true; 18244 mCurUserSwitchCallback = callback; 18245 } 18246 for (int i=0; i<N; i++) { 18247 try { 18248 mUserSwitchObservers.getBroadcastItem(i).onUserSwitching( 18249 newUserId, callback); 18250 } catch (RemoteException e) { 18251 } 18252 } 18253 } else { 18254 synchronized (this) { 18255 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 18256 } 18257 } 18258 mUserSwitchObservers.finishBroadcast(); 18259 } 18260 18261 void timeoutUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 18262 synchronized (this) { 18263 Slog.w(TAG, "User switch timeout: from " + oldUserId + " to " + newUserId); 18264 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 18265 } 18266 } 18267 18268 void sendContinueUserSwitchLocked(UserStartedState uss, int oldUserId, int newUserId) { 18269 mCurUserSwitchCallback = null; 18270 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 18271 mHandler.sendMessage(mHandler.obtainMessage(CONTINUE_USER_SWITCH_MSG, 18272 oldUserId, newUserId, uss)); 18273 } 18274 18275 void onUserInitialized(UserStartedState uss, boolean foreground, int oldUserId, int newUserId) { 18276 synchronized (this) { 18277 if (foreground) { 18278 moveUserToForeground(uss, oldUserId, newUserId); 18279 } 18280 } 18281 18282 completeSwitchAndInitalize(uss, newUserId, true, false); 18283 } 18284 18285 void moveUserToForeground(UserStartedState uss, int oldUserId, int newUserId) { 18286 boolean homeInFront = mStackSupervisor.switchUserLocked(newUserId, uss); 18287 if (homeInFront) { 18288 startHomeActivityLocked(newUserId); 18289 } else { 18290 mStackSupervisor.resumeTopActivitiesLocked(); 18291 } 18292 EventLogTags.writeAmSwitchUser(newUserId); 18293 getUserManagerLocked().userForeground(newUserId); 18294 sendUserSwitchBroadcastsLocked(oldUserId, newUserId); 18295 } 18296 18297 void continueUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 18298 completeSwitchAndInitalize(uss, newUserId, false, true); 18299 } 18300 18301 void completeSwitchAndInitalize(UserStartedState uss, int newUserId, 18302 boolean clearInitializing, boolean clearSwitching) { 18303 boolean unfrozen = false; 18304 synchronized (this) { 18305 if (clearInitializing) { 18306 uss.initializing = false; 18307 getUserManagerLocked().makeInitialized(uss.mHandle.getIdentifier()); 18308 } 18309 if (clearSwitching) { 18310 uss.switching = false; 18311 } 18312 if (!uss.switching && !uss.initializing) { 18313 mWindowManager.stopFreezingScreen(); 18314 unfrozen = true; 18315 } 18316 } 18317 if (unfrozen) { 18318 final int N = mUserSwitchObservers.beginBroadcast(); 18319 for (int i=0; i<N; i++) { 18320 try { 18321 mUserSwitchObservers.getBroadcastItem(i).onUserSwitchComplete(newUserId); 18322 } catch (RemoteException e) { 18323 } 18324 } 18325 mUserSwitchObservers.finishBroadcast(); 18326 } 18327 } 18328 18329 void scheduleStartProfilesLocked() { 18330 if (!mHandler.hasMessages(START_PROFILES_MSG)) { 18331 mHandler.sendMessageDelayed(mHandler.obtainMessage(START_PROFILES_MSG), 18332 DateUtils.SECOND_IN_MILLIS); 18333 } 18334 } 18335 18336 void startProfilesLocked() { 18337 if (DEBUG_MU) Slog.i(TAG_MU, "startProfilesLocked"); 18338 List<UserInfo> profiles = getUserManagerLocked().getProfiles( 18339 mCurrentUserId, false /* enabledOnly */); 18340 List<UserInfo> toStart = new ArrayList<UserInfo>(profiles.size()); 18341 for (UserInfo user : profiles) { 18342 if ((user.flags & UserInfo.FLAG_INITIALIZED) == UserInfo.FLAG_INITIALIZED 18343 && user.id != mCurrentUserId) { 18344 toStart.add(user); 18345 } 18346 } 18347 final int n = toStart.size(); 18348 int i = 0; 18349 for (; i < n && i < (MAX_RUNNING_USERS - 1); ++i) { 18350 startUserInBackground(toStart.get(i).id); 18351 } 18352 if (i < n) { 18353 Slog.w(TAG_MU, "More profiles than MAX_RUNNING_USERS"); 18354 } 18355 } 18356 18357 void finishUserBoot(UserStartedState uss) { 18358 synchronized (this) { 18359 if (uss.mState == UserStartedState.STATE_BOOTING 18360 && mStartedUsers.get(uss.mHandle.getIdentifier()) == uss) { 18361 uss.mState = UserStartedState.STATE_RUNNING; 18362 final int userId = uss.mHandle.getIdentifier(); 18363 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 18364 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 18365 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 18366 broadcastIntentLocked(null, null, intent, 18367 null, null, 0, null, null, 18368 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, AppOpsManager.OP_NONE, 18369 true, false, MY_PID, Process.SYSTEM_UID, userId); 18370 } 18371 } 18372 } 18373 18374 void finishUserSwitch(UserStartedState uss) { 18375 synchronized (this) { 18376 finishUserBoot(uss); 18377 18378 startProfilesLocked(); 18379 18380 int num = mUserLru.size(); 18381 int i = 0; 18382 while (num > MAX_RUNNING_USERS && i < mUserLru.size()) { 18383 Integer oldUserId = mUserLru.get(i); 18384 UserStartedState oldUss = mStartedUsers.get(oldUserId); 18385 if (oldUss == null) { 18386 // Shouldn't happen, but be sane if it does. 18387 mUserLru.remove(i); 18388 num--; 18389 continue; 18390 } 18391 if (oldUss.mState == UserStartedState.STATE_STOPPING 18392 || oldUss.mState == UserStartedState.STATE_SHUTDOWN) { 18393 // This user is already stopping, doesn't count. 18394 num--; 18395 i++; 18396 continue; 18397 } 18398 if (oldUserId == UserHandle.USER_OWNER || oldUserId == mCurrentUserId) { 18399 // Owner and current can't be stopped, but count as running. 18400 i++; 18401 continue; 18402 } 18403 // This is a user to be stopped. 18404 stopUserLocked(oldUserId, null); 18405 num--; 18406 i++; 18407 } 18408 } 18409 } 18410 18411 @Override 18412 public int stopUser(final int userId, final IStopUserCallback callback) { 18413 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 18414 != PackageManager.PERMISSION_GRANTED) { 18415 String msg = "Permission Denial: switchUser() from pid=" 18416 + Binder.getCallingPid() 18417 + ", uid=" + Binder.getCallingUid() 18418 + " requires " + INTERACT_ACROSS_USERS_FULL; 18419 Slog.w(TAG, msg); 18420 throw new SecurityException(msg); 18421 } 18422 if (userId <= 0) { 18423 throw new IllegalArgumentException("Can't stop primary user " + userId); 18424 } 18425 synchronized (this) { 18426 return stopUserLocked(userId, callback); 18427 } 18428 } 18429 18430 private int stopUserLocked(final int userId, final IStopUserCallback callback) { 18431 if (DEBUG_MU) Slog.i(TAG_MU, "stopUserLocked userId=" + userId); 18432 if (mCurrentUserId == userId && mTargetUserId == UserHandle.USER_NULL) { 18433 return ActivityManager.USER_OP_IS_CURRENT; 18434 } 18435 18436 final UserStartedState uss = mStartedUsers.get(userId); 18437 if (uss == null) { 18438 // User is not started, nothing to do... but we do need to 18439 // callback if requested. 18440 if (callback != null) { 18441 mHandler.post(new Runnable() { 18442 @Override 18443 public void run() { 18444 try { 18445 callback.userStopped(userId); 18446 } catch (RemoteException e) { 18447 } 18448 } 18449 }); 18450 } 18451 return ActivityManager.USER_OP_SUCCESS; 18452 } 18453 18454 if (callback != null) { 18455 uss.mStopCallbacks.add(callback); 18456 } 18457 18458 if (uss.mState != UserStartedState.STATE_STOPPING 18459 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 18460 uss.mState = UserStartedState.STATE_STOPPING; 18461 updateStartedUserArrayLocked(); 18462 18463 long ident = Binder.clearCallingIdentity(); 18464 try { 18465 // We are going to broadcast ACTION_USER_STOPPING and then 18466 // once that is done send a final ACTION_SHUTDOWN and then 18467 // stop the user. 18468 final Intent stoppingIntent = new Intent(Intent.ACTION_USER_STOPPING); 18469 stoppingIntent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 18470 stoppingIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 18471 stoppingIntent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 18472 final Intent shutdownIntent = new Intent(Intent.ACTION_SHUTDOWN); 18473 // This is the result receiver for the final shutdown broadcast. 18474 final IIntentReceiver shutdownReceiver = new IIntentReceiver.Stub() { 18475 @Override 18476 public void performReceive(Intent intent, int resultCode, String data, 18477 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 18478 finishUserStop(uss); 18479 } 18480 }; 18481 // This is the result receiver for the initial stopping broadcast. 18482 final IIntentReceiver stoppingReceiver = new IIntentReceiver.Stub() { 18483 @Override 18484 public void performReceive(Intent intent, int resultCode, String data, 18485 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 18486 // On to the next. 18487 synchronized (ActivityManagerService.this) { 18488 if (uss.mState != UserStartedState.STATE_STOPPING) { 18489 // Whoops, we are being started back up. Abort, abort! 18490 return; 18491 } 18492 uss.mState = UserStartedState.STATE_SHUTDOWN; 18493 } 18494 mBatteryStatsService.noteEvent( 18495 BatteryStats.HistoryItem.EVENT_USER_RUNNING_FINISH, 18496 Integer.toString(userId), userId); 18497 mSystemServiceManager.stopUser(userId); 18498 broadcastIntentLocked(null, null, shutdownIntent, 18499 null, shutdownReceiver, 0, null, null, null, AppOpsManager.OP_NONE, 18500 true, false, MY_PID, Process.SYSTEM_UID, userId); 18501 } 18502 }; 18503 // Kick things off. 18504 broadcastIntentLocked(null, null, stoppingIntent, 18505 null, stoppingReceiver, 0, null, null, 18506 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 18507 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 18508 } finally { 18509 Binder.restoreCallingIdentity(ident); 18510 } 18511 } 18512 18513 return ActivityManager.USER_OP_SUCCESS; 18514 } 18515 18516 void finishUserStop(UserStartedState uss) { 18517 final int userId = uss.mHandle.getIdentifier(); 18518 boolean stopped; 18519 ArrayList<IStopUserCallback> callbacks; 18520 synchronized (this) { 18521 callbacks = new ArrayList<IStopUserCallback>(uss.mStopCallbacks); 18522 if (mStartedUsers.get(userId) != uss) { 18523 stopped = false; 18524 } else if (uss.mState != UserStartedState.STATE_SHUTDOWN) { 18525 stopped = false; 18526 } else { 18527 stopped = true; 18528 // User can no longer run. 18529 mStartedUsers.remove(userId); 18530 mUserLru.remove(Integer.valueOf(userId)); 18531 updateStartedUserArrayLocked(); 18532 18533 // Clean up all state and processes associated with the user. 18534 // Kill all the processes for the user. 18535 forceStopUserLocked(userId, "finish user"); 18536 } 18537 18538 // Explicitly remove the old information in mRecentTasks. 18539 removeRecentTasksForUserLocked(userId); 18540 } 18541 18542 for (int i=0; i<callbacks.size(); i++) { 18543 try { 18544 if (stopped) callbacks.get(i).userStopped(userId); 18545 else callbacks.get(i).userStopAborted(userId); 18546 } catch (RemoteException e) { 18547 } 18548 } 18549 18550 if (stopped) { 18551 mSystemServiceManager.cleanupUser(userId); 18552 synchronized (this) { 18553 mStackSupervisor.removeUserLocked(userId); 18554 } 18555 } 18556 } 18557 18558 @Override 18559 public UserInfo getCurrentUser() { 18560 if ((checkCallingPermission(INTERACT_ACROSS_USERS) 18561 != PackageManager.PERMISSION_GRANTED) && ( 18562 checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 18563 != PackageManager.PERMISSION_GRANTED)) { 18564 String msg = "Permission Denial: getCurrentUser() from pid=" 18565 + Binder.getCallingPid() 18566 + ", uid=" + Binder.getCallingUid() 18567 + " requires " + INTERACT_ACROSS_USERS; 18568 Slog.w(TAG, msg); 18569 throw new SecurityException(msg); 18570 } 18571 synchronized (this) { 18572 int userId = mTargetUserId != UserHandle.USER_NULL ? mTargetUserId : mCurrentUserId; 18573 return getUserManagerLocked().getUserInfo(userId); 18574 } 18575 } 18576 18577 int getCurrentUserIdLocked() { 18578 return mTargetUserId != UserHandle.USER_NULL ? mTargetUserId : mCurrentUserId; 18579 } 18580 18581 @Override 18582 public boolean isUserRunning(int userId, boolean orStopped) { 18583 if (checkCallingPermission(INTERACT_ACROSS_USERS) 18584 != PackageManager.PERMISSION_GRANTED) { 18585 String msg = "Permission Denial: isUserRunning() from pid=" 18586 + Binder.getCallingPid() 18587 + ", uid=" + Binder.getCallingUid() 18588 + " requires " + INTERACT_ACROSS_USERS; 18589 Slog.w(TAG, msg); 18590 throw new SecurityException(msg); 18591 } 18592 synchronized (this) { 18593 return isUserRunningLocked(userId, orStopped); 18594 } 18595 } 18596 18597 boolean isUserRunningLocked(int userId, boolean orStopped) { 18598 UserStartedState state = mStartedUsers.get(userId); 18599 if (state == null) { 18600 return false; 18601 } 18602 if (orStopped) { 18603 return true; 18604 } 18605 return state.mState != UserStartedState.STATE_STOPPING 18606 && state.mState != UserStartedState.STATE_SHUTDOWN; 18607 } 18608 18609 @Override 18610 public int[] getRunningUserIds() { 18611 if (checkCallingPermission(INTERACT_ACROSS_USERS) 18612 != PackageManager.PERMISSION_GRANTED) { 18613 String msg = "Permission Denial: isUserRunning() from pid=" 18614 + Binder.getCallingPid() 18615 + ", uid=" + Binder.getCallingUid() 18616 + " requires " + INTERACT_ACROSS_USERS; 18617 Slog.w(TAG, msg); 18618 throw new SecurityException(msg); 18619 } 18620 synchronized (this) { 18621 return mStartedUserArray; 18622 } 18623 } 18624 18625 private void updateStartedUserArrayLocked() { 18626 int num = 0; 18627 for (int i=0; i<mStartedUsers.size(); i++) { 18628 UserStartedState uss = mStartedUsers.valueAt(i); 18629 // This list does not include stopping users. 18630 if (uss.mState != UserStartedState.STATE_STOPPING 18631 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 18632 num++; 18633 } 18634 } 18635 mStartedUserArray = new int[num]; 18636 num = 0; 18637 for (int i=0; i<mStartedUsers.size(); i++) { 18638 UserStartedState uss = mStartedUsers.valueAt(i); 18639 if (uss.mState != UserStartedState.STATE_STOPPING 18640 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 18641 mStartedUserArray[num] = mStartedUsers.keyAt(i); 18642 num++; 18643 } 18644 } 18645 } 18646 18647 @Override 18648 public void registerUserSwitchObserver(IUserSwitchObserver observer) { 18649 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 18650 != PackageManager.PERMISSION_GRANTED) { 18651 String msg = "Permission Denial: registerUserSwitchObserver() from pid=" 18652 + Binder.getCallingPid() 18653 + ", uid=" + Binder.getCallingUid() 18654 + " requires " + INTERACT_ACROSS_USERS_FULL; 18655 Slog.w(TAG, msg); 18656 throw new SecurityException(msg); 18657 } 18658 18659 mUserSwitchObservers.register(observer); 18660 } 18661 18662 @Override 18663 public void unregisterUserSwitchObserver(IUserSwitchObserver observer) { 18664 mUserSwitchObservers.unregister(observer); 18665 } 18666 18667 private boolean userExists(int userId) { 18668 if (userId == 0) { 18669 return true; 18670 } 18671 UserManagerService ums = getUserManagerLocked(); 18672 return ums != null ? (ums.getUserInfo(userId) != null) : false; 18673 } 18674 18675 int[] getUsersLocked() { 18676 UserManagerService ums = getUserManagerLocked(); 18677 return ums != null ? ums.getUserIds() : new int[] { 0 }; 18678 } 18679 18680 UserManagerService getUserManagerLocked() { 18681 if (mUserManager == null) { 18682 IBinder b = ServiceManager.getService(Context.USER_SERVICE); 18683 mUserManager = (UserManagerService)IUserManager.Stub.asInterface(b); 18684 } 18685 return mUserManager; 18686 } 18687 18688 private int applyUserId(int uid, int userId) { 18689 return UserHandle.getUid(userId, uid); 18690 } 18691 18692 ApplicationInfo getAppInfoForUser(ApplicationInfo info, int userId) { 18693 if (info == null) return null; 18694 ApplicationInfo newInfo = new ApplicationInfo(info); 18695 newInfo.uid = applyUserId(info.uid, userId); 18696 newInfo.dataDir = USER_DATA_DIR + userId + "/" 18697 + info.packageName; 18698 return newInfo; 18699 } 18700 18701 ActivityInfo getActivityInfoForUser(ActivityInfo aInfo, int userId) { 18702 if (aInfo == null 18703 || (userId < 1 && aInfo.applicationInfo.uid < UserHandle.PER_USER_RANGE)) { 18704 return aInfo; 18705 } 18706 18707 ActivityInfo info = new ActivityInfo(aInfo); 18708 info.applicationInfo = getAppInfoForUser(info.applicationInfo, userId); 18709 return info; 18710 } 18711 18712 private final class LocalService extends ActivityManagerInternal { 18713 @Override 18714 public void goingToSleep() { 18715 ActivityManagerService.this.goingToSleep(); 18716 } 18717 18718 @Override 18719 public void wakingUp() { 18720 ActivityManagerService.this.wakingUp(); 18721 } 18722 18723 @Override 18724 public int startIsolatedProcess(String entryPoint, String[] entryPointArgs, 18725 String processName, String abiOverride, int uid, Runnable crashHandler) { 18726 return ActivityManagerService.this.startIsolatedProcess(entryPoint, entryPointArgs, 18727 processName, abiOverride, uid, crashHandler); 18728 } 18729 } 18730 18731 /** 18732 * An implementation of IAppTask, that allows an app to manage its own tasks via 18733 * {@link android.app.ActivityManager.AppTask}. We keep track of the callingUid to ensure that 18734 * only the process that calls getAppTasks() can call the AppTask methods. 18735 */ 18736 class AppTaskImpl extends IAppTask.Stub { 18737 private int mTaskId; 18738 private int mCallingUid; 18739 18740 public AppTaskImpl(int taskId, int callingUid) { 18741 mTaskId = taskId; 18742 mCallingUid = callingUid; 18743 } 18744 18745 private void checkCaller() { 18746 if (mCallingUid != Binder.getCallingUid()) { 18747 throw new SecurityException("Caller " + mCallingUid 18748 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 18749 } 18750 } 18751 18752 @Override 18753 public void finishAndRemoveTask() { 18754 checkCaller(); 18755 18756 synchronized (ActivityManagerService.this) { 18757 long origId = Binder.clearCallingIdentity(); 18758 try { 18759 TaskRecord tr = recentTaskForIdLocked(mTaskId); 18760 if (tr == null) { 18761 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 18762 } 18763 // Only kill the process if we are not a new document 18764 int flags = tr.getBaseIntent().getFlags(); 18765 boolean isDocument = (flags & Intent.FLAG_ACTIVITY_NEW_DOCUMENT) == 18766 Intent.FLAG_ACTIVITY_NEW_DOCUMENT; 18767 removeTaskByIdLocked(mTaskId, 18768 !isDocument ? ActivityManager.REMOVE_TASK_KILL_PROCESS : 0); 18769 } finally { 18770 Binder.restoreCallingIdentity(origId); 18771 } 18772 } 18773 } 18774 18775 @Override 18776 public ActivityManager.RecentTaskInfo getTaskInfo() { 18777 checkCaller(); 18778 18779 synchronized (ActivityManagerService.this) { 18780 long origId = Binder.clearCallingIdentity(); 18781 try { 18782 TaskRecord tr = recentTaskForIdLocked(mTaskId); 18783 if (tr == null) { 18784 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 18785 } 18786 return createRecentTaskInfoFromTaskRecord(tr); 18787 } finally { 18788 Binder.restoreCallingIdentity(origId); 18789 } 18790 } 18791 } 18792 18793 @Override 18794 public void moveToFront() { 18795 checkCaller(); 18796 18797 final TaskRecord tr; 18798 synchronized (ActivityManagerService.this) { 18799 tr = recentTaskForIdLocked(mTaskId); 18800 if (tr == null) { 18801 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 18802 } 18803 if (tr.getRootActivity() != null) { 18804 long origId = Binder.clearCallingIdentity(); 18805 try { 18806 moveTaskToFrontLocked(tr.taskId, 0, null); 18807 return; 18808 } finally { 18809 Binder.restoreCallingIdentity(origId); 18810 } 18811 } 18812 } 18813 18814 startActivityFromRecentsInner(tr.taskId, null); 18815 } 18816 18817 @Override 18818 public int startActivity(IBinder whoThread, String callingPackage, 18819 Intent intent, String resolvedType, Bundle options) { 18820 checkCaller(); 18821 18822 int callingUser = UserHandle.getCallingUserId(); 18823 TaskRecord tr; 18824 IApplicationThread appThread; 18825 synchronized (ActivityManagerService.this) { 18826 tr = recentTaskForIdLocked(mTaskId); 18827 if (tr == null) { 18828 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 18829 } 18830 appThread = ApplicationThreadNative.asInterface(whoThread); 18831 if (appThread == null) { 18832 throw new IllegalArgumentException("Bad app thread " + appThread); 18833 } 18834 } 18835 return mStackSupervisor.startActivityMayWait(appThread, -1, callingPackage, intent, 18836 resolvedType, null, null, null, null, 0, 0, null, null, 18837 null, options, callingUser, null, tr); 18838 } 18839 18840 @Override 18841 public void setExcludeFromRecents(boolean exclude) { 18842 checkCaller(); 18843 18844 synchronized (ActivityManagerService.this) { 18845 long origId = Binder.clearCallingIdentity(); 18846 try { 18847 TaskRecord tr = recentTaskForIdLocked(mTaskId); 18848 if (tr == null) { 18849 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 18850 } 18851 Intent intent = tr.getBaseIntent(); 18852 if (exclude) { 18853 intent.addFlags(Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 18854 } else { 18855 intent.setFlags(intent.getFlags() 18856 & ~Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 18857 } 18858 } finally { 18859 Binder.restoreCallingIdentity(origId); 18860 } 18861 } 18862 } 18863 } 18864} 18865