ActivityManagerService.java revision f71edcaa1446c54956ea5d29a44343361a668755
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; 199 200import java.io.BufferedInputStream; 201import java.io.BufferedOutputStream; 202import java.io.DataInputStream; 203import java.io.DataOutputStream; 204import java.io.File; 205import java.io.FileDescriptor; 206import java.io.FileInputStream; 207import java.io.FileNotFoundException; 208import java.io.FileOutputStream; 209import java.io.IOException; 210import java.io.InputStreamReader; 211import java.io.PrintWriter; 212import java.io.StringWriter; 213import java.lang.ref.WeakReference; 214import java.util.ArrayList; 215import java.util.Arrays; 216import java.util.Collections; 217import java.util.Comparator; 218import java.util.HashMap; 219import java.util.HashSet; 220import java.util.Iterator; 221import java.util.List; 222import java.util.Locale; 223import java.util.Map; 224import java.util.Set; 225import java.util.concurrent.atomic.AtomicBoolean; 226import java.util.concurrent.atomic.AtomicLong; 227 228public final class ActivityManagerService extends ActivityManagerNative 229 implements Watchdog.Monitor, BatteryStatsImpl.BatteryCallback { 230 231 private static final String USER_DATA_DIR = "/data/user/"; 232 // File that stores last updated system version and called preboot receivers 233 static final String CALLED_PRE_BOOTS_FILENAME = "called_pre_boots.dat"; 234 235 static final String TAG = "ActivityManager"; 236 static final String TAG_MU = "ActivityManagerServiceMU"; 237 static final boolean DEBUG = false; 238 static final boolean localLOGV = DEBUG; 239 static final boolean DEBUG_BACKUP = localLOGV || false; 240 static final boolean DEBUG_BROADCAST = localLOGV || false; 241 static final boolean DEBUG_BROADCAST_LIGHT = DEBUG_BROADCAST || false; 242 static final boolean DEBUG_BACKGROUND_BROADCAST = DEBUG_BROADCAST || false; 243 static final boolean DEBUG_CLEANUP = localLOGV || false; 244 static final boolean DEBUG_CONFIGURATION = localLOGV || false; 245 static final boolean DEBUG_FOCUS = false; 246 static final boolean DEBUG_IMMERSIVE = localLOGV || false; 247 static final boolean DEBUG_MU = localLOGV || false; 248 static final boolean DEBUG_OOM_ADJ = localLOGV || false; 249 static final boolean DEBUG_LRU = localLOGV || false; 250 static final boolean DEBUG_PAUSE = localLOGV || false; 251 static final boolean DEBUG_POWER = localLOGV || false; 252 static final boolean DEBUG_POWER_QUICK = DEBUG_POWER || false; 253 static final boolean DEBUG_PROCESS_OBSERVERS = localLOGV || false; 254 static final boolean DEBUG_PROCESSES = localLOGV || false; 255 static final boolean DEBUG_PROVIDER = localLOGV || false; 256 static final boolean DEBUG_RESULTS = localLOGV || false; 257 static final boolean DEBUG_SERVICE = localLOGV || false; 258 static final boolean DEBUG_SERVICE_EXECUTING = localLOGV || false; 259 static final boolean DEBUG_STACK = localLOGV || false; 260 static final boolean DEBUG_SWITCH = localLOGV || false; 261 static final boolean DEBUG_TASKS = localLOGV || false; 262 static final boolean DEBUG_THUMBNAILS = localLOGV || false; 263 static final boolean DEBUG_TRANSITION = localLOGV || false; 264 static final boolean DEBUG_URI_PERMISSION = localLOGV || false; 265 static final boolean DEBUG_USER_LEAVING = localLOGV || false; 266 static final boolean DEBUG_VISBILITY = localLOGV || false; 267 static final boolean DEBUG_PSS = localLOGV || false; 268 static final boolean DEBUG_LOCKSCREEN = localLOGV || false; 269 static final boolean DEBUG_RECENTS = localLOGV || false; 270 static final boolean VALIDATE_TOKENS = false; 271 static final boolean SHOW_ACTIVITY_START_TIME = true; 272 273 // Control over CPU and battery monitoring. 274 static final long BATTERY_STATS_TIME = 30*60*1000; // write battery stats every 30 minutes. 275 static final boolean MONITOR_CPU_USAGE = true; 276 static final long MONITOR_CPU_MIN_TIME = 5*1000; // don't sample cpu less than every 5 seconds. 277 static final long MONITOR_CPU_MAX_TIME = 0x0fffffff; // wait possibly forever for next cpu sample. 278 static final boolean MONITOR_THREAD_CPU_USAGE = false; 279 280 // The flags that are set for all calls we make to the package manager. 281 static final int STOCK_PM_FLAGS = PackageManager.GET_SHARED_LIBRARY_FILES; 282 283 private static final String SYSTEM_DEBUGGABLE = "ro.debuggable"; 284 285 static final boolean IS_USER_BUILD = "user".equals(Build.TYPE); 286 287 // Maximum number recent bitmaps to keep in memory. 288 static final int MAX_RECENT_BITMAPS = 5; 289 290 // Amount of time after a call to stopAppSwitches() during which we will 291 // prevent further untrusted switches from happening. 292 static final long APP_SWITCH_DELAY_TIME = 5*1000; 293 294 // How long we wait for a launched process to attach to the activity manager 295 // before we decide it's never going to come up for real. 296 static final int PROC_START_TIMEOUT = 10*1000; 297 298 // How long we wait for a launched process to attach to the activity manager 299 // before we decide it's never going to come up for real, when the process was 300 // started with a wrapper for instrumentation (such as Valgrind) because it 301 // could take much longer than usual. 302 static final int PROC_START_TIMEOUT_WITH_WRAPPER = 1200*1000; 303 304 // How long to wait after going idle before forcing apps to GC. 305 static final int GC_TIMEOUT = 5*1000; 306 307 // The minimum amount of time between successive GC requests for a process. 308 static final int GC_MIN_INTERVAL = 60*1000; 309 310 // The minimum amount of time between successive PSS requests for a process. 311 static final int FULL_PSS_MIN_INTERVAL = 10*60*1000; 312 313 // The minimum amount of time between successive PSS requests for a process 314 // when the request is due to the memory state being lowered. 315 static final int FULL_PSS_LOWERED_INTERVAL = 2*60*1000; 316 317 // The rate at which we check for apps using excessive power -- 15 mins. 318 static final int POWER_CHECK_DELAY = (DEBUG_POWER_QUICK ? 2 : 15) * 60*1000; 319 320 // The minimum sample duration we will allow before deciding we have 321 // enough data on wake locks to start killing things. 322 static final int WAKE_LOCK_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 323 324 // The minimum sample duration we will allow before deciding we have 325 // enough data on CPU usage to start killing things. 326 static final int CPU_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 327 328 // How long we allow a receiver to run before giving up on it. 329 static final int BROADCAST_FG_TIMEOUT = 10*1000; 330 static final int BROADCAST_BG_TIMEOUT = 60*1000; 331 332 // How long we wait until we timeout on key dispatching. 333 static final int KEY_DISPATCHING_TIMEOUT = 5*1000; 334 335 // How long we wait until we timeout on key dispatching during instrumentation. 336 static final int INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT = 60*1000; 337 338 // Amount of time we wait for observers to handle a user switch before 339 // giving up on them and unfreezing the screen. 340 static final int USER_SWITCH_TIMEOUT = 2*1000; 341 342 // Maximum number of users we allow to be running at a time. 343 static final int MAX_RUNNING_USERS = 3; 344 345 // How long to wait in getAssistContextExtras for the activity and foreground services 346 // to respond with the result. 347 static final int PENDING_ASSIST_EXTRAS_TIMEOUT = 500; 348 349 // Maximum number of persisted Uri grants a package is allowed 350 static final int MAX_PERSISTED_URI_GRANTS = 128; 351 352 static final int MY_PID = Process.myPid(); 353 354 static final String[] EMPTY_STRING_ARRAY = new String[0]; 355 356 // How many bytes to write into the dropbox log before truncating 357 static final int DROPBOX_MAX_SIZE = 256 * 1024; 358 359 // Access modes for handleIncomingUser. 360 static final int ALLOW_NON_FULL = 0; 361 static final int ALLOW_NON_FULL_IN_PROFILE = 1; 362 static final int ALLOW_FULL_ONLY = 2; 363 364 static final int LAST_PREBOOT_DELIVERED_FILE_VERSION = 10000; 365 366 /** All system services */ 367 SystemServiceManager mSystemServiceManager; 368 369 /** Run all ActivityStacks through this */ 370 ActivityStackSupervisor mStackSupervisor; 371 372 public IntentFirewall mIntentFirewall; 373 374 // Whether we should show our dialogs (ANR, crash, etc) or just perform their 375 // default actuion automatically. Important for devices without direct input 376 // devices. 377 private boolean mShowDialogs = true; 378 379 BroadcastQueue mFgBroadcastQueue; 380 BroadcastQueue mBgBroadcastQueue; 381 // Convenient for easy iteration over the queues. Foreground is first 382 // so that dispatch of foreground broadcasts gets precedence. 383 final BroadcastQueue[] mBroadcastQueues = new BroadcastQueue[2]; 384 385 BroadcastQueue broadcastQueueForIntent(Intent intent) { 386 final boolean isFg = (intent.getFlags() & Intent.FLAG_RECEIVER_FOREGROUND) != 0; 387 if (DEBUG_BACKGROUND_BROADCAST) { 388 Slog.i(TAG, "Broadcast intent " + intent + " on " 389 + (isFg ? "foreground" : "background") 390 + " queue"); 391 } 392 return (isFg) ? mFgBroadcastQueue : mBgBroadcastQueue; 393 } 394 395 BroadcastRecord broadcastRecordForReceiverLocked(IBinder receiver) { 396 for (BroadcastQueue queue : mBroadcastQueues) { 397 BroadcastRecord r = queue.getMatchingOrderedReceiver(receiver); 398 if (r != null) { 399 return r; 400 } 401 } 402 return null; 403 } 404 405 /** 406 * Activity we have told the window manager to have key focus. 407 */ 408 ActivityRecord mFocusedActivity = null; 409 410 /** 411 * List of intents that were used to start the most recent tasks. 412 */ 413 ArrayList<TaskRecord> mRecentTasks; 414 ArraySet<TaskRecord> mTmpRecents = new ArraySet<TaskRecord>(); 415 416 /** 417 * For addAppTask: cached of the last activity component that was added. 418 */ 419 ComponentName mLastAddedTaskComponent; 420 421 /** 422 * For addAppTask: cached of the last activity uid that was added. 423 */ 424 int mLastAddedTaskUid; 425 426 /** 427 * For addAppTask: cached of the last ActivityInfo that was added. 428 */ 429 ActivityInfo mLastAddedTaskActivity; 430 431 public class PendingAssistExtras extends Binder implements Runnable { 432 public final ActivityRecord activity; 433 public boolean haveResult = false; 434 public Bundle result = null; 435 public PendingAssistExtras(ActivityRecord _activity) { 436 activity = _activity; 437 } 438 @Override 439 public void run() { 440 Slog.w(TAG, "getAssistContextExtras failed: timeout retrieving from " + activity); 441 synchronized (this) { 442 haveResult = true; 443 notifyAll(); 444 } 445 } 446 } 447 448 final ArrayList<PendingAssistExtras> mPendingAssistExtras 449 = new ArrayList<PendingAssistExtras>(); 450 451 /** 452 * Process management. 453 */ 454 final ProcessList mProcessList = new ProcessList(); 455 456 /** 457 * All of the applications we currently have running organized by name. 458 * The keys are strings of the application package name (as 459 * returned by the package manager), and the keys are ApplicationRecord 460 * objects. 461 */ 462 final ProcessMap<ProcessRecord> mProcessNames = new ProcessMap<ProcessRecord>(); 463 464 /** 465 * Tracking long-term execution of processes to look for abuse and other 466 * bad app behavior. 467 */ 468 final ProcessStatsService mProcessStats; 469 470 /** 471 * The currently running isolated processes. 472 */ 473 final SparseArray<ProcessRecord> mIsolatedProcesses = new SparseArray<ProcessRecord>(); 474 475 /** 476 * Counter for assigning isolated process uids, to avoid frequently reusing the 477 * same ones. 478 */ 479 int mNextIsolatedProcessUid = 0; 480 481 /** 482 * The currently running heavy-weight process, if any. 483 */ 484 ProcessRecord mHeavyWeightProcess = null; 485 486 /** 487 * The last time that various processes have crashed. 488 */ 489 final ProcessMap<Long> mProcessCrashTimes = new ProcessMap<Long>(); 490 491 /** 492 * Information about a process that is currently marked as bad. 493 */ 494 static final class BadProcessInfo { 495 BadProcessInfo(long time, String shortMsg, String longMsg, String stack) { 496 this.time = time; 497 this.shortMsg = shortMsg; 498 this.longMsg = longMsg; 499 this.stack = stack; 500 } 501 502 final long time; 503 final String shortMsg; 504 final String longMsg; 505 final String stack; 506 } 507 508 /** 509 * Set of applications that we consider to be bad, and will reject 510 * incoming broadcasts from (which the user has no control over). 511 * Processes are added to this set when they have crashed twice within 512 * a minimum amount of time; they are removed from it when they are 513 * later restarted (hopefully due to some user action). The value is the 514 * time it was added to the list. 515 */ 516 final ProcessMap<BadProcessInfo> mBadProcesses = new ProcessMap<BadProcessInfo>(); 517 518 /** 519 * All of the processes we currently have running organized by pid. 520 * The keys are the pid running the application. 521 * 522 * <p>NOTE: This object is protected by its own lock, NOT the global 523 * activity manager lock! 524 */ 525 final SparseArray<ProcessRecord> mPidsSelfLocked = new SparseArray<ProcessRecord>(); 526 527 /** 528 * All of the processes that have been forced to be foreground. The key 529 * is the pid of the caller who requested it (we hold a death 530 * link on it). 531 */ 532 abstract class ForegroundToken implements IBinder.DeathRecipient { 533 int pid; 534 IBinder token; 535 } 536 final SparseArray<ForegroundToken> mForegroundProcesses = new SparseArray<ForegroundToken>(); 537 538 /** 539 * List of records for processes that someone had tried to start before the 540 * system was ready. We don't start them at that point, but ensure they 541 * are started by the time booting is complete. 542 */ 543 final ArrayList<ProcessRecord> mProcessesOnHold = new ArrayList<ProcessRecord>(); 544 545 /** 546 * List of persistent applications that are in the process 547 * of being started. 548 */ 549 final ArrayList<ProcessRecord> mPersistentStartingProcesses = new ArrayList<ProcessRecord>(); 550 551 /** 552 * Processes that are being forcibly torn down. 553 */ 554 final ArrayList<ProcessRecord> mRemovedProcesses = new ArrayList<ProcessRecord>(); 555 556 /** 557 * List of running applications, sorted by recent usage. 558 * The first entry in the list is the least recently used. 559 */ 560 final ArrayList<ProcessRecord> mLruProcesses = new ArrayList<ProcessRecord>(); 561 562 /** 563 * Where in mLruProcesses that the processes hosting activities start. 564 */ 565 int mLruProcessActivityStart = 0; 566 567 /** 568 * Where in mLruProcesses that the processes hosting services start. 569 * This is after (lower index) than mLruProcessesActivityStart. 570 */ 571 int mLruProcessServiceStart = 0; 572 573 /** 574 * List of processes that should gc as soon as things are idle. 575 */ 576 final ArrayList<ProcessRecord> mProcessesToGc = new ArrayList<ProcessRecord>(); 577 578 /** 579 * Processes we want to collect PSS data from. 580 */ 581 final ArrayList<ProcessRecord> mPendingPssProcesses = new ArrayList<ProcessRecord>(); 582 583 /** 584 * Last time we requested PSS data of all processes. 585 */ 586 long mLastFullPssTime = SystemClock.uptimeMillis(); 587 588 /** 589 * If set, the next time we collect PSS data we should do a full collection 590 * with data from native processes and the kernel. 591 */ 592 boolean mFullPssPending = false; 593 594 /** 595 * This is the process holding what we currently consider to be 596 * the "home" activity. 597 */ 598 ProcessRecord mHomeProcess; 599 600 /** 601 * This is the process holding the activity the user last visited that 602 * is in a different process from the one they are currently in. 603 */ 604 ProcessRecord mPreviousProcess; 605 606 /** 607 * The time at which the previous process was last visible. 608 */ 609 long mPreviousProcessVisibleTime; 610 611 /** 612 * Which uses have been started, so are allowed to run code. 613 */ 614 final SparseArray<UserStartedState> mStartedUsers = new SparseArray<UserStartedState>(); 615 616 /** 617 * LRU list of history of current users. Most recently current is at the end. 618 */ 619 final ArrayList<Integer> mUserLru = new ArrayList<Integer>(); 620 621 /** 622 * Constant array of the users that are currently started. 623 */ 624 int[] mStartedUserArray = new int[] { 0 }; 625 626 /** 627 * Registered observers of the user switching mechanics. 628 */ 629 final RemoteCallbackList<IUserSwitchObserver> mUserSwitchObservers 630 = new RemoteCallbackList<IUserSwitchObserver>(); 631 632 /** 633 * Currently active user switch. 634 */ 635 Object mCurUserSwitchCallback; 636 637 /** 638 * Packages that the user has asked to have run in screen size 639 * compatibility mode instead of filling the screen. 640 */ 641 final CompatModePackages mCompatModePackages; 642 643 /** 644 * Set of IntentSenderRecord objects that are currently active. 645 */ 646 final HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>> mIntentSenderRecords 647 = new HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>>(); 648 649 /** 650 * Fingerprints (hashCode()) of stack traces that we've 651 * already logged DropBox entries for. Guarded by itself. If 652 * something (rogue user app) forces this over 653 * MAX_DUP_SUPPRESSED_STACKS entries, the contents are cleared. 654 */ 655 private final HashSet<Integer> mAlreadyLoggedViolatedStacks = new HashSet<Integer>(); 656 private static final int MAX_DUP_SUPPRESSED_STACKS = 5000; 657 658 /** 659 * Strict Mode background batched logging state. 660 * 661 * The string buffer is guarded by itself, and its lock is also 662 * used to determine if another batched write is already 663 * in-flight. 664 */ 665 private final StringBuilder mStrictModeBuffer = new StringBuilder(); 666 667 /** 668 * Keeps track of all IIntentReceivers that have been registered for 669 * broadcasts. Hash keys are the receiver IBinder, hash value is 670 * a ReceiverList. 671 */ 672 final HashMap<IBinder, ReceiverList> mRegisteredReceivers = 673 new HashMap<IBinder, ReceiverList>(); 674 675 /** 676 * Resolver for broadcast intents to registered receivers. 677 * Holds BroadcastFilter (subclass of IntentFilter). 678 */ 679 final IntentResolver<BroadcastFilter, BroadcastFilter> mReceiverResolver 680 = new IntentResolver<BroadcastFilter, BroadcastFilter>() { 681 @Override 682 protected boolean allowFilterResult( 683 BroadcastFilter filter, List<BroadcastFilter> dest) { 684 IBinder target = filter.receiverList.receiver.asBinder(); 685 for (int i=dest.size()-1; i>=0; i--) { 686 if (dest.get(i).receiverList.receiver.asBinder() == target) { 687 return false; 688 } 689 } 690 return true; 691 } 692 693 @Override 694 protected BroadcastFilter newResult(BroadcastFilter filter, int match, int userId) { 695 if (userId == UserHandle.USER_ALL || filter.owningUserId == UserHandle.USER_ALL 696 || userId == filter.owningUserId) { 697 return super.newResult(filter, match, userId); 698 } 699 return null; 700 } 701 702 @Override 703 protected BroadcastFilter[] newArray(int size) { 704 return new BroadcastFilter[size]; 705 } 706 707 @Override 708 protected boolean isPackageForFilter(String packageName, BroadcastFilter filter) { 709 return packageName.equals(filter.packageName); 710 } 711 }; 712 713 /** 714 * State of all active sticky broadcasts per user. Keys are the action of the 715 * sticky Intent, values are an ArrayList of all broadcasted intents with 716 * that action (which should usually be one). The SparseArray is keyed 717 * by the user ID the sticky is for, and can include UserHandle.USER_ALL 718 * for stickies that are sent to all users. 719 */ 720 final SparseArray<ArrayMap<String, ArrayList<Intent>>> mStickyBroadcasts = 721 new SparseArray<ArrayMap<String, ArrayList<Intent>>>(); 722 723 final ActiveServices mServices; 724 725 /** 726 * Backup/restore process management 727 */ 728 String mBackupAppName = null; 729 BackupRecord mBackupTarget = null; 730 731 final ProviderMap mProviderMap; 732 733 /** 734 * List of content providers who have clients waiting for them. The 735 * application is currently being launched and the provider will be 736 * removed from this list once it is published. 737 */ 738 final ArrayList<ContentProviderRecord> mLaunchingProviders 739 = new ArrayList<ContentProviderRecord>(); 740 741 /** 742 * File storing persisted {@link #mGrantedUriPermissions}. 743 */ 744 private final AtomicFile mGrantFile; 745 746 /** XML constants used in {@link #mGrantFile} */ 747 private static final String TAG_URI_GRANTS = "uri-grants"; 748 private static final String TAG_URI_GRANT = "uri-grant"; 749 private static final String ATTR_USER_HANDLE = "userHandle"; 750 private static final String ATTR_SOURCE_USER_ID = "sourceUserId"; 751 private static final String ATTR_TARGET_USER_ID = "targetUserId"; 752 private static final String ATTR_SOURCE_PKG = "sourcePkg"; 753 private static final String ATTR_TARGET_PKG = "targetPkg"; 754 private static final String ATTR_URI = "uri"; 755 private static final String ATTR_MODE_FLAGS = "modeFlags"; 756 private static final String ATTR_CREATED_TIME = "createdTime"; 757 private static final String ATTR_PREFIX = "prefix"; 758 759 /** 760 * Global set of specific {@link Uri} permissions that have been granted. 761 * This optimized lookup structure maps from {@link UriPermission#targetUid} 762 * to {@link UriPermission#uri} to {@link UriPermission}. 763 */ 764 @GuardedBy("this") 765 private final SparseArray<ArrayMap<GrantUri, UriPermission>> 766 mGrantedUriPermissions = new SparseArray<ArrayMap<GrantUri, UriPermission>>(); 767 768 public static class GrantUri { 769 public final int sourceUserId; 770 public final Uri uri; 771 public boolean prefix; 772 773 public GrantUri(int sourceUserId, Uri uri, boolean prefix) { 774 this.sourceUserId = sourceUserId; 775 this.uri = uri; 776 this.prefix = prefix; 777 } 778 779 @Override 780 public int hashCode() { 781 return toString().hashCode(); 782 } 783 784 @Override 785 public boolean equals(Object o) { 786 if (o instanceof GrantUri) { 787 GrantUri other = (GrantUri) o; 788 return uri.equals(other.uri) && (sourceUserId == other.sourceUserId) 789 && prefix == other.prefix; 790 } 791 return false; 792 } 793 794 @Override 795 public String toString() { 796 String result = Integer.toString(sourceUserId) + " @ " + uri.toString(); 797 if (prefix) result += " [prefix]"; 798 return result; 799 } 800 801 public String toSafeString() { 802 String result = Integer.toString(sourceUserId) + " @ " + uri.toSafeString(); 803 if (prefix) result += " [prefix]"; 804 return result; 805 } 806 807 public static GrantUri resolve(int defaultSourceUserHandle, Uri uri) { 808 return new GrantUri(ContentProvider.getUserIdFromUri(uri, defaultSourceUserHandle), 809 ContentProvider.getUriWithoutUserId(uri), false); 810 } 811 } 812 813 CoreSettingsObserver mCoreSettingsObserver; 814 815 /** 816 * Thread-local storage used to carry caller permissions over through 817 * indirect content-provider access. 818 */ 819 private class Identity { 820 public int pid; 821 public int uid; 822 823 Identity(int _pid, int _uid) { 824 pid = _pid; 825 uid = _uid; 826 } 827 } 828 829 private static final ThreadLocal<Identity> sCallerIdentity = new ThreadLocal<Identity>(); 830 831 /** 832 * All information we have collected about the runtime performance of 833 * any user id that can impact battery performance. 834 */ 835 final BatteryStatsService mBatteryStatsService; 836 837 /** 838 * Information about component usage 839 */ 840 UsageStatsManagerInternal mUsageStatsService; 841 842 /** 843 * Information about and control over application operations 844 */ 845 final AppOpsService mAppOpsService; 846 847 /** 848 * Save recent tasks information across reboots. 849 */ 850 final TaskPersister mTaskPersister; 851 852 /** 853 * Current configuration information. HistoryRecord objects are given 854 * a reference to this object to indicate which configuration they are 855 * currently running in, so this object must be kept immutable. 856 */ 857 Configuration mConfiguration = new Configuration(); 858 859 /** 860 * Current sequencing integer of the configuration, for skipping old 861 * configurations. 862 */ 863 int mConfigurationSeq = 0; 864 865 /** 866 * Hardware-reported OpenGLES version. 867 */ 868 final int GL_ES_VERSION; 869 870 /** 871 * List of initialization arguments to pass to all processes when binding applications to them. 872 * For example, references to the commonly used services. 873 */ 874 HashMap<String, IBinder> mAppBindArgs; 875 876 /** 877 * Temporary to avoid allocations. Protected by main lock. 878 */ 879 final StringBuilder mStringBuilder = new StringBuilder(256); 880 881 /** 882 * Used to control how we initialize the service. 883 */ 884 ComponentName mTopComponent; 885 String mTopAction = Intent.ACTION_MAIN; 886 String mTopData; 887 boolean mProcessesReady = false; 888 boolean mSystemReady = false; 889 boolean mBooting = false; 890 boolean mWaitingUpdate = false; 891 boolean mDidUpdate = false; 892 boolean mOnBattery = false; 893 boolean mLaunchWarningShown = false; 894 895 Context mContext; 896 897 int mFactoryTest; 898 899 boolean mCheckedForSetup; 900 901 /** 902 * The time at which we will allow normal application switches again, 903 * after a call to {@link #stopAppSwitches()}. 904 */ 905 long mAppSwitchesAllowedTime; 906 907 /** 908 * This is set to true after the first switch after mAppSwitchesAllowedTime 909 * is set; any switches after that will clear the time. 910 */ 911 boolean mDidAppSwitch; 912 913 /** 914 * Last time (in realtime) at which we checked for power usage. 915 */ 916 long mLastPowerCheckRealtime; 917 918 /** 919 * Last time (in uptime) at which we checked for power usage. 920 */ 921 long mLastPowerCheckUptime; 922 923 /** 924 * Set while we are wanting to sleep, to prevent any 925 * activities from being started/resumed. 926 */ 927 private boolean mSleeping = false; 928 929 /** 930 * Set while we are running a voice interaction. This overrides 931 * sleeping while it is active. 932 */ 933 private boolean mRunningVoice = false; 934 935 /** 936 * State of external calls telling us if the device is asleep. 937 */ 938 private boolean mWentToSleep = false; 939 940 /** 941 * State of external call telling us if the lock screen is shown. 942 */ 943 private boolean mLockScreenShown = false; 944 945 /** 946 * Set if we are shutting down the system, similar to sleeping. 947 */ 948 boolean mShuttingDown = false; 949 950 /** 951 * Current sequence id for oom_adj computation traversal. 952 */ 953 int mAdjSeq = 0; 954 955 /** 956 * Current sequence id for process LRU updating. 957 */ 958 int mLruSeq = 0; 959 960 /** 961 * Keep track of the non-cached/empty process we last found, to help 962 * determine how to distribute cached/empty processes next time. 963 */ 964 int mNumNonCachedProcs = 0; 965 966 /** 967 * Keep track of the number of cached hidden procs, to balance oom adj 968 * distribution between those and empty procs. 969 */ 970 int mNumCachedHiddenProcs = 0; 971 972 /** 973 * Keep track of the number of service processes we last found, to 974 * determine on the next iteration which should be B services. 975 */ 976 int mNumServiceProcs = 0; 977 int mNewNumAServiceProcs = 0; 978 int mNewNumServiceProcs = 0; 979 980 /** 981 * Allow the current computed overall memory level of the system to go down? 982 * This is set to false when we are killing processes for reasons other than 983 * memory management, so that the now smaller process list will not be taken as 984 * an indication that memory is tighter. 985 */ 986 boolean mAllowLowerMemLevel = false; 987 988 /** 989 * The last computed memory level, for holding when we are in a state that 990 * processes are going away for other reasons. 991 */ 992 int mLastMemoryLevel = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 993 994 /** 995 * The last total number of process we have, to determine if changes actually look 996 * like a shrinking number of process due to lower RAM. 997 */ 998 int mLastNumProcesses; 999 1000 /** 1001 * The uptime of the last time we performed idle maintenance. 1002 */ 1003 long mLastIdleTime = SystemClock.uptimeMillis(); 1004 1005 /** 1006 * Total time spent with RAM that has been added in the past since the last idle time. 1007 */ 1008 long mLowRamTimeSinceLastIdle = 0; 1009 1010 /** 1011 * If RAM is currently low, when that horrible situation started. 1012 */ 1013 long mLowRamStartTime = 0; 1014 1015 /** 1016 * For reporting to battery stats the current top application. 1017 */ 1018 private String mCurResumedPackage = null; 1019 private int mCurResumedUid = -1; 1020 1021 /** 1022 * For reporting to battery stats the apps currently running foreground 1023 * service. The ProcessMap is package/uid tuples; each of these contain 1024 * an array of the currently foreground processes. 1025 */ 1026 final ProcessMap<ArrayList<ProcessRecord>> mForegroundPackages 1027 = new ProcessMap<ArrayList<ProcessRecord>>(); 1028 1029 /** 1030 * This is set if we had to do a delayed dexopt of an app before launching 1031 * it, to increase the ANR timeouts in that case. 1032 */ 1033 boolean mDidDexOpt; 1034 1035 /** 1036 * Set if the systemServer made a call to enterSafeMode. 1037 */ 1038 boolean mSafeMode; 1039 1040 String mDebugApp = null; 1041 boolean mWaitForDebugger = false; 1042 boolean mDebugTransient = false; 1043 String mOrigDebugApp = null; 1044 boolean mOrigWaitForDebugger = false; 1045 boolean mAlwaysFinishActivities = false; 1046 IActivityController mController = null; 1047 String mProfileApp = null; 1048 ProcessRecord mProfileProc = null; 1049 String mProfileFile; 1050 ParcelFileDescriptor mProfileFd; 1051 int mSamplingInterval = 0; 1052 boolean mAutoStopProfiler = false; 1053 int mProfileType = 0; 1054 String mOpenGlTraceApp = null; 1055 1056 static class ProcessChangeItem { 1057 static final int CHANGE_ACTIVITIES = 1<<0; 1058 static final int CHANGE_PROCESS_STATE = 1<<1; 1059 int changes; 1060 int uid; 1061 int pid; 1062 int processState; 1063 boolean foregroundActivities; 1064 } 1065 1066 final RemoteCallbackList<IProcessObserver> mProcessObservers 1067 = new RemoteCallbackList<IProcessObserver>(); 1068 ProcessChangeItem[] mActiveProcessChanges = new ProcessChangeItem[5]; 1069 1070 final ArrayList<ProcessChangeItem> mPendingProcessChanges 1071 = new ArrayList<ProcessChangeItem>(); 1072 final ArrayList<ProcessChangeItem> mAvailProcessChanges 1073 = new ArrayList<ProcessChangeItem>(); 1074 1075 /** 1076 * Runtime CPU use collection thread. This object's lock is used to 1077 * protect all related state. 1078 */ 1079 final Thread mProcessCpuThread; 1080 1081 /** 1082 * Used to collect process stats when showing not responding dialog. 1083 * Protected by mProcessCpuThread. 1084 */ 1085 final ProcessCpuTracker mProcessCpuTracker = new ProcessCpuTracker( 1086 MONITOR_THREAD_CPU_USAGE); 1087 final AtomicLong mLastCpuTime = new AtomicLong(0); 1088 final AtomicBoolean mProcessCpuMutexFree = new AtomicBoolean(true); 1089 1090 long mLastWriteTime = 0; 1091 1092 /** 1093 * Used to retain an update lock when the foreground activity is in 1094 * immersive mode. 1095 */ 1096 final UpdateLock mUpdateLock = new UpdateLock("immersive"); 1097 1098 /** 1099 * Set to true after the system has finished booting. 1100 */ 1101 boolean mBooted = false; 1102 1103 int mProcessLimit = ProcessList.MAX_CACHED_APPS; 1104 int mProcessLimitOverride = -1; 1105 1106 WindowManagerService mWindowManager; 1107 1108 final ActivityThread mSystemThread; 1109 1110 int mCurrentUserId = 0; 1111 int[] mCurrentProfileIds = new int[] {UserHandle.USER_OWNER}; // Accessed by ActivityStack 1112 1113 /** 1114 * Mapping from each known user ID to the profile group ID it is associated with. 1115 */ 1116 SparseIntArray mUserProfileGroupIdsSelfLocked = new SparseIntArray(); 1117 1118 private UserManagerService mUserManager; 1119 1120 private final class AppDeathRecipient implements IBinder.DeathRecipient { 1121 final ProcessRecord mApp; 1122 final int mPid; 1123 final IApplicationThread mAppThread; 1124 1125 AppDeathRecipient(ProcessRecord app, int pid, 1126 IApplicationThread thread) { 1127 if (localLOGV) Slog.v( 1128 TAG, "New death recipient " + this 1129 + " for thread " + thread.asBinder()); 1130 mApp = app; 1131 mPid = pid; 1132 mAppThread = thread; 1133 } 1134 1135 @Override 1136 public void binderDied() { 1137 if (localLOGV) Slog.v( 1138 TAG, "Death received in " + this 1139 + " for thread " + mAppThread.asBinder()); 1140 synchronized(ActivityManagerService.this) { 1141 appDiedLocked(mApp, mPid, mAppThread); 1142 } 1143 } 1144 } 1145 1146 static final int SHOW_ERROR_MSG = 1; 1147 static final int SHOW_NOT_RESPONDING_MSG = 2; 1148 static final int SHOW_FACTORY_ERROR_MSG = 3; 1149 static final int UPDATE_CONFIGURATION_MSG = 4; 1150 static final int GC_BACKGROUND_PROCESSES_MSG = 5; 1151 static final int WAIT_FOR_DEBUGGER_MSG = 6; 1152 static final int SERVICE_TIMEOUT_MSG = 12; 1153 static final int UPDATE_TIME_ZONE = 13; 1154 static final int SHOW_UID_ERROR_MSG = 14; 1155 static final int IM_FEELING_LUCKY_MSG = 15; 1156 static final int PROC_START_TIMEOUT_MSG = 20; 1157 static final int DO_PENDING_ACTIVITY_LAUNCHES_MSG = 21; 1158 static final int KILL_APPLICATION_MSG = 22; 1159 static final int FINALIZE_PENDING_INTENT_MSG = 23; 1160 static final int POST_HEAVY_NOTIFICATION_MSG = 24; 1161 static final int CANCEL_HEAVY_NOTIFICATION_MSG = 25; 1162 static final int SHOW_STRICT_MODE_VIOLATION_MSG = 26; 1163 static final int CHECK_EXCESSIVE_WAKE_LOCKS_MSG = 27; 1164 static final int CLEAR_DNS_CACHE_MSG = 28; 1165 static final int UPDATE_HTTP_PROXY_MSG = 29; 1166 static final int SHOW_COMPAT_MODE_DIALOG_MSG = 30; 1167 static final int DISPATCH_PROCESSES_CHANGED = 31; 1168 static final int DISPATCH_PROCESS_DIED = 32; 1169 static final int REPORT_MEM_USAGE_MSG = 33; 1170 static final int REPORT_USER_SWITCH_MSG = 34; 1171 static final int CONTINUE_USER_SWITCH_MSG = 35; 1172 static final int USER_SWITCH_TIMEOUT_MSG = 36; 1173 static final int IMMERSIVE_MODE_LOCK_MSG = 37; 1174 static final int PERSIST_URI_GRANTS_MSG = 38; 1175 static final int REQUEST_ALL_PSS_MSG = 39; 1176 static final int START_PROFILES_MSG = 40; 1177 static final int UPDATE_TIME = 41; 1178 static final int SYSTEM_USER_START_MSG = 42; 1179 static final int SYSTEM_USER_CURRENT_MSG = 43; 1180 static final int ENTER_ANIMATION_COMPLETE_MSG = 44; 1181 static final int ENABLE_SCREEN_AFTER_BOOT_MSG = 45; 1182 static final int START_USER_SWITCH_MSG = 46; 1183 1184 static final int FIRST_ACTIVITY_STACK_MSG = 100; 1185 static final int FIRST_BROADCAST_QUEUE_MSG = 200; 1186 static final int FIRST_COMPAT_MODE_MSG = 300; 1187 static final int FIRST_SUPERVISOR_STACK_MSG = 100; 1188 1189 AlertDialog mUidAlert; 1190 CompatModeDialog mCompatModeDialog; 1191 long mLastMemUsageReportTime = 0; 1192 1193 private LockToAppRequestDialog mLockToAppRequest; 1194 1195 /** 1196 * Flag whether the current user is a "monkey", i.e. whether 1197 * the UI is driven by a UI automation tool. 1198 */ 1199 private boolean mUserIsMonkey; 1200 1201 /** Flag whether the device has a Recents UI */ 1202 boolean mHasRecents; 1203 1204 /** The dimensions of the thumbnails in the Recents UI. */ 1205 int mThumbnailWidth; 1206 int mThumbnailHeight; 1207 1208 final ServiceThread mHandlerThread; 1209 final MainHandler mHandler; 1210 1211 final class MainHandler extends Handler { 1212 public MainHandler(Looper looper) { 1213 super(looper, null, true); 1214 } 1215 1216 @Override 1217 public void handleMessage(Message msg) { 1218 switch (msg.what) { 1219 case SHOW_ERROR_MSG: { 1220 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1221 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 1222 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 1223 synchronized (ActivityManagerService.this) { 1224 ProcessRecord proc = (ProcessRecord)data.get("app"); 1225 AppErrorResult res = (AppErrorResult) data.get("result"); 1226 if (proc != null && proc.crashDialog != null) { 1227 Slog.e(TAG, "App already has crash dialog: " + proc); 1228 if (res != null) { 1229 res.set(0); 1230 } 1231 return; 1232 } 1233 boolean isBackground = (UserHandle.getAppId(proc.uid) 1234 >= Process.FIRST_APPLICATION_UID 1235 && proc.pid != MY_PID); 1236 for (int userId : mCurrentProfileIds) { 1237 isBackground &= (proc.userId != userId); 1238 } 1239 if (isBackground && !showBackground) { 1240 Slog.w(TAG, "Skipping crash dialog of " + proc + ": background"); 1241 if (res != null) { 1242 res.set(0); 1243 } 1244 return; 1245 } 1246 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1247 Dialog d = new AppErrorDialog(mContext, 1248 ActivityManagerService.this, res, proc); 1249 d.show(); 1250 proc.crashDialog = d; 1251 } else { 1252 // The device is asleep, so just pretend that the user 1253 // saw a crash dialog and hit "force quit". 1254 if (res != null) { 1255 res.set(0); 1256 } 1257 } 1258 } 1259 1260 ensureBootCompleted(); 1261 } break; 1262 case SHOW_NOT_RESPONDING_MSG: { 1263 synchronized (ActivityManagerService.this) { 1264 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1265 ProcessRecord proc = (ProcessRecord)data.get("app"); 1266 if (proc != null && proc.anrDialog != null) { 1267 Slog.e(TAG, "App already has anr dialog: " + proc); 1268 return; 1269 } 1270 1271 Intent intent = new Intent("android.intent.action.ANR"); 1272 if (!mProcessesReady) { 1273 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 1274 | Intent.FLAG_RECEIVER_FOREGROUND); 1275 } 1276 broadcastIntentLocked(null, null, intent, 1277 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 1278 false, false, MY_PID, Process.SYSTEM_UID, 0 /* TODO: Verify */); 1279 1280 if (mShowDialogs) { 1281 Dialog d = new AppNotRespondingDialog(ActivityManagerService.this, 1282 mContext, proc, (ActivityRecord)data.get("activity"), 1283 msg.arg1 != 0); 1284 d.show(); 1285 proc.anrDialog = d; 1286 } else { 1287 // Just kill the app if there is no dialog to be shown. 1288 killAppAtUsersRequest(proc, null); 1289 } 1290 } 1291 1292 ensureBootCompleted(); 1293 } break; 1294 case SHOW_STRICT_MODE_VIOLATION_MSG: { 1295 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1296 synchronized (ActivityManagerService.this) { 1297 ProcessRecord proc = (ProcessRecord) data.get("app"); 1298 if (proc == null) { 1299 Slog.e(TAG, "App not found when showing strict mode dialog."); 1300 break; 1301 } 1302 if (proc.crashDialog != null) { 1303 Slog.e(TAG, "App already has strict mode dialog: " + proc); 1304 return; 1305 } 1306 AppErrorResult res = (AppErrorResult) data.get("result"); 1307 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1308 Dialog d = new StrictModeViolationDialog(mContext, 1309 ActivityManagerService.this, res, proc); 1310 d.show(); 1311 proc.crashDialog = d; 1312 } else { 1313 // The device is asleep, so just pretend that the user 1314 // saw a crash dialog and hit "force quit". 1315 res.set(0); 1316 } 1317 } 1318 ensureBootCompleted(); 1319 } break; 1320 case SHOW_FACTORY_ERROR_MSG: { 1321 Dialog d = new FactoryErrorDialog( 1322 mContext, msg.getData().getCharSequence("msg")); 1323 d.show(); 1324 ensureBootCompleted(); 1325 } break; 1326 case UPDATE_CONFIGURATION_MSG: { 1327 final ContentResolver resolver = mContext.getContentResolver(); 1328 Settings.System.putConfiguration(resolver, (Configuration)msg.obj); 1329 } break; 1330 case GC_BACKGROUND_PROCESSES_MSG: { 1331 synchronized (ActivityManagerService.this) { 1332 performAppGcsIfAppropriateLocked(); 1333 } 1334 } break; 1335 case WAIT_FOR_DEBUGGER_MSG: { 1336 synchronized (ActivityManagerService.this) { 1337 ProcessRecord app = (ProcessRecord)msg.obj; 1338 if (msg.arg1 != 0) { 1339 if (!app.waitedForDebugger) { 1340 Dialog d = new AppWaitingForDebuggerDialog( 1341 ActivityManagerService.this, 1342 mContext, app); 1343 app.waitDialog = d; 1344 app.waitedForDebugger = true; 1345 d.show(); 1346 } 1347 } else { 1348 if (app.waitDialog != null) { 1349 app.waitDialog.dismiss(); 1350 app.waitDialog = null; 1351 } 1352 } 1353 } 1354 } break; 1355 case SERVICE_TIMEOUT_MSG: { 1356 if (mDidDexOpt) { 1357 mDidDexOpt = false; 1358 Message nmsg = mHandler.obtainMessage(SERVICE_TIMEOUT_MSG); 1359 nmsg.obj = msg.obj; 1360 mHandler.sendMessageDelayed(nmsg, ActiveServices.SERVICE_TIMEOUT); 1361 return; 1362 } 1363 mServices.serviceTimeout((ProcessRecord)msg.obj); 1364 } break; 1365 case UPDATE_TIME_ZONE: { 1366 synchronized (ActivityManagerService.this) { 1367 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1368 ProcessRecord r = mLruProcesses.get(i); 1369 if (r.thread != null) { 1370 try { 1371 r.thread.updateTimeZone(); 1372 } catch (RemoteException ex) { 1373 Slog.w(TAG, "Failed to update time zone for: " + r.info.processName); 1374 } 1375 } 1376 } 1377 } 1378 } break; 1379 case CLEAR_DNS_CACHE_MSG: { 1380 synchronized (ActivityManagerService.this) { 1381 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1382 ProcessRecord r = mLruProcesses.get(i); 1383 if (r.thread != null) { 1384 try { 1385 r.thread.clearDnsCache(); 1386 } catch (RemoteException ex) { 1387 Slog.w(TAG, "Failed to clear dns cache for: " + r.info.processName); 1388 } 1389 } 1390 } 1391 } 1392 } break; 1393 case UPDATE_HTTP_PROXY_MSG: { 1394 ProxyInfo proxy = (ProxyInfo)msg.obj; 1395 String host = ""; 1396 String port = ""; 1397 String exclList = ""; 1398 Uri pacFileUrl = Uri.EMPTY; 1399 if (proxy != null) { 1400 host = proxy.getHost(); 1401 port = Integer.toString(proxy.getPort()); 1402 exclList = proxy.getExclusionListAsString(); 1403 pacFileUrl = proxy.getPacFileUrl(); 1404 } 1405 synchronized (ActivityManagerService.this) { 1406 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1407 ProcessRecord r = mLruProcesses.get(i); 1408 if (r.thread != null) { 1409 try { 1410 r.thread.setHttpProxy(host, port, exclList, pacFileUrl); 1411 } catch (RemoteException ex) { 1412 Slog.w(TAG, "Failed to update http proxy for: " + 1413 r.info.processName); 1414 } 1415 } 1416 } 1417 } 1418 } break; 1419 case SHOW_UID_ERROR_MSG: { 1420 String title = "System UIDs Inconsistent"; 1421 String text = "UIDs on the system are inconsistent, you need to wipe your" 1422 + " data partition or your device will be unstable."; 1423 Log.e(TAG, title + ": " + text); 1424 if (mShowDialogs) { 1425 // XXX This is a temporary dialog, no need to localize. 1426 AlertDialog d = new BaseErrorDialog(mContext); 1427 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 1428 d.setCancelable(false); 1429 d.setTitle(title); 1430 d.setMessage(text); 1431 d.setButton(DialogInterface.BUTTON_POSITIVE, "I'm Feeling Lucky", 1432 mHandler.obtainMessage(IM_FEELING_LUCKY_MSG)); 1433 mUidAlert = d; 1434 d.show(); 1435 } 1436 } break; 1437 case IM_FEELING_LUCKY_MSG: { 1438 if (mUidAlert != null) { 1439 mUidAlert.dismiss(); 1440 mUidAlert = null; 1441 } 1442 } break; 1443 case PROC_START_TIMEOUT_MSG: { 1444 if (mDidDexOpt) { 1445 mDidDexOpt = false; 1446 Message nmsg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 1447 nmsg.obj = msg.obj; 1448 mHandler.sendMessageDelayed(nmsg, PROC_START_TIMEOUT); 1449 return; 1450 } 1451 ProcessRecord app = (ProcessRecord)msg.obj; 1452 synchronized (ActivityManagerService.this) { 1453 processStartTimedOutLocked(app); 1454 } 1455 } break; 1456 case DO_PENDING_ACTIVITY_LAUNCHES_MSG: { 1457 synchronized (ActivityManagerService.this) { 1458 mStackSupervisor.doPendingActivityLaunchesLocked(true); 1459 } 1460 } break; 1461 case KILL_APPLICATION_MSG: { 1462 synchronized (ActivityManagerService.this) { 1463 int appid = msg.arg1; 1464 boolean restart = (msg.arg2 == 1); 1465 Bundle bundle = (Bundle)msg.obj; 1466 String pkg = bundle.getString("pkg"); 1467 String reason = bundle.getString("reason"); 1468 forceStopPackageLocked(pkg, appid, restart, false, true, false, 1469 false, UserHandle.USER_ALL, reason); 1470 } 1471 } break; 1472 case FINALIZE_PENDING_INTENT_MSG: { 1473 ((PendingIntentRecord)msg.obj).completeFinalize(); 1474 } break; 1475 case POST_HEAVY_NOTIFICATION_MSG: { 1476 INotificationManager inm = NotificationManager.getService(); 1477 if (inm == null) { 1478 return; 1479 } 1480 1481 ActivityRecord root = (ActivityRecord)msg.obj; 1482 ProcessRecord process = root.app; 1483 if (process == null) { 1484 return; 1485 } 1486 1487 try { 1488 Context context = mContext.createPackageContext(process.info.packageName, 0); 1489 String text = mContext.getString(R.string.heavy_weight_notification, 1490 context.getApplicationInfo().loadLabel(context.getPackageManager())); 1491 Notification notification = new Notification(); 1492 notification.icon = com.android.internal.R.drawable.stat_sys_adb; //context.getApplicationInfo().icon; 1493 notification.when = 0; 1494 notification.flags = Notification.FLAG_ONGOING_EVENT; 1495 notification.tickerText = text; 1496 notification.defaults = 0; // please be quiet 1497 notification.sound = null; 1498 notification.vibrate = null; 1499 notification.color = mContext.getResources().getColor( 1500 com.android.internal.R.color.system_notification_accent_color); 1501 notification.setLatestEventInfo(context, text, 1502 mContext.getText(R.string.heavy_weight_notification_detail), 1503 PendingIntent.getActivityAsUser(mContext, 0, root.intent, 1504 PendingIntent.FLAG_CANCEL_CURRENT, null, 1505 new UserHandle(root.userId))); 1506 1507 try { 1508 int[] outId = new int[1]; 1509 inm.enqueueNotificationWithTag("android", "android", null, 1510 R.string.heavy_weight_notification, 1511 notification, outId, root.userId); 1512 } catch (RuntimeException e) { 1513 Slog.w(ActivityManagerService.TAG, 1514 "Error showing notification for heavy-weight app", e); 1515 } catch (RemoteException e) { 1516 } 1517 } catch (NameNotFoundException e) { 1518 Slog.w(TAG, "Unable to create context for heavy notification", e); 1519 } 1520 } break; 1521 case CANCEL_HEAVY_NOTIFICATION_MSG: { 1522 INotificationManager inm = NotificationManager.getService(); 1523 if (inm == null) { 1524 return; 1525 } 1526 try { 1527 inm.cancelNotificationWithTag("android", null, 1528 R.string.heavy_weight_notification, msg.arg1); 1529 } catch (RuntimeException e) { 1530 Slog.w(ActivityManagerService.TAG, 1531 "Error canceling notification for service", e); 1532 } catch (RemoteException e) { 1533 } 1534 } break; 1535 case CHECK_EXCESSIVE_WAKE_LOCKS_MSG: { 1536 synchronized (ActivityManagerService.this) { 1537 checkExcessivePowerUsageLocked(true); 1538 removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1539 Message nmsg = obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1540 sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 1541 } 1542 } break; 1543 case SHOW_COMPAT_MODE_DIALOG_MSG: { 1544 synchronized (ActivityManagerService.this) { 1545 ActivityRecord ar = (ActivityRecord)msg.obj; 1546 if (mCompatModeDialog != null) { 1547 if (mCompatModeDialog.mAppInfo.packageName.equals( 1548 ar.info.applicationInfo.packageName)) { 1549 return; 1550 } 1551 mCompatModeDialog.dismiss(); 1552 mCompatModeDialog = null; 1553 } 1554 if (ar != null && false) { 1555 if (mCompatModePackages.getPackageAskCompatModeLocked( 1556 ar.packageName)) { 1557 int mode = mCompatModePackages.computeCompatModeLocked( 1558 ar.info.applicationInfo); 1559 if (mode == ActivityManager.COMPAT_MODE_DISABLED 1560 || mode == ActivityManager.COMPAT_MODE_ENABLED) { 1561 mCompatModeDialog = new CompatModeDialog( 1562 ActivityManagerService.this, mContext, 1563 ar.info.applicationInfo); 1564 mCompatModeDialog.show(); 1565 } 1566 } 1567 } 1568 } 1569 break; 1570 } 1571 case DISPATCH_PROCESSES_CHANGED: { 1572 dispatchProcessesChanged(); 1573 break; 1574 } 1575 case DISPATCH_PROCESS_DIED: { 1576 final int pid = msg.arg1; 1577 final int uid = msg.arg2; 1578 dispatchProcessDied(pid, uid); 1579 break; 1580 } 1581 case REPORT_MEM_USAGE_MSG: { 1582 final ArrayList<ProcessMemInfo> memInfos = (ArrayList<ProcessMemInfo>)msg.obj; 1583 Thread thread = new Thread() { 1584 @Override public void run() { 1585 final SparseArray<ProcessMemInfo> infoMap 1586 = new SparseArray<ProcessMemInfo>(memInfos.size()); 1587 for (int i=0, N=memInfos.size(); i<N; i++) { 1588 ProcessMemInfo mi = memInfos.get(i); 1589 infoMap.put(mi.pid, mi); 1590 } 1591 updateCpuStatsNow(); 1592 synchronized (mProcessCpuThread) { 1593 final int N = mProcessCpuTracker.countStats(); 1594 for (int i=0; i<N; i++) { 1595 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 1596 if (st.vsize > 0) { 1597 long pss = Debug.getPss(st.pid, null); 1598 if (pss > 0) { 1599 if (infoMap.indexOfKey(st.pid) < 0) { 1600 ProcessMemInfo mi = new ProcessMemInfo(st.name, st.pid, 1601 ProcessList.NATIVE_ADJ, -1, "native", null); 1602 mi.pss = pss; 1603 memInfos.add(mi); 1604 } 1605 } 1606 } 1607 } 1608 } 1609 1610 long totalPss = 0; 1611 for (int i=0, N=memInfos.size(); i<N; i++) { 1612 ProcessMemInfo mi = memInfos.get(i); 1613 if (mi.pss == 0) { 1614 mi.pss = Debug.getPss(mi.pid, null); 1615 } 1616 totalPss += mi.pss; 1617 } 1618 Collections.sort(memInfos, new Comparator<ProcessMemInfo>() { 1619 @Override public int compare(ProcessMemInfo lhs, ProcessMemInfo rhs) { 1620 if (lhs.oomAdj != rhs.oomAdj) { 1621 return lhs.oomAdj < rhs.oomAdj ? -1 : 1; 1622 } 1623 if (lhs.pss != rhs.pss) { 1624 return lhs.pss < rhs.pss ? 1 : -1; 1625 } 1626 return 0; 1627 } 1628 }); 1629 1630 StringBuilder tag = new StringBuilder(128); 1631 StringBuilder stack = new StringBuilder(128); 1632 tag.append("Low on memory -- "); 1633 appendMemBucket(tag, totalPss, "total", false); 1634 appendMemBucket(stack, totalPss, "total", true); 1635 1636 StringBuilder logBuilder = new StringBuilder(1024); 1637 logBuilder.append("Low on memory:\n"); 1638 1639 boolean firstLine = true; 1640 int lastOomAdj = Integer.MIN_VALUE; 1641 for (int i=0, N=memInfos.size(); i<N; i++) { 1642 ProcessMemInfo mi = memInfos.get(i); 1643 1644 if (mi.oomAdj != ProcessList.NATIVE_ADJ 1645 && (mi.oomAdj < ProcessList.SERVICE_ADJ 1646 || mi.oomAdj == ProcessList.HOME_APP_ADJ 1647 || mi.oomAdj == ProcessList.PREVIOUS_APP_ADJ)) { 1648 if (lastOomAdj != mi.oomAdj) { 1649 lastOomAdj = mi.oomAdj; 1650 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1651 tag.append(" / "); 1652 } 1653 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ) { 1654 if (firstLine) { 1655 stack.append(":"); 1656 firstLine = false; 1657 } 1658 stack.append("\n\t at "); 1659 } else { 1660 stack.append("$"); 1661 } 1662 } else { 1663 tag.append(" "); 1664 stack.append("$"); 1665 } 1666 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1667 appendMemBucket(tag, mi.pss, mi.name, false); 1668 } 1669 appendMemBucket(stack, mi.pss, mi.name, true); 1670 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ 1671 && ((i+1) >= N || memInfos.get(i+1).oomAdj != lastOomAdj)) { 1672 stack.append("("); 1673 for (int k=0; k<DUMP_MEM_OOM_ADJ.length; k++) { 1674 if (DUMP_MEM_OOM_ADJ[k] == mi.oomAdj) { 1675 stack.append(DUMP_MEM_OOM_LABEL[k]); 1676 stack.append(":"); 1677 stack.append(DUMP_MEM_OOM_ADJ[k]); 1678 } 1679 } 1680 stack.append(")"); 1681 } 1682 } 1683 1684 logBuilder.append(" "); 1685 logBuilder.append(ProcessList.makeOomAdjString(mi.oomAdj)); 1686 logBuilder.append(' '); 1687 logBuilder.append(ProcessList.makeProcStateString(mi.procState)); 1688 logBuilder.append(' '); 1689 ProcessList.appendRamKb(logBuilder, mi.pss); 1690 logBuilder.append(" kB: "); 1691 logBuilder.append(mi.name); 1692 logBuilder.append(" ("); 1693 logBuilder.append(mi.pid); 1694 logBuilder.append(") "); 1695 logBuilder.append(mi.adjType); 1696 logBuilder.append('\n'); 1697 if (mi.adjReason != null) { 1698 logBuilder.append(" "); 1699 logBuilder.append(mi.adjReason); 1700 logBuilder.append('\n'); 1701 } 1702 } 1703 1704 logBuilder.append(" "); 1705 ProcessList.appendRamKb(logBuilder, totalPss); 1706 logBuilder.append(" kB: TOTAL\n"); 1707 1708 long[] infos = new long[Debug.MEMINFO_COUNT]; 1709 Debug.getMemInfo(infos); 1710 logBuilder.append(" MemInfo: "); 1711 logBuilder.append(infos[Debug.MEMINFO_SLAB]).append(" kB slab, "); 1712 logBuilder.append(infos[Debug.MEMINFO_SHMEM]).append(" kB shmem, "); 1713 logBuilder.append(infos[Debug.MEMINFO_BUFFERS]).append(" kB buffers, "); 1714 logBuilder.append(infos[Debug.MEMINFO_CACHED]).append(" kB cached, "); 1715 logBuilder.append(infos[Debug.MEMINFO_FREE]).append(" kB free\n"); 1716 if (infos[Debug.MEMINFO_ZRAM_TOTAL] != 0) { 1717 logBuilder.append(" ZRAM: "); 1718 logBuilder.append(infos[Debug.MEMINFO_ZRAM_TOTAL]); 1719 logBuilder.append(" kB RAM, "); 1720 logBuilder.append(infos[Debug.MEMINFO_SWAP_TOTAL]); 1721 logBuilder.append(" kB swap total, "); 1722 logBuilder.append(infos[Debug.MEMINFO_SWAP_FREE]); 1723 logBuilder.append(" kB swap free\n"); 1724 } 1725 Slog.i(TAG, logBuilder.toString()); 1726 1727 StringBuilder dropBuilder = new StringBuilder(1024); 1728 /* 1729 StringWriter oomSw = new StringWriter(); 1730 PrintWriter oomPw = new FastPrintWriter(oomSw, false, 256); 1731 StringWriter catSw = new StringWriter(); 1732 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1733 String[] emptyArgs = new String[] { }; 1734 dumpApplicationMemoryUsage(null, oomPw, " ", emptyArgs, true, catPw); 1735 oomPw.flush(); 1736 String oomString = oomSw.toString(); 1737 */ 1738 dropBuilder.append(stack); 1739 dropBuilder.append('\n'); 1740 dropBuilder.append('\n'); 1741 dropBuilder.append(logBuilder); 1742 dropBuilder.append('\n'); 1743 /* 1744 dropBuilder.append(oomString); 1745 dropBuilder.append('\n'); 1746 */ 1747 StringWriter catSw = new StringWriter(); 1748 synchronized (ActivityManagerService.this) { 1749 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1750 String[] emptyArgs = new String[] { }; 1751 catPw.println(); 1752 dumpProcessesLocked(null, catPw, emptyArgs, 0, false, null); 1753 catPw.println(); 1754 mServices.dumpServicesLocked(null, catPw, emptyArgs, 0, 1755 false, false, null); 1756 catPw.println(); 1757 dumpActivitiesLocked(null, catPw, emptyArgs, 0, false, false, null); 1758 catPw.flush(); 1759 } 1760 dropBuilder.append(catSw.toString()); 1761 addErrorToDropBox("lowmem", null, "system_server", null, 1762 null, tag.toString(), dropBuilder.toString(), null, null); 1763 //Slog.i(TAG, "Sent to dropbox:"); 1764 //Slog.i(TAG, dropBuilder.toString()); 1765 synchronized (ActivityManagerService.this) { 1766 long now = SystemClock.uptimeMillis(); 1767 if (mLastMemUsageReportTime < now) { 1768 mLastMemUsageReportTime = now; 1769 } 1770 } 1771 } 1772 }; 1773 thread.start(); 1774 break; 1775 } 1776 case START_USER_SWITCH_MSG: { 1777 showUserSwitchDialog(msg.arg1, (String) msg.obj); 1778 break; 1779 } 1780 case REPORT_USER_SWITCH_MSG: { 1781 dispatchUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1782 break; 1783 } 1784 case CONTINUE_USER_SWITCH_MSG: { 1785 continueUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1786 break; 1787 } 1788 case USER_SWITCH_TIMEOUT_MSG: { 1789 timeoutUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1790 break; 1791 } 1792 case IMMERSIVE_MODE_LOCK_MSG: { 1793 final boolean nextState = (msg.arg1 != 0); 1794 if (mUpdateLock.isHeld() != nextState) { 1795 if (DEBUG_IMMERSIVE) { 1796 final ActivityRecord r = (ActivityRecord) msg.obj; 1797 Slog.d(TAG, "Applying new update lock state '" + nextState + "' for " + r); 1798 } 1799 if (nextState) { 1800 mUpdateLock.acquire(); 1801 } else { 1802 mUpdateLock.release(); 1803 } 1804 } 1805 break; 1806 } 1807 case PERSIST_URI_GRANTS_MSG: { 1808 writeGrantedUriPermissions(); 1809 break; 1810 } 1811 case REQUEST_ALL_PSS_MSG: { 1812 requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, false); 1813 break; 1814 } 1815 case START_PROFILES_MSG: { 1816 synchronized (ActivityManagerService.this) { 1817 startProfilesLocked(); 1818 } 1819 break; 1820 } 1821 case UPDATE_TIME: { 1822 synchronized (ActivityManagerService.this) { 1823 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1824 ProcessRecord r = mLruProcesses.get(i); 1825 if (r.thread != null) { 1826 try { 1827 r.thread.updateTimePrefs(msg.arg1 == 0 ? false : true); 1828 } catch (RemoteException ex) { 1829 Slog.w(TAG, "Failed to update preferences for: " + r.info.processName); 1830 } 1831 } 1832 } 1833 } 1834 break; 1835 } 1836 case SYSTEM_USER_START_MSG: { 1837 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 1838 Integer.toString(msg.arg1), msg.arg1); 1839 mSystemServiceManager.startUser(msg.arg1); 1840 break; 1841 } 1842 case SYSTEM_USER_CURRENT_MSG: { 1843 mBatteryStatsService.noteEvent( 1844 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_FINISH, 1845 Integer.toString(msg.arg2), msg.arg2); 1846 mBatteryStatsService.noteEvent( 1847 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 1848 Integer.toString(msg.arg1), msg.arg1); 1849 mSystemServiceManager.switchUser(msg.arg1); 1850 mLockToAppRequest.clearPrompt(); 1851 break; 1852 } 1853 case ENTER_ANIMATION_COMPLETE_MSG: { 1854 synchronized (ActivityManagerService.this) { 1855 ActivityRecord r = ActivityRecord.forToken((IBinder) msg.obj); 1856 if (r != null && r.app != null && r.app.thread != null) { 1857 try { 1858 r.app.thread.scheduleEnterAnimationComplete(r.appToken); 1859 } catch (RemoteException e) { 1860 } 1861 } 1862 } 1863 break; 1864 } 1865 case ENABLE_SCREEN_AFTER_BOOT_MSG: { 1866 enableScreenAfterBoot(); 1867 break; 1868 } 1869 } 1870 } 1871 }; 1872 1873 static final int COLLECT_PSS_BG_MSG = 1; 1874 1875 final Handler mBgHandler = new Handler(BackgroundThread.getHandler().getLooper()) { 1876 @Override 1877 public void handleMessage(Message msg) { 1878 switch (msg.what) { 1879 case COLLECT_PSS_BG_MSG: { 1880 long start = SystemClock.uptimeMillis(); 1881 MemInfoReader memInfo = null; 1882 synchronized (ActivityManagerService.this) { 1883 if (mFullPssPending) { 1884 mFullPssPending = false; 1885 memInfo = new MemInfoReader(); 1886 } 1887 } 1888 if (memInfo != null) { 1889 updateCpuStatsNow(); 1890 long nativeTotalPss = 0; 1891 synchronized (mProcessCpuThread) { 1892 final int N = mProcessCpuTracker.countStats(); 1893 for (int j=0; j<N; j++) { 1894 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(j); 1895 if (st.vsize <= 0 || st.uid >= Process.FIRST_APPLICATION_UID) { 1896 // This is definitely an application process; skip it. 1897 continue; 1898 } 1899 synchronized (mPidsSelfLocked) { 1900 if (mPidsSelfLocked.indexOfKey(st.pid) >= 0) { 1901 // This is one of our own processes; skip it. 1902 continue; 1903 } 1904 } 1905 nativeTotalPss += Debug.getPss(st.pid, null); 1906 } 1907 } 1908 memInfo.readMemInfo(); 1909 synchronized (this) { 1910 if (DEBUG_PSS) Slog.d(TAG, "Collected native and kernel memory in " 1911 + (SystemClock.uptimeMillis()-start) + "ms"); 1912 mProcessStats.addSysMemUsageLocked(memInfo.getCachedSizeKb(), 1913 memInfo.getFreeSizeKb(), memInfo.getZramTotalSizeKb(), 1914 memInfo.getBuffersSizeKb()+memInfo.getShmemSizeKb() 1915 +memInfo.getSlabSizeKb(), 1916 nativeTotalPss); 1917 } 1918 } 1919 1920 int i=0, num=0; 1921 long[] tmp = new long[1]; 1922 do { 1923 ProcessRecord proc; 1924 int procState; 1925 int pid; 1926 synchronized (ActivityManagerService.this) { 1927 if (i >= mPendingPssProcesses.size()) { 1928 if (DEBUG_PSS) Slog.d(TAG, "Collected PSS of " + num + " of " + i 1929 + " processes in " + (SystemClock.uptimeMillis()-start) + "ms"); 1930 mPendingPssProcesses.clear(); 1931 return; 1932 } 1933 proc = mPendingPssProcesses.get(i); 1934 procState = proc.pssProcState; 1935 if (proc.thread != null && procState == proc.setProcState) { 1936 pid = proc.pid; 1937 } else { 1938 proc = null; 1939 pid = 0; 1940 } 1941 i++; 1942 } 1943 if (proc != null) { 1944 long pss = Debug.getPss(pid, tmp); 1945 synchronized (ActivityManagerService.this) { 1946 if (proc.thread != null && proc.setProcState == procState 1947 && proc.pid == pid) { 1948 num++; 1949 proc.lastPssTime = SystemClock.uptimeMillis(); 1950 proc.baseProcessTracker.addPss(pss, tmp[0], true, proc.pkgList); 1951 if (DEBUG_PSS) Slog.d(TAG, "PSS of " + proc.toShortString() 1952 + ": " + pss + " lastPss=" + proc.lastPss 1953 + " state=" + ProcessList.makeProcStateString(procState)); 1954 if (proc.initialIdlePss == 0) { 1955 proc.initialIdlePss = pss; 1956 } 1957 proc.lastPss = pss; 1958 if (procState >= ActivityManager.PROCESS_STATE_HOME) { 1959 proc.lastCachedPss = pss; 1960 } 1961 } 1962 } 1963 } 1964 } while (true); 1965 } 1966 } 1967 } 1968 }; 1969 1970 /** 1971 * Monitor for package changes and update our internal state. 1972 */ 1973 private final PackageMonitor mPackageMonitor = new PackageMonitor() { 1974 @Override 1975 public void onPackageRemoved(String packageName, int uid) { 1976 // Remove all tasks with activities in the specified package from the list of recent tasks 1977 synchronized (ActivityManagerService.this) { 1978 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 1979 TaskRecord tr = mRecentTasks.get(i); 1980 ComponentName cn = tr.intent.getComponent(); 1981 if (cn != null && cn.getPackageName().equals(packageName)) { 1982 // If the package name matches, remove the task and kill the process 1983 removeTaskByIdLocked(tr.taskId, ActivityManager.REMOVE_TASK_KILL_PROCESS); 1984 } 1985 } 1986 } 1987 } 1988 1989 @Override 1990 public boolean onPackageChanged(String packageName, int uid, String[] components) { 1991 onPackageModified(packageName); 1992 return true; 1993 } 1994 1995 @Override 1996 public void onPackageModified(String packageName) { 1997 final PackageManager pm = mContext.getPackageManager(); 1998 final ArrayList<Pair<Intent, Integer>> recentTaskIntents = 1999 new ArrayList<Pair<Intent, Integer>>(); 2000 final ArrayList<Integer> tasksToRemove = new ArrayList<Integer>(); 2001 // Copy the list of recent tasks so that we don't hold onto the lock on 2002 // ActivityManagerService for long periods while checking if components exist. 2003 synchronized (ActivityManagerService.this) { 2004 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 2005 TaskRecord tr = mRecentTasks.get(i); 2006 recentTaskIntents.add(new Pair<Intent, Integer>(tr.intent, tr.taskId)); 2007 } 2008 } 2009 // Check the recent tasks and filter out all tasks with components that no longer exist. 2010 Intent tmpI = new Intent(); 2011 for (int i = recentTaskIntents.size() - 1; i >= 0; i--) { 2012 Pair<Intent, Integer> p = recentTaskIntents.get(i); 2013 ComponentName cn = p.first.getComponent(); 2014 if (cn != null && cn.getPackageName().equals(packageName)) { 2015 try { 2016 // Add the task to the list to remove if the component no longer exists 2017 tmpI.setComponent(cn); 2018 if (pm.queryIntentActivities(tmpI, PackageManager.MATCH_DEFAULT_ONLY).isEmpty()) { 2019 tasksToRemove.add(p.second); 2020 } 2021 } catch (Exception e) {} 2022 } 2023 } 2024 // Prune all the tasks with removed components from the list of recent tasks 2025 synchronized (ActivityManagerService.this) { 2026 for (int i = tasksToRemove.size() - 1; i >= 0; i--) { 2027 // Remove the task but don't kill the process (since other components in that 2028 // package may still be running and in the background) 2029 removeTaskByIdLocked(tasksToRemove.get(i), 0); 2030 } 2031 } 2032 } 2033 2034 @Override 2035 public boolean onHandleForceStop(Intent intent, String[] packages, int uid, boolean doit) { 2036 // Force stop the specified packages 2037 if (packages != null) { 2038 for (String pkg : packages) { 2039 synchronized (ActivityManagerService.this) { 2040 if (forceStopPackageLocked(pkg, -1, false, false, false, false, false, 0, 2041 "finished booting")) { 2042 return true; 2043 } 2044 } 2045 } 2046 } 2047 return false; 2048 } 2049 }; 2050 2051 public void setSystemProcess() { 2052 try { 2053 ServiceManager.addService(Context.ACTIVITY_SERVICE, this, true); 2054 ServiceManager.addService(ProcessStats.SERVICE_NAME, mProcessStats); 2055 ServiceManager.addService("meminfo", new MemBinder(this)); 2056 ServiceManager.addService("gfxinfo", new GraphicsBinder(this)); 2057 ServiceManager.addService("dbinfo", new DbBinder(this)); 2058 if (MONITOR_CPU_USAGE) { 2059 ServiceManager.addService("cpuinfo", new CpuBinder(this)); 2060 } 2061 ServiceManager.addService("permission", new PermissionController(this)); 2062 2063 ApplicationInfo info = mContext.getPackageManager().getApplicationInfo( 2064 "android", STOCK_PM_FLAGS); 2065 mSystemThread.installSystemApplicationInfo(info, getClass().getClassLoader()); 2066 2067 synchronized (this) { 2068 ProcessRecord app = newProcessRecordLocked(info, info.processName, false, 0); 2069 app.persistent = true; 2070 app.pid = MY_PID; 2071 app.maxAdj = ProcessList.SYSTEM_ADJ; 2072 app.makeActive(mSystemThread.getApplicationThread(), mProcessStats); 2073 mProcessNames.put(app.processName, app.uid, app); 2074 synchronized (mPidsSelfLocked) { 2075 mPidsSelfLocked.put(app.pid, app); 2076 } 2077 updateLruProcessLocked(app, false, null); 2078 updateOomAdjLocked(); 2079 } 2080 } catch (PackageManager.NameNotFoundException e) { 2081 throw new RuntimeException( 2082 "Unable to find android system package", e); 2083 } 2084 } 2085 2086 public void setWindowManager(WindowManagerService wm) { 2087 mWindowManager = wm; 2088 mStackSupervisor.setWindowManager(wm); 2089 } 2090 2091 public void setUsageStatsManager(UsageStatsManagerInternal usageStatsManager) { 2092 mUsageStatsService = usageStatsManager; 2093 } 2094 2095 public void startObservingNativeCrashes() { 2096 final NativeCrashListener ncl = new NativeCrashListener(this); 2097 ncl.start(); 2098 } 2099 2100 public IAppOpsService getAppOpsService() { 2101 return mAppOpsService; 2102 } 2103 2104 static class MemBinder extends Binder { 2105 ActivityManagerService mActivityManagerService; 2106 MemBinder(ActivityManagerService activityManagerService) { 2107 mActivityManagerService = activityManagerService; 2108 } 2109 2110 @Override 2111 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2112 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2113 != PackageManager.PERMISSION_GRANTED) { 2114 pw.println("Permission Denial: can't dump meminfo from from pid=" 2115 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2116 + " without permission " + android.Manifest.permission.DUMP); 2117 return; 2118 } 2119 2120 mActivityManagerService.dumpApplicationMemoryUsage(fd, pw, " ", args, false, null); 2121 } 2122 } 2123 2124 static class GraphicsBinder extends Binder { 2125 ActivityManagerService mActivityManagerService; 2126 GraphicsBinder(ActivityManagerService activityManagerService) { 2127 mActivityManagerService = activityManagerService; 2128 } 2129 2130 @Override 2131 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2132 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2133 != PackageManager.PERMISSION_GRANTED) { 2134 pw.println("Permission Denial: can't dump gfxinfo from from pid=" 2135 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2136 + " without permission " + android.Manifest.permission.DUMP); 2137 return; 2138 } 2139 2140 mActivityManagerService.dumpGraphicsHardwareUsage(fd, pw, args); 2141 } 2142 } 2143 2144 static class DbBinder extends Binder { 2145 ActivityManagerService mActivityManagerService; 2146 DbBinder(ActivityManagerService activityManagerService) { 2147 mActivityManagerService = activityManagerService; 2148 } 2149 2150 @Override 2151 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2152 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2153 != PackageManager.PERMISSION_GRANTED) { 2154 pw.println("Permission Denial: can't dump dbinfo from from pid=" 2155 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2156 + " without permission " + android.Manifest.permission.DUMP); 2157 return; 2158 } 2159 2160 mActivityManagerService.dumpDbInfo(fd, pw, args); 2161 } 2162 } 2163 2164 static class CpuBinder extends Binder { 2165 ActivityManagerService mActivityManagerService; 2166 CpuBinder(ActivityManagerService activityManagerService) { 2167 mActivityManagerService = activityManagerService; 2168 } 2169 2170 @Override 2171 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2172 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2173 != PackageManager.PERMISSION_GRANTED) { 2174 pw.println("Permission Denial: can't dump cpuinfo from from pid=" 2175 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2176 + " without permission " + android.Manifest.permission.DUMP); 2177 return; 2178 } 2179 2180 synchronized (mActivityManagerService.mProcessCpuThread) { 2181 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentLoad()); 2182 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentState( 2183 SystemClock.uptimeMillis())); 2184 } 2185 } 2186 } 2187 2188 public static final class Lifecycle extends SystemService { 2189 private final ActivityManagerService mService; 2190 2191 public Lifecycle(Context context) { 2192 super(context); 2193 mService = new ActivityManagerService(context); 2194 } 2195 2196 @Override 2197 public void onStart() { 2198 mService.start(); 2199 } 2200 2201 public ActivityManagerService getService() { 2202 return mService; 2203 } 2204 } 2205 2206 // Note: This method is invoked on the main thread but may need to attach various 2207 // handlers to other threads. So take care to be explicit about the looper. 2208 public ActivityManagerService(Context systemContext) { 2209 mContext = systemContext; 2210 mFactoryTest = FactoryTest.getMode(); 2211 mSystemThread = ActivityThread.currentActivityThread(); 2212 2213 Slog.i(TAG, "Memory class: " + ActivityManager.staticGetMemoryClass()); 2214 2215 mHandlerThread = new ServiceThread(TAG, 2216 android.os.Process.THREAD_PRIORITY_FOREGROUND, false /*allowIo*/); 2217 mHandlerThread.start(); 2218 mHandler = new MainHandler(mHandlerThread.getLooper()); 2219 2220 mFgBroadcastQueue = new BroadcastQueue(this, mHandler, 2221 "foreground", BROADCAST_FG_TIMEOUT, false); 2222 mBgBroadcastQueue = new BroadcastQueue(this, mHandler, 2223 "background", BROADCAST_BG_TIMEOUT, true); 2224 mBroadcastQueues[0] = mFgBroadcastQueue; 2225 mBroadcastQueues[1] = mBgBroadcastQueue; 2226 2227 mServices = new ActiveServices(this); 2228 mProviderMap = new ProviderMap(this); 2229 2230 // TODO: Move creation of battery stats service outside of activity manager service. 2231 File dataDir = Environment.getDataDirectory(); 2232 File systemDir = new File(dataDir, "system"); 2233 systemDir.mkdirs(); 2234 mBatteryStatsService = new BatteryStatsService(systemDir, mHandler); 2235 mBatteryStatsService.getActiveStatistics().readLocked(); 2236 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2237 mOnBattery = DEBUG_POWER ? true 2238 : mBatteryStatsService.getActiveStatistics().getIsOnBattery(); 2239 mBatteryStatsService.getActiveStatistics().setCallback(this); 2240 2241 mProcessStats = new ProcessStatsService(this, new File(systemDir, "procstats")); 2242 2243 mAppOpsService = new AppOpsService(new File(systemDir, "appops.xml"), mHandler); 2244 2245 mGrantFile = new AtomicFile(new File(systemDir, "urigrants.xml")); 2246 2247 // User 0 is the first and only user that runs at boot. 2248 mStartedUsers.put(0, new UserStartedState(new UserHandle(0), true)); 2249 mUserLru.add(Integer.valueOf(0)); 2250 updateStartedUserArrayLocked(); 2251 2252 GL_ES_VERSION = SystemProperties.getInt("ro.opengles.version", 2253 ConfigurationInfo.GL_ES_VERSION_UNDEFINED); 2254 2255 mConfiguration.setToDefaults(); 2256 mConfiguration.setLocale(Locale.getDefault()); 2257 2258 mConfigurationSeq = mConfiguration.seq = 1; 2259 mProcessCpuTracker.init(); 2260 2261 mCompatModePackages = new CompatModePackages(this, systemDir, mHandler); 2262 mIntentFirewall = new IntentFirewall(new IntentFirewallInterface(), mHandler); 2263 mStackSupervisor = new ActivityStackSupervisor(this); 2264 mTaskPersister = new TaskPersister(systemDir, mStackSupervisor); 2265 2266 mProcessCpuThread = new Thread("CpuTracker") { 2267 @Override 2268 public void run() { 2269 while (true) { 2270 try { 2271 try { 2272 synchronized(this) { 2273 final long now = SystemClock.uptimeMillis(); 2274 long nextCpuDelay = (mLastCpuTime.get()+MONITOR_CPU_MAX_TIME)-now; 2275 long nextWriteDelay = (mLastWriteTime+BATTERY_STATS_TIME)-now; 2276 //Slog.i(TAG, "Cpu delay=" + nextCpuDelay 2277 // + ", write delay=" + nextWriteDelay); 2278 if (nextWriteDelay < nextCpuDelay) { 2279 nextCpuDelay = nextWriteDelay; 2280 } 2281 if (nextCpuDelay > 0) { 2282 mProcessCpuMutexFree.set(true); 2283 this.wait(nextCpuDelay); 2284 } 2285 } 2286 } catch (InterruptedException e) { 2287 } 2288 updateCpuStatsNow(); 2289 } catch (Exception e) { 2290 Slog.e(TAG, "Unexpected exception collecting process stats", e); 2291 } 2292 } 2293 } 2294 }; 2295 2296 mLockToAppRequest = new LockToAppRequestDialog(mContext, this); 2297 2298 Watchdog.getInstance().addMonitor(this); 2299 Watchdog.getInstance().addThread(mHandler); 2300 } 2301 2302 public void setSystemServiceManager(SystemServiceManager mgr) { 2303 mSystemServiceManager = mgr; 2304 } 2305 2306 private void start() { 2307 Process.removeAllProcessGroups(); 2308 mProcessCpuThread.start(); 2309 2310 mBatteryStatsService.publish(mContext); 2311 mAppOpsService.publish(mContext); 2312 Slog.d("AppOps", "AppOpsService published"); 2313 LocalServices.addService(ActivityManagerInternal.class, new LocalService()); 2314 } 2315 2316 public void initPowerManagement() { 2317 mStackSupervisor.initPowerManagement(); 2318 mBatteryStatsService.initPowerManagement(); 2319 } 2320 2321 @Override 2322 public boolean onTransact(int code, Parcel data, Parcel reply, int flags) 2323 throws RemoteException { 2324 if (code == SYSPROPS_TRANSACTION) { 2325 // We need to tell all apps about the system property change. 2326 ArrayList<IBinder> procs = new ArrayList<IBinder>(); 2327 synchronized(this) { 2328 final int NP = mProcessNames.getMap().size(); 2329 for (int ip=0; ip<NP; ip++) { 2330 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 2331 final int NA = apps.size(); 2332 for (int ia=0; ia<NA; ia++) { 2333 ProcessRecord app = apps.valueAt(ia); 2334 if (app.thread != null) { 2335 procs.add(app.thread.asBinder()); 2336 } 2337 } 2338 } 2339 } 2340 2341 int N = procs.size(); 2342 for (int i=0; i<N; i++) { 2343 Parcel data2 = Parcel.obtain(); 2344 try { 2345 procs.get(i).transact(IBinder.SYSPROPS_TRANSACTION, data2, null, 0); 2346 } catch (RemoteException e) { 2347 } 2348 data2.recycle(); 2349 } 2350 } 2351 try { 2352 return super.onTransact(code, data, reply, flags); 2353 } catch (RuntimeException e) { 2354 // The activity manager only throws security exceptions, so let's 2355 // log all others. 2356 if (!(e instanceof SecurityException)) { 2357 Slog.wtf(TAG, "Activity Manager Crash", e); 2358 } 2359 throw e; 2360 } 2361 } 2362 2363 void updateCpuStats() { 2364 final long now = SystemClock.uptimeMillis(); 2365 if (mLastCpuTime.get() >= now - MONITOR_CPU_MIN_TIME) { 2366 return; 2367 } 2368 if (mProcessCpuMutexFree.compareAndSet(true, false)) { 2369 synchronized (mProcessCpuThread) { 2370 mProcessCpuThread.notify(); 2371 } 2372 } 2373 } 2374 2375 void updateCpuStatsNow() { 2376 synchronized (mProcessCpuThread) { 2377 mProcessCpuMutexFree.set(false); 2378 final long now = SystemClock.uptimeMillis(); 2379 boolean haveNewCpuStats = false; 2380 2381 if (MONITOR_CPU_USAGE && 2382 mLastCpuTime.get() < (now-MONITOR_CPU_MIN_TIME)) { 2383 mLastCpuTime.set(now); 2384 haveNewCpuStats = true; 2385 mProcessCpuTracker.update(); 2386 //Slog.i(TAG, mProcessCpu.printCurrentState()); 2387 //Slog.i(TAG, "Total CPU usage: " 2388 // + mProcessCpu.getTotalCpuPercent() + "%"); 2389 2390 // Slog the cpu usage if the property is set. 2391 if ("true".equals(SystemProperties.get("events.cpu"))) { 2392 int user = mProcessCpuTracker.getLastUserTime(); 2393 int system = mProcessCpuTracker.getLastSystemTime(); 2394 int iowait = mProcessCpuTracker.getLastIoWaitTime(); 2395 int irq = mProcessCpuTracker.getLastIrqTime(); 2396 int softIrq = mProcessCpuTracker.getLastSoftIrqTime(); 2397 int idle = mProcessCpuTracker.getLastIdleTime(); 2398 2399 int total = user + system + iowait + irq + softIrq + idle; 2400 if (total == 0) total = 1; 2401 2402 EventLog.writeEvent(EventLogTags.CPU, 2403 ((user+system+iowait+irq+softIrq) * 100) / total, 2404 (user * 100) / total, 2405 (system * 100) / total, 2406 (iowait * 100) / total, 2407 (irq * 100) / total, 2408 (softIrq * 100) / total); 2409 } 2410 } 2411 2412 long[] cpuSpeedTimes = mProcessCpuTracker.getLastCpuSpeedTimes(); 2413 final BatteryStatsImpl bstats = mBatteryStatsService.getActiveStatistics(); 2414 synchronized(bstats) { 2415 synchronized(mPidsSelfLocked) { 2416 if (haveNewCpuStats) { 2417 if (mOnBattery) { 2418 int perc = bstats.startAddingCpuLocked(); 2419 int totalUTime = 0; 2420 int totalSTime = 0; 2421 final int N = mProcessCpuTracker.countStats(); 2422 for (int i=0; i<N; i++) { 2423 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 2424 if (!st.working) { 2425 continue; 2426 } 2427 ProcessRecord pr = mPidsSelfLocked.get(st.pid); 2428 int otherUTime = (st.rel_utime*perc)/100; 2429 int otherSTime = (st.rel_stime*perc)/100; 2430 totalUTime += otherUTime; 2431 totalSTime += otherSTime; 2432 if (pr != null) { 2433 BatteryStatsImpl.Uid.Proc ps = pr.curProcBatteryStats; 2434 if (ps == null || !ps.isActive()) { 2435 pr.curProcBatteryStats = ps = bstats.getProcessStatsLocked( 2436 pr.info.uid, pr.processName); 2437 } 2438 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2439 st.rel_stime-otherSTime); 2440 ps.addSpeedStepTimes(cpuSpeedTimes); 2441 pr.curCpuTime += (st.rel_utime+st.rel_stime) * 10; 2442 } else { 2443 BatteryStatsImpl.Uid.Proc ps = st.batteryStats; 2444 if (ps == null || !ps.isActive()) { 2445 st.batteryStats = ps = bstats.getProcessStatsLocked( 2446 bstats.mapUid(st.uid), st.name); 2447 } 2448 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2449 st.rel_stime-otherSTime); 2450 ps.addSpeedStepTimes(cpuSpeedTimes); 2451 } 2452 } 2453 bstats.finishAddingCpuLocked(perc, totalUTime, 2454 totalSTime, cpuSpeedTimes); 2455 } 2456 } 2457 } 2458 2459 if (mLastWriteTime < (now-BATTERY_STATS_TIME)) { 2460 mLastWriteTime = now; 2461 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2462 } 2463 } 2464 } 2465 } 2466 2467 @Override 2468 public void batteryNeedsCpuUpdate() { 2469 updateCpuStatsNow(); 2470 } 2471 2472 @Override 2473 public void batteryPowerChanged(boolean onBattery) { 2474 // When plugging in, update the CPU stats first before changing 2475 // the plug state. 2476 updateCpuStatsNow(); 2477 synchronized (this) { 2478 synchronized(mPidsSelfLocked) { 2479 mOnBattery = DEBUG_POWER ? true : onBattery; 2480 } 2481 } 2482 } 2483 2484 /** 2485 * Initialize the application bind args. These are passed to each 2486 * process when the bindApplication() IPC is sent to the process. They're 2487 * lazily setup to make sure the services are running when they're asked for. 2488 */ 2489 private HashMap<String, IBinder> getCommonServicesLocked() { 2490 if (mAppBindArgs == null) { 2491 mAppBindArgs = new HashMap<String, IBinder>(); 2492 2493 // Setup the application init args 2494 mAppBindArgs.put("package", ServiceManager.getService("package")); 2495 mAppBindArgs.put("window", ServiceManager.getService("window")); 2496 mAppBindArgs.put(Context.ALARM_SERVICE, 2497 ServiceManager.getService(Context.ALARM_SERVICE)); 2498 } 2499 return mAppBindArgs; 2500 } 2501 2502 final void setFocusedActivityLocked(ActivityRecord r) { 2503 if (mFocusedActivity != r) { 2504 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedActivityLocked: r=" + r); 2505 mFocusedActivity = r; 2506 if (r.task != null && r.task.voiceInteractor != null) { 2507 startRunningVoiceLocked(); 2508 } else { 2509 finishRunningVoiceLocked(); 2510 } 2511 mStackSupervisor.setFocusedStack(r); 2512 if (r != null) { 2513 mWindowManager.setFocusedApp(r.appToken, true); 2514 } 2515 applyUpdateLockStateLocked(r); 2516 } 2517 } 2518 2519 final void clearFocusedActivity(ActivityRecord r) { 2520 if (mFocusedActivity == r) { 2521 mFocusedActivity = null; 2522 } 2523 } 2524 2525 @Override 2526 public void setFocusedStack(int stackId) { 2527 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedStack: stackId=" + stackId); 2528 synchronized (ActivityManagerService.this) { 2529 ActivityStack stack = mStackSupervisor.getStack(stackId); 2530 if (stack != null) { 2531 ActivityRecord r = stack.topRunningActivityLocked(null); 2532 if (r != null) { 2533 setFocusedActivityLocked(r); 2534 } 2535 } 2536 } 2537 } 2538 2539 @Override 2540 public void notifyActivityDrawn(IBinder token) { 2541 if (DEBUG_VISBILITY) Slog.d(TAG, "notifyActivityDrawn: token=" + token); 2542 synchronized (this) { 2543 ActivityRecord r= mStackSupervisor.isInAnyStackLocked(token); 2544 if (r != null) { 2545 r.task.stack.notifyActivityDrawnLocked(r); 2546 } 2547 } 2548 } 2549 2550 final void applyUpdateLockStateLocked(ActivityRecord r) { 2551 // Modifications to the UpdateLock state are done on our handler, outside 2552 // the activity manager's locks. The new state is determined based on the 2553 // state *now* of the relevant activity record. The object is passed to 2554 // the handler solely for logging detail, not to be consulted/modified. 2555 final boolean nextState = r != null && r.immersive; 2556 mHandler.sendMessage( 2557 mHandler.obtainMessage(IMMERSIVE_MODE_LOCK_MSG, (nextState) ? 1 : 0, 0, r)); 2558 } 2559 2560 final void showAskCompatModeDialogLocked(ActivityRecord r) { 2561 Message msg = Message.obtain(); 2562 msg.what = SHOW_COMPAT_MODE_DIALOG_MSG; 2563 msg.obj = r.task.askedCompatMode ? null : r; 2564 mHandler.sendMessage(msg); 2565 } 2566 2567 private final int updateLruProcessInternalLocked(ProcessRecord app, long now, int index, 2568 String what, Object obj, ProcessRecord srcApp) { 2569 app.lastActivityTime = now; 2570 2571 if (app.activities.size() > 0) { 2572 // Don't want to touch dependent processes that are hosting activities. 2573 return index; 2574 } 2575 2576 int lrui = mLruProcesses.lastIndexOf(app); 2577 if (lrui < 0) { 2578 Slog.wtf(TAG, "Adding dependent process " + app + " not on LRU list: " 2579 + what + " " + obj + " from " + srcApp); 2580 return index; 2581 } 2582 2583 if (lrui >= index) { 2584 // Don't want to cause this to move dependent processes *back* in the 2585 // list as if they were less frequently used. 2586 return index; 2587 } 2588 2589 if (lrui >= mLruProcessActivityStart) { 2590 // Don't want to touch dependent processes that are hosting activities. 2591 return index; 2592 } 2593 2594 mLruProcesses.remove(lrui); 2595 if (index > 0) { 2596 index--; 2597 } 2598 if (DEBUG_LRU) Slog.d(TAG, "Moving dep from " + lrui + " to " + index 2599 + " in LRU list: " + app); 2600 mLruProcesses.add(index, app); 2601 return index; 2602 } 2603 2604 final void removeLruProcessLocked(ProcessRecord app) { 2605 int lrui = mLruProcesses.lastIndexOf(app); 2606 if (lrui >= 0) { 2607 if (lrui <= mLruProcessActivityStart) { 2608 mLruProcessActivityStart--; 2609 } 2610 if (lrui <= mLruProcessServiceStart) { 2611 mLruProcessServiceStart--; 2612 } 2613 mLruProcesses.remove(lrui); 2614 } 2615 } 2616 2617 final void updateLruProcessLocked(ProcessRecord app, boolean activityChange, 2618 ProcessRecord client) { 2619 final boolean hasActivity = app.activities.size() > 0 || app.hasClientActivities 2620 || app.treatLikeActivity; 2621 final boolean hasService = false; // not impl yet. app.services.size() > 0; 2622 if (!activityChange && hasActivity) { 2623 // The process has activities, so we are only allowing activity-based adjustments 2624 // to move it. It should be kept in the front of the list with other 2625 // processes that have activities, and we don't want those to change their 2626 // order except due to activity operations. 2627 return; 2628 } 2629 2630 mLruSeq++; 2631 final long now = SystemClock.uptimeMillis(); 2632 app.lastActivityTime = now; 2633 2634 // First a quick reject: if the app is already at the position we will 2635 // put it, then there is nothing to do. 2636 if (hasActivity) { 2637 final int N = mLruProcesses.size(); 2638 if (N > 0 && mLruProcesses.get(N-1) == app) { 2639 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top activity: " + app); 2640 return; 2641 } 2642 } else { 2643 if (mLruProcessServiceStart > 0 2644 && mLruProcesses.get(mLruProcessServiceStart-1) == app) { 2645 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top other: " + app); 2646 return; 2647 } 2648 } 2649 2650 int lrui = mLruProcesses.lastIndexOf(app); 2651 2652 if (app.persistent && lrui >= 0) { 2653 // We don't care about the position of persistent processes, as long as 2654 // they are in the list. 2655 if (DEBUG_LRU) Slog.d(TAG, "Not moving, persistent: " + app); 2656 return; 2657 } 2658 2659 /* In progress: compute new position first, so we can avoid doing work 2660 if the process is not actually going to move. Not yet working. 2661 int addIndex; 2662 int nextIndex; 2663 boolean inActivity = false, inService = false; 2664 if (hasActivity) { 2665 // Process has activities, put it at the very tipsy-top. 2666 addIndex = mLruProcesses.size(); 2667 nextIndex = mLruProcessServiceStart; 2668 inActivity = true; 2669 } else if (hasService) { 2670 // Process has services, put it at the top of the service list. 2671 addIndex = mLruProcessActivityStart; 2672 nextIndex = mLruProcessServiceStart; 2673 inActivity = true; 2674 inService = true; 2675 } else { 2676 // Process not otherwise of interest, it goes to the top of the non-service area. 2677 addIndex = mLruProcessServiceStart; 2678 if (client != null) { 2679 int clientIndex = mLruProcesses.lastIndexOf(client); 2680 if (clientIndex < 0) Slog.d(TAG, "Unknown client " + client + " when updating " 2681 + app); 2682 if (clientIndex >= 0 && addIndex > clientIndex) { 2683 addIndex = clientIndex; 2684 } 2685 } 2686 nextIndex = addIndex > 0 ? addIndex-1 : addIndex; 2687 } 2688 2689 Slog.d(TAG, "Update LRU at " + lrui + " to " + addIndex + " (act=" 2690 + mLruProcessActivityStart + "): " + app); 2691 */ 2692 2693 if (lrui >= 0) { 2694 if (lrui < mLruProcessActivityStart) { 2695 mLruProcessActivityStart--; 2696 } 2697 if (lrui < mLruProcessServiceStart) { 2698 mLruProcessServiceStart--; 2699 } 2700 /* 2701 if (addIndex > lrui) { 2702 addIndex--; 2703 } 2704 if (nextIndex > lrui) { 2705 nextIndex--; 2706 } 2707 */ 2708 mLruProcesses.remove(lrui); 2709 } 2710 2711 /* 2712 mLruProcesses.add(addIndex, app); 2713 if (inActivity) { 2714 mLruProcessActivityStart++; 2715 } 2716 if (inService) { 2717 mLruProcessActivityStart++; 2718 } 2719 */ 2720 2721 int nextIndex; 2722 if (hasActivity) { 2723 final int N = mLruProcesses.size(); 2724 if (app.activities.size() == 0 && mLruProcessActivityStart < (N-1)) { 2725 // Process doesn't have activities, but has clients with 2726 // activities... move it up, but one below the top (the top 2727 // should always have a real activity). 2728 if (DEBUG_LRU) Slog.d(TAG, "Adding to second-top of LRU activity list: " + app); 2729 mLruProcesses.add(N-1, app); 2730 // To keep it from spamming the LRU list (by making a bunch of clients), 2731 // we will push down any other entries owned by the app. 2732 final int uid = app.info.uid; 2733 for (int i=N-2; i>mLruProcessActivityStart; i--) { 2734 ProcessRecord subProc = mLruProcesses.get(i); 2735 if (subProc.info.uid == uid) { 2736 // We want to push this one down the list. If the process after 2737 // it is for the same uid, however, don't do so, because we don't 2738 // want them internally to be re-ordered. 2739 if (mLruProcesses.get(i-1).info.uid != uid) { 2740 if (DEBUG_LRU) Slog.d(TAG, "Pushing uid " + uid + " swapping at " + i 2741 + ": " + mLruProcesses.get(i) + " : " + mLruProcesses.get(i-1)); 2742 ProcessRecord tmp = mLruProcesses.get(i); 2743 mLruProcesses.set(i, mLruProcesses.get(i-1)); 2744 mLruProcesses.set(i-1, tmp); 2745 i--; 2746 } 2747 } else { 2748 // A gap, we can stop here. 2749 break; 2750 } 2751 } 2752 } else { 2753 // Process has activities, put it at the very tipsy-top. 2754 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU activity list: " + app); 2755 mLruProcesses.add(app); 2756 } 2757 nextIndex = mLruProcessServiceStart; 2758 } else if (hasService) { 2759 // Process has services, put it at the top of the service list. 2760 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU service list: " + app); 2761 mLruProcesses.add(mLruProcessActivityStart, app); 2762 nextIndex = mLruProcessServiceStart; 2763 mLruProcessActivityStart++; 2764 } else { 2765 // Process not otherwise of interest, it goes to the top of the non-service area. 2766 int index = mLruProcessServiceStart; 2767 if (client != null) { 2768 // If there is a client, don't allow the process to be moved up higher 2769 // in the list than that client. 2770 int clientIndex = mLruProcesses.lastIndexOf(client); 2771 if (DEBUG_LRU && clientIndex < 0) Slog.d(TAG, "Unknown client " + client 2772 + " when updating " + app); 2773 if (clientIndex <= lrui) { 2774 // Don't allow the client index restriction to push it down farther in the 2775 // list than it already is. 2776 clientIndex = lrui; 2777 } 2778 if (clientIndex >= 0 && index > clientIndex) { 2779 index = clientIndex; 2780 } 2781 } 2782 if (DEBUG_LRU) Slog.d(TAG, "Adding at " + index + " of LRU list: " + app); 2783 mLruProcesses.add(index, app); 2784 nextIndex = index-1; 2785 mLruProcessActivityStart++; 2786 mLruProcessServiceStart++; 2787 } 2788 2789 // If the app is currently using a content provider or service, 2790 // bump those processes as well. 2791 for (int j=app.connections.size()-1; j>=0; j--) { 2792 ConnectionRecord cr = app.connections.valueAt(j); 2793 if (cr.binding != null && !cr.serviceDead && cr.binding.service != null 2794 && cr.binding.service.app != null 2795 && cr.binding.service.app.lruSeq != mLruSeq 2796 && !cr.binding.service.app.persistent) { 2797 nextIndex = updateLruProcessInternalLocked(cr.binding.service.app, now, nextIndex, 2798 "service connection", cr, app); 2799 } 2800 } 2801 for (int j=app.conProviders.size()-1; j>=0; j--) { 2802 ContentProviderRecord cpr = app.conProviders.get(j).provider; 2803 if (cpr.proc != null && cpr.proc.lruSeq != mLruSeq && !cpr.proc.persistent) { 2804 nextIndex = updateLruProcessInternalLocked(cpr.proc, now, nextIndex, 2805 "provider reference", cpr, app); 2806 } 2807 } 2808 } 2809 2810 final ProcessRecord getProcessRecordLocked(String processName, int uid, boolean keepIfLarge) { 2811 if (uid == Process.SYSTEM_UID) { 2812 // The system gets to run in any process. If there are multiple 2813 // processes with the same uid, just pick the first (this 2814 // should never happen). 2815 SparseArray<ProcessRecord> procs = mProcessNames.getMap().get(processName); 2816 if (procs == null) return null; 2817 final int N = procs.size(); 2818 for (int i = 0; i < N; i++) { 2819 if (UserHandle.isSameUser(procs.keyAt(i), uid)) return procs.valueAt(i); 2820 } 2821 } 2822 ProcessRecord proc = mProcessNames.get(processName, uid); 2823 if (false && proc != null && !keepIfLarge 2824 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY 2825 && proc.lastCachedPss >= 4000) { 2826 // Turn this condition on to cause killing to happen regularly, for testing. 2827 if (proc.baseProcessTracker != null) { 2828 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2829 } 2830 proc.kill(Long.toString(proc.lastCachedPss) + "k from cached", true); 2831 } else if (proc != null && !keepIfLarge 2832 && mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 2833 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 2834 if (DEBUG_PSS) Slog.d(TAG, "May not keep " + proc + ": pss=" + proc.lastCachedPss); 2835 if (proc.lastCachedPss >= mProcessList.getCachedRestoreThresholdKb()) { 2836 if (proc.baseProcessTracker != null) { 2837 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2838 } 2839 proc.kill(Long.toString(proc.lastCachedPss) + "k from cached", true); 2840 } 2841 } 2842 return proc; 2843 } 2844 2845 void ensurePackageDexOpt(String packageName) { 2846 IPackageManager pm = AppGlobals.getPackageManager(); 2847 try { 2848 if (pm.performDexOptIfNeeded(packageName, null /* instruction set */)) { 2849 mDidDexOpt = true; 2850 } 2851 } catch (RemoteException e) { 2852 } 2853 } 2854 2855 boolean isNextTransitionForward() { 2856 int transit = mWindowManager.getPendingAppTransition(); 2857 return transit == AppTransition.TRANSIT_ACTIVITY_OPEN 2858 || transit == AppTransition.TRANSIT_TASK_OPEN 2859 || transit == AppTransition.TRANSIT_TASK_TO_FRONT; 2860 } 2861 2862 int startIsolatedProcess(String entryPoint, String[] entryPointArgs, 2863 String processName, String abiOverride, int uid, Runnable crashHandler) { 2864 synchronized(this) { 2865 ApplicationInfo info = new ApplicationInfo(); 2866 // In general the ApplicationInfo.uid isn't neccesarily equal to ProcessRecord.uid. 2867 // For isolated processes, the former contains the parent's uid and the latter the 2868 // actual uid of the isolated process. 2869 // In the special case introduced by this method (which is, starting an isolated 2870 // process directly from the SystemServer without an actual parent app process) the 2871 // closest thing to a parent's uid is SYSTEM_UID. 2872 // The only important thing here is to keep AI.uid != PR.uid, in order to trigger 2873 // the |isolated| logic in the ProcessRecord constructor. 2874 info.uid = Process.SYSTEM_UID; 2875 info.processName = processName; 2876 info.className = entryPoint; 2877 info.packageName = "android"; 2878 ProcessRecord proc = startProcessLocked(processName, info /* info */, 2879 false /* knownToBeDead */, 0 /* intentFlags */, "" /* hostingType */, 2880 null /* hostingName */, true /* allowWhileBooting */, true /* isolated */, 2881 uid, true /* keepIfLarge */, abiOverride, entryPoint, entryPointArgs, 2882 crashHandler); 2883 return proc != null ? proc.pid : 0; 2884 } 2885 } 2886 2887 final ProcessRecord startProcessLocked(String processName, 2888 ApplicationInfo info, boolean knownToBeDead, int intentFlags, 2889 String hostingType, ComponentName hostingName, boolean allowWhileBooting, 2890 boolean isolated, boolean keepIfLarge) { 2891 return startProcessLocked(processName, info, knownToBeDead, intentFlags, hostingType, 2892 hostingName, allowWhileBooting, isolated, 0 /* isolatedUid */, keepIfLarge, 2893 null /* ABI override */, null /* entryPoint */, null /* entryPointArgs */, 2894 null /* crashHandler */); 2895 } 2896 2897 final ProcessRecord startProcessLocked(String processName, ApplicationInfo info, 2898 boolean knownToBeDead, int intentFlags, String hostingType, ComponentName hostingName, 2899 boolean allowWhileBooting, boolean isolated, int isolatedUid, boolean keepIfLarge, 2900 String abiOverride, String entryPoint, String[] entryPointArgs, Runnable crashHandler) { 2901 ProcessRecord app; 2902 if (!isolated) { 2903 app = getProcessRecordLocked(processName, info.uid, keepIfLarge); 2904 } else { 2905 // If this is an isolated process, it can't re-use an existing process. 2906 app = null; 2907 } 2908 // We don't have to do anything more if: 2909 // (1) There is an existing application record; and 2910 // (2) The caller doesn't think it is dead, OR there is no thread 2911 // object attached to it so we know it couldn't have crashed; and 2912 // (3) There is a pid assigned to it, so it is either starting or 2913 // already running. 2914 if (DEBUG_PROCESSES) Slog.v(TAG, "startProcess: name=" + processName 2915 + " app=" + app + " knownToBeDead=" + knownToBeDead 2916 + " thread=" + (app != null ? app.thread : null) 2917 + " pid=" + (app != null ? app.pid : -1)); 2918 if (app != null && app.pid > 0) { 2919 if (!knownToBeDead || app.thread == null) { 2920 // We already have the app running, or are waiting for it to 2921 // come up (we have a pid but not yet its thread), so keep it. 2922 if (DEBUG_PROCESSES) Slog.v(TAG, "App already running: " + app); 2923 // If this is a new package in the process, add the package to the list 2924 app.addPackage(info.packageName, info.versionCode, mProcessStats); 2925 return app; 2926 } 2927 2928 // An application record is attached to a previous process, 2929 // clean it up now. 2930 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, "App died: " + app); 2931 Process.killProcessGroup(app.info.uid, app.pid); 2932 handleAppDiedLocked(app, true, true); 2933 } 2934 2935 String hostingNameStr = hostingName != null 2936 ? hostingName.flattenToShortString() : null; 2937 2938 if (!isolated) { 2939 if ((intentFlags&Intent.FLAG_FROM_BACKGROUND) != 0) { 2940 // If we are in the background, then check to see if this process 2941 // is bad. If so, we will just silently fail. 2942 if (mBadProcesses.get(info.processName, info.uid) != null) { 2943 if (DEBUG_PROCESSES) Slog.v(TAG, "Bad process: " + info.uid 2944 + "/" + info.processName); 2945 return null; 2946 } 2947 } else { 2948 // When the user is explicitly starting a process, then clear its 2949 // crash count so that we won't make it bad until they see at 2950 // least one crash dialog again, and make the process good again 2951 // if it had been bad. 2952 if (DEBUG_PROCESSES) Slog.v(TAG, "Clearing bad process: " + info.uid 2953 + "/" + info.processName); 2954 mProcessCrashTimes.remove(info.processName, info.uid); 2955 if (mBadProcesses.get(info.processName, info.uid) != null) { 2956 EventLog.writeEvent(EventLogTags.AM_PROC_GOOD, 2957 UserHandle.getUserId(info.uid), info.uid, 2958 info.processName); 2959 mBadProcesses.remove(info.processName, info.uid); 2960 if (app != null) { 2961 app.bad = false; 2962 } 2963 } 2964 } 2965 } 2966 2967 if (app == null) { 2968 app = newProcessRecordLocked(info, processName, isolated, isolatedUid); 2969 app.crashHandler = crashHandler; 2970 if (app == null) { 2971 Slog.w(TAG, "Failed making new process record for " 2972 + processName + "/" + info.uid + " isolated=" + isolated); 2973 return null; 2974 } 2975 mProcessNames.put(processName, app.uid, app); 2976 if (isolated) { 2977 mIsolatedProcesses.put(app.uid, app); 2978 } 2979 } else { 2980 // If this is a new package in the process, add the package to the list 2981 app.addPackage(info.packageName, info.versionCode, mProcessStats); 2982 } 2983 2984 // If the system is not ready yet, then hold off on starting this 2985 // process until it is. 2986 if (!mProcessesReady 2987 && !isAllowedWhileBooting(info) 2988 && !allowWhileBooting) { 2989 if (!mProcessesOnHold.contains(app)) { 2990 mProcessesOnHold.add(app); 2991 } 2992 if (DEBUG_PROCESSES) Slog.v(TAG, "System not ready, putting on hold: " + app); 2993 return app; 2994 } 2995 2996 startProcessLocked( 2997 app, hostingType, hostingNameStr, abiOverride, entryPoint, entryPointArgs); 2998 return (app.pid != 0) ? app : null; 2999 } 3000 3001 boolean isAllowedWhileBooting(ApplicationInfo ai) { 3002 return (ai.flags&ApplicationInfo.FLAG_PERSISTENT) != 0; 3003 } 3004 3005 private final void startProcessLocked(ProcessRecord app, 3006 String hostingType, String hostingNameStr) { 3007 startProcessLocked(app, hostingType, hostingNameStr, null /* abiOverride */, 3008 null /* entryPoint */, null /* entryPointArgs */); 3009 } 3010 3011 private final void startProcessLocked(ProcessRecord app, String hostingType, 3012 String hostingNameStr, String abiOverride, String entryPoint, String[] entryPointArgs) { 3013 if (app.pid > 0 && app.pid != MY_PID) { 3014 synchronized (mPidsSelfLocked) { 3015 mPidsSelfLocked.remove(app.pid); 3016 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 3017 } 3018 app.setPid(0); 3019 } 3020 3021 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 3022 "startProcessLocked removing on hold: " + app); 3023 mProcessesOnHold.remove(app); 3024 3025 updateCpuStats(); 3026 3027 try { 3028 int uid = app.uid; 3029 3030 int[] gids = null; 3031 int mountExternal = Zygote.MOUNT_EXTERNAL_NONE; 3032 if (!app.isolated) { 3033 int[] permGids = null; 3034 try { 3035 final PackageManager pm = mContext.getPackageManager(); 3036 permGids = pm.getPackageGids(app.info.packageName); 3037 3038 if (Environment.isExternalStorageEmulated()) { 3039 if (pm.checkPermission( 3040 android.Manifest.permission.ACCESS_ALL_EXTERNAL_STORAGE, 3041 app.info.packageName) == PERMISSION_GRANTED) { 3042 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER_ALL; 3043 } else { 3044 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER; 3045 } 3046 } 3047 } catch (PackageManager.NameNotFoundException e) { 3048 Slog.w(TAG, "Unable to retrieve gids", e); 3049 } 3050 3051 /* 3052 * Add shared application and profile GIDs so applications can share some 3053 * resources like shared libraries and access user-wide resources 3054 */ 3055 if (permGids == null) { 3056 gids = new int[2]; 3057 } else { 3058 gids = new int[permGids.length + 2]; 3059 System.arraycopy(permGids, 0, gids, 2, permGids.length); 3060 } 3061 gids[0] = UserHandle.getSharedAppGid(UserHandle.getAppId(uid)); 3062 gids[1] = UserHandle.getUserGid(UserHandle.getUserId(uid)); 3063 } 3064 if (mFactoryTest != FactoryTest.FACTORY_TEST_OFF) { 3065 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3066 && mTopComponent != null 3067 && app.processName.equals(mTopComponent.getPackageName())) { 3068 uid = 0; 3069 } 3070 if (mFactoryTest == FactoryTest.FACTORY_TEST_HIGH_LEVEL 3071 && (app.info.flags&ApplicationInfo.FLAG_FACTORY_TEST) != 0) { 3072 uid = 0; 3073 } 3074 } 3075 int debugFlags = 0; 3076 if ((app.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 3077 debugFlags |= Zygote.DEBUG_ENABLE_DEBUGGER; 3078 // Also turn on CheckJNI for debuggable apps. It's quite 3079 // awkward to turn on otherwise. 3080 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 3081 } 3082 // Run the app in safe mode if its manifest requests so or the 3083 // system is booted in safe mode. 3084 if ((app.info.flags & ApplicationInfo.FLAG_VM_SAFE_MODE) != 0 || 3085 mSafeMode == true) { 3086 debugFlags |= Zygote.DEBUG_ENABLE_SAFEMODE; 3087 } 3088 if ("1".equals(SystemProperties.get("debug.checkjni"))) { 3089 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 3090 } 3091 if ("1".equals(SystemProperties.get("debug.jni.logging"))) { 3092 debugFlags |= Zygote.DEBUG_ENABLE_JNI_LOGGING; 3093 } 3094 if ("1".equals(SystemProperties.get("debug.assert"))) { 3095 debugFlags |= Zygote.DEBUG_ENABLE_ASSERT; 3096 } 3097 3098 String requiredAbi = (abiOverride != null) ? abiOverride : app.info.primaryCpuAbi; 3099 if (requiredAbi == null) { 3100 requiredAbi = Build.SUPPORTED_ABIS[0]; 3101 } 3102 3103 // Start the process. It will either succeed and return a result containing 3104 // the PID of the new process, or else throw a RuntimeException. 3105 boolean isActivityProcess = (entryPoint == null); 3106 if (entryPoint == null) entryPoint = "android.app.ActivityThread"; 3107 Process.ProcessStartResult startResult = Process.start(entryPoint, 3108 app.processName, uid, uid, gids, debugFlags, mountExternal, 3109 app.info.targetSdkVersion, app.info.seinfo, requiredAbi, entryPointArgs); 3110 3111 if (app.isolated) { 3112 mBatteryStatsService.addIsolatedUid(app.uid, app.info.uid); 3113 } 3114 mBatteryStatsService.noteProcessStart(app.processName, app.info.uid); 3115 3116 EventLog.writeEvent(EventLogTags.AM_PROC_START, 3117 UserHandle.getUserId(uid), startResult.pid, uid, 3118 app.processName, hostingType, 3119 hostingNameStr != null ? hostingNameStr : ""); 3120 3121 if (app.persistent) { 3122 Watchdog.getInstance().processStarted(app.processName, startResult.pid); 3123 } 3124 3125 StringBuilder buf = mStringBuilder; 3126 buf.setLength(0); 3127 buf.append("Start proc "); 3128 buf.append(app.processName); 3129 if (!isActivityProcess) { 3130 buf.append(" ["); 3131 buf.append(entryPoint); 3132 buf.append("]"); 3133 } 3134 buf.append(" for "); 3135 buf.append(hostingType); 3136 if (hostingNameStr != null) { 3137 buf.append(" "); 3138 buf.append(hostingNameStr); 3139 } 3140 buf.append(": pid="); 3141 buf.append(startResult.pid); 3142 buf.append(" uid="); 3143 buf.append(uid); 3144 buf.append(" gids={"); 3145 if (gids != null) { 3146 for (int gi=0; gi<gids.length; gi++) { 3147 if (gi != 0) buf.append(", "); 3148 buf.append(gids[gi]); 3149 3150 } 3151 } 3152 buf.append("}"); 3153 if (requiredAbi != null) { 3154 buf.append(" abi="); 3155 buf.append(requiredAbi); 3156 } 3157 Slog.i(TAG, buf.toString()); 3158 app.setPid(startResult.pid); 3159 app.usingWrapper = startResult.usingWrapper; 3160 app.removed = false; 3161 app.killedByAm = false; 3162 synchronized (mPidsSelfLocked) { 3163 this.mPidsSelfLocked.put(startResult.pid, app); 3164 if (isActivityProcess) { 3165 Message msg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 3166 msg.obj = app; 3167 mHandler.sendMessageDelayed(msg, startResult.usingWrapper 3168 ? PROC_START_TIMEOUT_WITH_WRAPPER : PROC_START_TIMEOUT); 3169 } 3170 } 3171 } catch (RuntimeException e) { 3172 // XXX do better error recovery. 3173 app.setPid(0); 3174 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 3175 if (app.isolated) { 3176 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 3177 } 3178 Slog.e(TAG, "Failure starting process " + app.processName, e); 3179 } 3180 } 3181 3182 void updateUsageStats(ActivityRecord component, boolean resumed) { 3183 if (DEBUG_SWITCH) Slog.d(TAG, "updateUsageStats: comp=" + component + "res=" + resumed); 3184 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 3185 if (resumed) { 3186 if (mUsageStatsService != null) { 3187 mUsageStatsService.reportEvent(component.realActivity, component.userId, 3188 System.currentTimeMillis(), 3189 UsageEvents.Event.MOVE_TO_FOREGROUND); 3190 } 3191 synchronized (stats) { 3192 stats.noteActivityResumedLocked(component.app.uid); 3193 } 3194 } else { 3195 if (mUsageStatsService != null) { 3196 mUsageStatsService.reportEvent(component.realActivity, component.userId, 3197 System.currentTimeMillis(), 3198 UsageEvents.Event.MOVE_TO_BACKGROUND); 3199 } 3200 synchronized (stats) { 3201 stats.noteActivityPausedLocked(component.app.uid); 3202 } 3203 } 3204 } 3205 3206 Intent getHomeIntent() { 3207 Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null); 3208 intent.setComponent(mTopComponent); 3209 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 3210 intent.addCategory(Intent.CATEGORY_HOME); 3211 } 3212 return intent; 3213 } 3214 3215 boolean startHomeActivityLocked(int userId) { 3216 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3217 && mTopAction == null) { 3218 // We are running in factory test mode, but unable to find 3219 // the factory test app, so just sit around displaying the 3220 // error message and don't try to start anything. 3221 return false; 3222 } 3223 Intent intent = getHomeIntent(); 3224 ActivityInfo aInfo = 3225 resolveActivityInfo(intent, STOCK_PM_FLAGS, userId); 3226 if (aInfo != null) { 3227 intent.setComponent(new ComponentName( 3228 aInfo.applicationInfo.packageName, aInfo.name)); 3229 // Don't do this if the home app is currently being 3230 // instrumented. 3231 aInfo = new ActivityInfo(aInfo); 3232 aInfo.applicationInfo = getAppInfoForUser(aInfo.applicationInfo, userId); 3233 ProcessRecord app = getProcessRecordLocked(aInfo.processName, 3234 aInfo.applicationInfo.uid, true); 3235 if (app == null || app.instrumentationClass == null) { 3236 intent.setFlags(intent.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK); 3237 mStackSupervisor.startHomeActivity(intent, aInfo); 3238 } 3239 } 3240 3241 return true; 3242 } 3243 3244 private ActivityInfo resolveActivityInfo(Intent intent, int flags, int userId) { 3245 ActivityInfo ai = null; 3246 ComponentName comp = intent.getComponent(); 3247 try { 3248 if (comp != null) { 3249 ai = AppGlobals.getPackageManager().getActivityInfo(comp, flags, userId); 3250 } else { 3251 ResolveInfo info = AppGlobals.getPackageManager().resolveIntent( 3252 intent, 3253 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 3254 flags, userId); 3255 3256 if (info != null) { 3257 ai = info.activityInfo; 3258 } 3259 } 3260 } catch (RemoteException e) { 3261 // ignore 3262 } 3263 3264 return ai; 3265 } 3266 3267 /** 3268 * Starts the "new version setup screen" if appropriate. 3269 */ 3270 void startSetupActivityLocked() { 3271 // Only do this once per boot. 3272 if (mCheckedForSetup) { 3273 return; 3274 } 3275 3276 // We will show this screen if the current one is a different 3277 // version than the last one shown, and we are not running in 3278 // low-level factory test mode. 3279 final ContentResolver resolver = mContext.getContentResolver(); 3280 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL && 3281 Settings.Global.getInt(resolver, 3282 Settings.Global.DEVICE_PROVISIONED, 0) != 0) { 3283 mCheckedForSetup = true; 3284 3285 // See if we should be showing the platform update setup UI. 3286 Intent intent = new Intent(Intent.ACTION_UPGRADE_SETUP); 3287 List<ResolveInfo> ris = mContext.getPackageManager() 3288 .queryIntentActivities(intent, PackageManager.GET_META_DATA); 3289 3290 // We don't allow third party apps to replace this. 3291 ResolveInfo ri = null; 3292 for (int i=0; ris != null && i<ris.size(); i++) { 3293 if ((ris.get(i).activityInfo.applicationInfo.flags 3294 & ApplicationInfo.FLAG_SYSTEM) != 0) { 3295 ri = ris.get(i); 3296 break; 3297 } 3298 } 3299 3300 if (ri != null) { 3301 String vers = ri.activityInfo.metaData != null 3302 ? ri.activityInfo.metaData.getString(Intent.METADATA_SETUP_VERSION) 3303 : null; 3304 if (vers == null && ri.activityInfo.applicationInfo.metaData != null) { 3305 vers = ri.activityInfo.applicationInfo.metaData.getString( 3306 Intent.METADATA_SETUP_VERSION); 3307 } 3308 String lastVers = Settings.Secure.getString( 3309 resolver, Settings.Secure.LAST_SETUP_SHOWN); 3310 if (vers != null && !vers.equals(lastVers)) { 3311 intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 3312 intent.setComponent(new ComponentName( 3313 ri.activityInfo.packageName, ri.activityInfo.name)); 3314 mStackSupervisor.startActivityLocked(null, intent, null, ri.activityInfo, 3315 null, null, null, null, 0, 0, 0, null, 0, null, false, null, null, 3316 null); 3317 } 3318 } 3319 } 3320 } 3321 3322 CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) { 3323 return mCompatModePackages.compatibilityInfoForPackageLocked(ai); 3324 } 3325 3326 void enforceNotIsolatedCaller(String caller) { 3327 if (UserHandle.isIsolated(Binder.getCallingUid())) { 3328 throw new SecurityException("Isolated process not allowed to call " + caller); 3329 } 3330 } 3331 3332 @Override 3333 public int getFrontActivityScreenCompatMode() { 3334 enforceNotIsolatedCaller("getFrontActivityScreenCompatMode"); 3335 synchronized (this) { 3336 return mCompatModePackages.getFrontActivityScreenCompatModeLocked(); 3337 } 3338 } 3339 3340 @Override 3341 public void setFrontActivityScreenCompatMode(int mode) { 3342 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3343 "setFrontActivityScreenCompatMode"); 3344 synchronized (this) { 3345 mCompatModePackages.setFrontActivityScreenCompatModeLocked(mode); 3346 } 3347 } 3348 3349 @Override 3350 public int getPackageScreenCompatMode(String packageName) { 3351 enforceNotIsolatedCaller("getPackageScreenCompatMode"); 3352 synchronized (this) { 3353 return mCompatModePackages.getPackageScreenCompatModeLocked(packageName); 3354 } 3355 } 3356 3357 @Override 3358 public void setPackageScreenCompatMode(String packageName, int mode) { 3359 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3360 "setPackageScreenCompatMode"); 3361 synchronized (this) { 3362 mCompatModePackages.setPackageScreenCompatModeLocked(packageName, mode); 3363 } 3364 } 3365 3366 @Override 3367 public boolean getPackageAskScreenCompat(String packageName) { 3368 enforceNotIsolatedCaller("getPackageAskScreenCompat"); 3369 synchronized (this) { 3370 return mCompatModePackages.getPackageAskCompatModeLocked(packageName); 3371 } 3372 } 3373 3374 @Override 3375 public void setPackageAskScreenCompat(String packageName, boolean ask) { 3376 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3377 "setPackageAskScreenCompat"); 3378 synchronized (this) { 3379 mCompatModePackages.setPackageAskCompatModeLocked(packageName, ask); 3380 } 3381 } 3382 3383 private void dispatchProcessesChanged() { 3384 int N; 3385 synchronized (this) { 3386 N = mPendingProcessChanges.size(); 3387 if (mActiveProcessChanges.length < N) { 3388 mActiveProcessChanges = new ProcessChangeItem[N]; 3389 } 3390 mPendingProcessChanges.toArray(mActiveProcessChanges); 3391 mAvailProcessChanges.addAll(mPendingProcessChanges); 3392 mPendingProcessChanges.clear(); 3393 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "*** Delivering " + N + " process changes"); 3394 } 3395 3396 int i = mProcessObservers.beginBroadcast(); 3397 while (i > 0) { 3398 i--; 3399 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3400 if (observer != null) { 3401 try { 3402 for (int j=0; j<N; j++) { 3403 ProcessChangeItem item = mActiveProcessChanges[j]; 3404 if ((item.changes&ProcessChangeItem.CHANGE_ACTIVITIES) != 0) { 3405 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "ACTIVITIES CHANGED pid=" 3406 + item.pid + " uid=" + item.uid + ": " 3407 + item.foregroundActivities); 3408 observer.onForegroundActivitiesChanged(item.pid, item.uid, 3409 item.foregroundActivities); 3410 } 3411 if ((item.changes&ProcessChangeItem.CHANGE_PROCESS_STATE) != 0) { 3412 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "PROCSTATE CHANGED pid=" 3413 + item.pid + " uid=" + item.uid + ": " + item.processState); 3414 observer.onProcessStateChanged(item.pid, item.uid, item.processState); 3415 } 3416 } 3417 } catch (RemoteException e) { 3418 } 3419 } 3420 } 3421 mProcessObservers.finishBroadcast(); 3422 } 3423 3424 private void dispatchProcessDied(int pid, int uid) { 3425 int i = mProcessObservers.beginBroadcast(); 3426 while (i > 0) { 3427 i--; 3428 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3429 if (observer != null) { 3430 try { 3431 observer.onProcessDied(pid, uid); 3432 } catch (RemoteException e) { 3433 } 3434 } 3435 } 3436 mProcessObservers.finishBroadcast(); 3437 } 3438 3439 @Override 3440 public final int startActivity(IApplicationThread caller, String callingPackage, 3441 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3442 int startFlags, ProfilerInfo profilerInfo, Bundle options) { 3443 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo, 3444 resultWho, requestCode, startFlags, profilerInfo, options, 3445 UserHandle.getCallingUserId()); 3446 } 3447 3448 @Override 3449 public final int startActivityAsUser(IApplicationThread caller, String callingPackage, 3450 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3451 int startFlags, ProfilerInfo profilerInfo, Bundle options, int userId) { 3452 enforceNotIsolatedCaller("startActivity"); 3453 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3454 false, ALLOW_FULL_ONLY, "startActivity", null); 3455 // TODO: Switch to user app stacks here. 3456 return mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, 3457 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3458 profilerInfo, null, null, options, userId, null, null); 3459 } 3460 3461 @Override 3462 public final int startActivityAsCaller(IApplicationThread caller, String callingPackage, 3463 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3464 int startFlags, ProfilerInfo profilerInfo, Bundle options) { 3465 3466 // This is very dangerous -- it allows you to perform a start activity (including 3467 // permission grants) as any app that may launch one of your own activities. So 3468 // we will only allow this to be done from activities that are part of the core framework, 3469 // and then only when they are running as the system. 3470 final ActivityRecord sourceRecord; 3471 final int targetUid; 3472 final String targetPackage; 3473 synchronized (this) { 3474 if (resultTo == null) { 3475 throw new SecurityException("Must be called from an activity"); 3476 } 3477 sourceRecord = mStackSupervisor.isInAnyStackLocked(resultTo); 3478 if (sourceRecord == null) { 3479 throw new SecurityException("Called with bad activity token: " + resultTo); 3480 } 3481 if (!sourceRecord.info.packageName.equals("android")) { 3482 throw new SecurityException( 3483 "Must be called from an activity that is declared in the android package"); 3484 } 3485 if (sourceRecord.app == null) { 3486 throw new SecurityException("Called without a process attached to activity"); 3487 } 3488 if (UserHandle.getAppId(sourceRecord.app.uid) != Process.SYSTEM_UID) { 3489 // This is still okay, as long as this activity is running under the 3490 // uid of the original calling activity. 3491 if (sourceRecord.app.uid != sourceRecord.launchedFromUid) { 3492 throw new SecurityException( 3493 "Calling activity in uid " + sourceRecord.app.uid 3494 + " must be system uid or original calling uid " 3495 + sourceRecord.launchedFromUid); 3496 } 3497 } 3498 targetUid = sourceRecord.launchedFromUid; 3499 targetPackage = sourceRecord.launchedFromPackage; 3500 } 3501 3502 // TODO: Switch to user app stacks here. 3503 try { 3504 int ret = mStackSupervisor.startActivityMayWait(null, targetUid, targetPackage, intent, 3505 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, null, 3506 null, null, options, UserHandle.getUserId(sourceRecord.app.uid), null, null); 3507 return ret; 3508 } catch (SecurityException e) { 3509 // XXX need to figure out how to propagate to original app. 3510 // A SecurityException here is generally actually a fault of the original 3511 // calling activity (such as a fairly granting permissions), so propagate it 3512 // back to them. 3513 /* 3514 StringBuilder msg = new StringBuilder(); 3515 msg.append("While launching"); 3516 msg.append(intent.toString()); 3517 msg.append(": "); 3518 msg.append(e.getMessage()); 3519 */ 3520 throw e; 3521 } 3522 } 3523 3524 @Override 3525 public final WaitResult startActivityAndWait(IApplicationThread caller, String callingPackage, 3526 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3527 int startFlags, ProfilerInfo profilerInfo, Bundle options, int userId) { 3528 enforceNotIsolatedCaller("startActivityAndWait"); 3529 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3530 false, ALLOW_FULL_ONLY, "startActivityAndWait", null); 3531 WaitResult res = new WaitResult(); 3532 // TODO: Switch to user app stacks here. 3533 mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 3534 null, null, resultTo, resultWho, requestCode, startFlags, profilerInfo, res, null, 3535 options, userId, null, null); 3536 return res; 3537 } 3538 3539 @Override 3540 public final int startActivityWithConfig(IApplicationThread caller, String callingPackage, 3541 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3542 int startFlags, Configuration config, Bundle options, int userId) { 3543 enforceNotIsolatedCaller("startActivityWithConfig"); 3544 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3545 false, ALLOW_FULL_ONLY, "startActivityWithConfig", null); 3546 // TODO: Switch to user app stacks here. 3547 int ret = mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, 3548 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3549 null, null, config, options, userId, null, null); 3550 return ret; 3551 } 3552 3553 @Override 3554 public int startActivityIntentSender(IApplicationThread caller, 3555 IntentSender intent, Intent fillInIntent, String resolvedType, 3556 IBinder resultTo, String resultWho, int requestCode, 3557 int flagsMask, int flagsValues, Bundle options) { 3558 enforceNotIsolatedCaller("startActivityIntentSender"); 3559 // Refuse possible leaked file descriptors 3560 if (fillInIntent != null && fillInIntent.hasFileDescriptors()) { 3561 throw new IllegalArgumentException("File descriptors passed in Intent"); 3562 } 3563 3564 IIntentSender sender = intent.getTarget(); 3565 if (!(sender instanceof PendingIntentRecord)) { 3566 throw new IllegalArgumentException("Bad PendingIntent object"); 3567 } 3568 3569 PendingIntentRecord pir = (PendingIntentRecord)sender; 3570 3571 synchronized (this) { 3572 // If this is coming from the currently resumed activity, it is 3573 // effectively saying that app switches are allowed at this point. 3574 final ActivityStack stack = getFocusedStack(); 3575 if (stack.mResumedActivity != null && 3576 stack.mResumedActivity.info.applicationInfo.uid == Binder.getCallingUid()) { 3577 mAppSwitchesAllowedTime = 0; 3578 } 3579 } 3580 int ret = pir.sendInner(0, fillInIntent, resolvedType, null, null, 3581 resultTo, resultWho, requestCode, flagsMask, flagsValues, options, null); 3582 return ret; 3583 } 3584 3585 @Override 3586 public int startVoiceActivity(String callingPackage, int callingPid, int callingUid, 3587 Intent intent, String resolvedType, IVoiceInteractionSession session, 3588 IVoiceInteractor interactor, int startFlags, ProfilerInfo profilerInfo, 3589 Bundle options, int userId) { 3590 if (checkCallingPermission(Manifest.permission.BIND_VOICE_INTERACTION) 3591 != PackageManager.PERMISSION_GRANTED) { 3592 String msg = "Permission Denial: startVoiceActivity() from pid=" 3593 + Binder.getCallingPid() 3594 + ", uid=" + Binder.getCallingUid() 3595 + " requires " + android.Manifest.permission.BIND_VOICE_INTERACTION; 3596 Slog.w(TAG, msg); 3597 throw new SecurityException(msg); 3598 } 3599 if (session == null || interactor == null) { 3600 throw new NullPointerException("null session or interactor"); 3601 } 3602 userId = handleIncomingUser(callingPid, callingUid, userId, 3603 false, ALLOW_FULL_ONLY, "startVoiceActivity", null); 3604 // TODO: Switch to user app stacks here. 3605 return mStackSupervisor.startActivityMayWait(null, callingUid, callingPackage, intent, 3606 resolvedType, session, interactor, null, null, 0, startFlags, profilerInfo, null, 3607 null, options, userId, null, null); 3608 } 3609 3610 @Override 3611 public boolean startNextMatchingActivity(IBinder callingActivity, 3612 Intent intent, Bundle options) { 3613 // Refuse possible leaked file descriptors 3614 if (intent != null && intent.hasFileDescriptors() == true) { 3615 throw new IllegalArgumentException("File descriptors passed in Intent"); 3616 } 3617 3618 synchronized (this) { 3619 final ActivityRecord r = ActivityRecord.isInStackLocked(callingActivity); 3620 if (r == null) { 3621 ActivityOptions.abort(options); 3622 return false; 3623 } 3624 if (r.app == null || r.app.thread == null) { 3625 // The caller is not running... d'oh! 3626 ActivityOptions.abort(options); 3627 return false; 3628 } 3629 intent = new Intent(intent); 3630 // The caller is not allowed to change the data. 3631 intent.setDataAndType(r.intent.getData(), r.intent.getType()); 3632 // And we are resetting to find the next component... 3633 intent.setComponent(null); 3634 3635 final boolean debug = ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0); 3636 3637 ActivityInfo aInfo = null; 3638 try { 3639 List<ResolveInfo> resolves = 3640 AppGlobals.getPackageManager().queryIntentActivities( 3641 intent, r.resolvedType, 3642 PackageManager.MATCH_DEFAULT_ONLY | STOCK_PM_FLAGS, 3643 UserHandle.getCallingUserId()); 3644 3645 // Look for the original activity in the list... 3646 final int N = resolves != null ? resolves.size() : 0; 3647 for (int i=0; i<N; i++) { 3648 ResolveInfo rInfo = resolves.get(i); 3649 if (rInfo.activityInfo.packageName.equals(r.packageName) 3650 && rInfo.activityInfo.name.equals(r.info.name)) { 3651 // We found the current one... the next matching is 3652 // after it. 3653 i++; 3654 if (i<N) { 3655 aInfo = resolves.get(i).activityInfo; 3656 } 3657 if (debug) { 3658 Slog.v(TAG, "Next matching activity: found current " + r.packageName 3659 + "/" + r.info.name); 3660 Slog.v(TAG, "Next matching activity: next is " + aInfo.packageName 3661 + "/" + aInfo.name); 3662 } 3663 break; 3664 } 3665 } 3666 } catch (RemoteException e) { 3667 } 3668 3669 if (aInfo == null) { 3670 // Nobody who is next! 3671 ActivityOptions.abort(options); 3672 if (debug) Slog.d(TAG, "Next matching activity: nothing found"); 3673 return false; 3674 } 3675 3676 intent.setComponent(new ComponentName( 3677 aInfo.applicationInfo.packageName, aInfo.name)); 3678 intent.setFlags(intent.getFlags()&~( 3679 Intent.FLAG_ACTIVITY_FORWARD_RESULT| 3680 Intent.FLAG_ACTIVITY_CLEAR_TOP| 3681 Intent.FLAG_ACTIVITY_MULTIPLE_TASK| 3682 Intent.FLAG_ACTIVITY_NEW_TASK)); 3683 3684 // Okay now we need to start the new activity, replacing the 3685 // currently running activity. This is a little tricky because 3686 // we want to start the new one as if the current one is finished, 3687 // but not finish the current one first so that there is no flicker. 3688 // And thus... 3689 final boolean wasFinishing = r.finishing; 3690 r.finishing = true; 3691 3692 // Propagate reply information over to the new activity. 3693 final ActivityRecord resultTo = r.resultTo; 3694 final String resultWho = r.resultWho; 3695 final int requestCode = r.requestCode; 3696 r.resultTo = null; 3697 if (resultTo != null) { 3698 resultTo.removeResultsLocked(r, resultWho, requestCode); 3699 } 3700 3701 final long origId = Binder.clearCallingIdentity(); 3702 int res = mStackSupervisor.startActivityLocked(r.app.thread, intent, 3703 r.resolvedType, aInfo, null, null, resultTo != null ? resultTo.appToken : null, 3704 resultWho, requestCode, -1, r.launchedFromUid, r.launchedFromPackage, 0, 3705 options, false, null, null, null); 3706 Binder.restoreCallingIdentity(origId); 3707 3708 r.finishing = wasFinishing; 3709 if (res != ActivityManager.START_SUCCESS) { 3710 return false; 3711 } 3712 return true; 3713 } 3714 } 3715 3716 @Override 3717 public final int startActivityFromRecents(int taskId, Bundle options) { 3718 if (checkCallingPermission(START_TASKS_FROM_RECENTS) != PackageManager.PERMISSION_GRANTED) { 3719 String msg = "Permission Denial: startActivityFromRecents called without " + 3720 START_TASKS_FROM_RECENTS; 3721 Slog.w(TAG, msg); 3722 throw new SecurityException(msg); 3723 } 3724 return startActivityFromRecentsInner(taskId, options); 3725 } 3726 3727 final int startActivityFromRecentsInner(int taskId, Bundle options) { 3728 final TaskRecord task; 3729 final int callingUid; 3730 final String callingPackage; 3731 final Intent intent; 3732 final int userId; 3733 synchronized (this) { 3734 task = recentTaskForIdLocked(taskId); 3735 if (task == null) { 3736 throw new IllegalArgumentException("Task " + taskId + " not found."); 3737 } 3738 callingUid = task.mCallingUid; 3739 callingPackage = task.mCallingPackage; 3740 intent = task.intent; 3741 intent.addFlags(Intent.FLAG_ACTIVITY_LAUNCHED_FROM_HISTORY); 3742 userId = task.userId; 3743 } 3744 return startActivityInPackage(callingUid, callingPackage, intent, null, null, null, 0, 0, 3745 options, userId, null, task); 3746 } 3747 3748 final int startActivityInPackage(int uid, String callingPackage, 3749 Intent intent, String resolvedType, IBinder resultTo, 3750 String resultWho, int requestCode, int startFlags, Bundle options, int userId, 3751 IActivityContainer container, TaskRecord inTask) { 3752 3753 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3754 false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 3755 3756 // TODO: Switch to user app stacks here. 3757 int ret = mStackSupervisor.startActivityMayWait(null, uid, callingPackage, intent, 3758 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3759 null, null, null, options, userId, container, inTask); 3760 return ret; 3761 } 3762 3763 @Override 3764 public final int startActivities(IApplicationThread caller, String callingPackage, 3765 Intent[] intents, String[] resolvedTypes, IBinder resultTo, Bundle options, 3766 int userId) { 3767 enforceNotIsolatedCaller("startActivities"); 3768 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3769 false, ALLOW_FULL_ONLY, "startActivity", null); 3770 // TODO: Switch to user app stacks here. 3771 int ret = mStackSupervisor.startActivities(caller, -1, callingPackage, intents, 3772 resolvedTypes, resultTo, options, userId); 3773 return ret; 3774 } 3775 3776 final int startActivitiesInPackage(int uid, String callingPackage, 3777 Intent[] intents, String[] resolvedTypes, IBinder resultTo, 3778 Bundle options, int userId) { 3779 3780 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3781 false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 3782 // TODO: Switch to user app stacks here. 3783 int ret = mStackSupervisor.startActivities(null, uid, callingPackage, intents, resolvedTypes, 3784 resultTo, options, userId); 3785 return ret; 3786 } 3787 3788 //explicitly remove thd old information in mRecentTasks when removing existing user. 3789 private void removeRecentTasksForUserLocked(int userId) { 3790 if(userId <= 0) { 3791 Slog.i(TAG, "Can't remove recent task on user " + userId); 3792 return; 3793 } 3794 3795 for (int i = mRecentTasks.size() - 1; i >= 0; --i) { 3796 TaskRecord tr = mRecentTasks.get(i); 3797 if (tr.userId == userId) { 3798 if(DEBUG_TASKS) Slog.i(TAG, "remove RecentTask " + tr 3799 + " when finishing user" + userId); 3800 mRecentTasks.remove(i); 3801 tr.removedFromRecents(mTaskPersister); 3802 } 3803 } 3804 3805 // Remove tasks from persistent storage. 3806 mTaskPersister.wakeup(null, true); 3807 } 3808 3809 /** 3810 * Update the recent tasks lists: make sure tasks should still be here (their 3811 * applications / activities still exist), update their availability, fixup ordering 3812 * of affiliations. 3813 */ 3814 void cleanupRecentTasksLocked(int userId) { 3815 if (mRecentTasks == null) { 3816 // Happens when called from the packagemanager broadcast before boot. 3817 return; 3818 } 3819 3820 final HashMap<ComponentName, ActivityInfo> availActCache = new HashMap<>(); 3821 final HashMap<String, ApplicationInfo> availAppCache = new HashMap<>(); 3822 final IPackageManager pm = AppGlobals.getPackageManager(); 3823 final ActivityInfo dummyAct = new ActivityInfo(); 3824 final ApplicationInfo dummyApp = new ApplicationInfo(); 3825 3826 int N = mRecentTasks.size(); 3827 3828 int[] users = userId == UserHandle.USER_ALL 3829 ? getUsersLocked() : new int[] { userId }; 3830 for (int user : users) { 3831 for (int i = 0; i < N; i++) { 3832 TaskRecord task = mRecentTasks.get(i); 3833 if (task.userId != user) { 3834 // Only look at tasks for the user ID of interest. 3835 continue; 3836 } 3837 if (task.autoRemoveRecents && task.getTopActivity() == null) { 3838 // This situation is broken, and we should just get rid of it now. 3839 mRecentTasks.remove(i); 3840 task.removedFromRecents(mTaskPersister); 3841 i--; 3842 N--; 3843 Slog.w(TAG, "Removing auto-remove without activity: " + task); 3844 continue; 3845 } 3846 // Check whether this activity is currently available. 3847 if (task.realActivity != null) { 3848 ActivityInfo ai = availActCache.get(task.realActivity); 3849 if (ai == null) { 3850 try { 3851 ai = pm.getActivityInfo(task.realActivity, 3852 PackageManager.GET_UNINSTALLED_PACKAGES 3853 | PackageManager.GET_DISABLED_COMPONENTS, user); 3854 } catch (RemoteException e) { 3855 // Will never happen. 3856 continue; 3857 } 3858 if (ai == null) { 3859 ai = dummyAct; 3860 } 3861 availActCache.put(task.realActivity, ai); 3862 } 3863 if (ai == dummyAct) { 3864 // This could be either because the activity no longer exists, or the 3865 // app is temporarily gone. For the former we want to remove the recents 3866 // entry; for the latter we want to mark it as unavailable. 3867 ApplicationInfo app = availAppCache.get(task.realActivity.getPackageName()); 3868 if (app == null) { 3869 try { 3870 app = pm.getApplicationInfo(task.realActivity.getPackageName(), 3871 PackageManager.GET_UNINSTALLED_PACKAGES 3872 | PackageManager.GET_DISABLED_COMPONENTS, user); 3873 } catch (RemoteException e) { 3874 // Will never happen. 3875 continue; 3876 } 3877 if (app == null) { 3878 app = dummyApp; 3879 } 3880 availAppCache.put(task.realActivity.getPackageName(), app); 3881 } 3882 if (app == dummyApp || (app.flags&ApplicationInfo.FLAG_INSTALLED) == 0) { 3883 // Doesn't exist any more! Good-bye. 3884 mRecentTasks.remove(i); 3885 task.removedFromRecents(mTaskPersister); 3886 i--; 3887 N--; 3888 Slog.w(TAG, "Removing no longer valid recent: " + task); 3889 continue; 3890 } else { 3891 // Otherwise just not available for now. 3892 if (task.isAvailable) { 3893 if (DEBUG_RECENTS) Slog.d(TAG, "Making recent unavailable: " 3894 + task); 3895 } 3896 task.isAvailable = false; 3897 } 3898 } else { 3899 if (!ai.enabled || !ai.applicationInfo.enabled 3900 || (ai.applicationInfo.flags&ApplicationInfo.FLAG_INSTALLED) == 0) { 3901 if (task.isAvailable) { 3902 if (DEBUG_RECENTS) Slog.d(TAG, "Making recent unavailable: " 3903 + task + " (enabled=" + ai.enabled + "/" 3904 + ai.applicationInfo.enabled + " flags=" 3905 + Integer.toHexString(ai.applicationInfo.flags) + ")"); 3906 } 3907 task.isAvailable = false; 3908 } else { 3909 if (!task.isAvailable) { 3910 if (DEBUG_RECENTS) Slog.d(TAG, "Making recent available: " 3911 + task); 3912 } 3913 task.isAvailable = true; 3914 } 3915 } 3916 } 3917 } 3918 } 3919 3920 // Verify the affiliate chain for each task. 3921 for (int i = 0; i < N; ) { 3922 TaskRecord task = mRecentTasks.remove(i); 3923 if (mTmpRecents.contains(task)) { 3924 continue; 3925 } 3926 int affiliatedTaskId = task.mAffiliatedTaskId; 3927 while (true) { 3928 TaskRecord next = task.mNextAffiliate; 3929 if (next == null) { 3930 break; 3931 } 3932 if (next.mAffiliatedTaskId != affiliatedTaskId) { 3933 Slog.e(TAG, "Error in Recents: next.affiliatedTaskId=" + 3934 next.mAffiliatedTaskId + " affiliatedTaskId=" + affiliatedTaskId); 3935 task.setNextAffiliate(null); 3936 if (next.mPrevAffiliate == task) { 3937 next.setPrevAffiliate(null); 3938 } 3939 break; 3940 } 3941 if (next.mPrevAffiliate != task) { 3942 Slog.e(TAG, "Error in Recents chain prev.mNextAffiliate=" + 3943 next.mPrevAffiliate + " task=" + task); 3944 next.setPrevAffiliate(null); 3945 task.setNextAffiliate(null); 3946 break; 3947 } 3948 if (!mRecentTasks.contains(next)) { 3949 Slog.e(TAG, "Error in Recents: next=" + next + " not in mRecentTasks"); 3950 task.setNextAffiliate(null); 3951 // We know that next.mPrevAffiliate is always task, from above, so clear 3952 // its previous affiliate. 3953 next.setPrevAffiliate(null); 3954 break; 3955 } 3956 task = next; 3957 } 3958 // task is now the end of the list 3959 do { 3960 mRecentTasks.remove(task); 3961 mRecentTasks.add(i++, task); 3962 mTmpRecents.add(task); 3963 task.inRecents = true; 3964 } while ((task = task.mPrevAffiliate) != null); 3965 } 3966 mTmpRecents.clear(); 3967 // mRecentTasks is now in sorted, affiliated order. 3968 } 3969 3970 private final boolean moveAffiliatedTasksToFront(TaskRecord task, int taskIndex) { 3971 int N = mRecentTasks.size(); 3972 TaskRecord top = task; 3973 int topIndex = taskIndex; 3974 while (top.mNextAffiliate != null && topIndex > 0) { 3975 top = top.mNextAffiliate; 3976 topIndex--; 3977 } 3978 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: adding affilliates starting at " 3979 + topIndex + " from intial " + taskIndex); 3980 // Find the end of the chain, doing a sanity check along the way. 3981 boolean sane = top.mAffiliatedTaskId == task.mAffiliatedTaskId; 3982 int endIndex = topIndex; 3983 TaskRecord prev = top; 3984 while (endIndex < N) { 3985 TaskRecord cur = mRecentTasks.get(endIndex); 3986 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: looking at next chain @" 3987 + endIndex + " " + cur); 3988 if (cur == top) { 3989 // Verify start of the chain. 3990 if (cur.mNextAffiliate != null || cur.mNextAffiliateTaskId != -1) { 3991 Slog.wtf(TAG, "Bad chain @" + endIndex 3992 + ": first task has next affiliate: " + prev); 3993 sane = false; 3994 break; 3995 } 3996 } else { 3997 // Verify middle of the chain's next points back to the one before. 3998 if (cur.mNextAffiliate != prev 3999 || cur.mNextAffiliateTaskId != prev.taskId) { 4000 Slog.wtf(TAG, "Bad chain @" + endIndex 4001 + ": middle task " + cur + " @" + endIndex 4002 + " has bad next affiliate " 4003 + cur.mNextAffiliate + " id " + cur.mNextAffiliateTaskId 4004 + ", expected " + prev); 4005 sane = false; 4006 break; 4007 } 4008 } 4009 if (cur.mPrevAffiliateTaskId == -1) { 4010 // Chain ends here. 4011 if (cur.mPrevAffiliate != null) { 4012 Slog.wtf(TAG, "Bad chain @" + endIndex 4013 + ": last task " + cur + " has previous affiliate " 4014 + cur.mPrevAffiliate); 4015 sane = false; 4016 } 4017 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: end of chain @" + endIndex); 4018 break; 4019 } else { 4020 // Verify middle of the chain's prev points to a valid item. 4021 if (cur.mPrevAffiliate == null) { 4022 Slog.wtf(TAG, "Bad chain @" + endIndex 4023 + ": task " + cur + " has previous affiliate " 4024 + cur.mPrevAffiliate + " but should be id " 4025 + cur.mPrevAffiliate); 4026 sane = false; 4027 break; 4028 } 4029 } 4030 if (cur.mAffiliatedTaskId != task.mAffiliatedTaskId) { 4031 Slog.wtf(TAG, "Bad chain @" + endIndex 4032 + ": task " + cur + " has affiliated id " 4033 + cur.mAffiliatedTaskId + " but should be " 4034 + task.mAffiliatedTaskId); 4035 sane = false; 4036 break; 4037 } 4038 prev = cur; 4039 endIndex++; 4040 if (endIndex >= N) { 4041 Slog.wtf(TAG, "Bad chain ran off index " + endIndex 4042 + ": last task " + prev); 4043 sane = false; 4044 break; 4045 } 4046 } 4047 if (sane) { 4048 if (endIndex < taskIndex) { 4049 Slog.wtf(TAG, "Bad chain @" + endIndex 4050 + ": did not extend to task " + task + " @" + taskIndex); 4051 sane = false; 4052 } 4053 } 4054 if (sane) { 4055 // All looks good, we can just move all of the affiliated tasks 4056 // to the top. 4057 for (int i=topIndex; i<=endIndex; i++) { 4058 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: moving affiliated " + task 4059 + " from " + i + " to " + (i-topIndex)); 4060 TaskRecord cur = mRecentTasks.remove(i); 4061 mRecentTasks.add(i-topIndex, cur); 4062 } 4063 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: done moving tasks " + topIndex 4064 + " to " + endIndex); 4065 return true; 4066 } 4067 4068 // Whoops, couldn't do it. 4069 return false; 4070 } 4071 4072 final void addRecentTaskLocked(TaskRecord task) { 4073 final boolean isAffiliated = task.mAffiliatedTaskId != task.taskId 4074 || task.mNextAffiliateTaskId != -1 || task.mPrevAffiliateTaskId != -1; 4075 4076 int N = mRecentTasks.size(); 4077 // Quick case: check if the top-most recent task is the same. 4078 if (!isAffiliated && N > 0 && mRecentTasks.get(0) == task) { 4079 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: already at top: " + task); 4080 return; 4081 } 4082 // Another quick case: check if this is part of a set of affiliated 4083 // tasks that are at the top. 4084 if (isAffiliated && N > 0 && task.inRecents 4085 && task.mAffiliatedTaskId == mRecentTasks.get(0).mAffiliatedTaskId) { 4086 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: affiliated " + mRecentTasks.get(0) 4087 + " at top when adding " + task); 4088 return; 4089 } 4090 // Another quick case: never add voice sessions. 4091 if (task.voiceSession != null) { 4092 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: not adding voice interaction " + task); 4093 return; 4094 } 4095 4096 boolean needAffiliationFix = false; 4097 4098 // Slightly less quick case: the task is already in recents, so all we need 4099 // to do is move it. 4100 if (task.inRecents) { 4101 int taskIndex = mRecentTasks.indexOf(task); 4102 if (taskIndex >= 0) { 4103 if (!isAffiliated) { 4104 // Simple case: this is not an affiliated task, so we just move it to the front. 4105 mRecentTasks.remove(taskIndex); 4106 mRecentTasks.add(0, task); 4107 notifyTaskPersisterLocked(task, false); 4108 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: moving to top " + task 4109 + " from " + taskIndex); 4110 return; 4111 } else { 4112 // More complicated: need to keep all affiliated tasks together. 4113 if (moveAffiliatedTasksToFront(task, taskIndex)) { 4114 // All went well. 4115 return; 4116 } 4117 4118 // Uh oh... something bad in the affiliation chain, try to rebuild 4119 // everything and then go through our general path of adding a new task. 4120 needAffiliationFix = true; 4121 } 4122 } else { 4123 Slog.wtf(TAG, "Task with inRecent not in recents: " + task); 4124 needAffiliationFix = true; 4125 } 4126 } 4127 4128 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: trimming tasks for " + task); 4129 trimRecentsForTask(task, true); 4130 4131 N = mRecentTasks.size(); 4132 while (N >= ActivityManager.getMaxRecentTasksStatic()) { 4133 final TaskRecord tr = mRecentTasks.remove(N - 1); 4134 tr.removedFromRecents(mTaskPersister); 4135 N--; 4136 } 4137 task.inRecents = true; 4138 if (!isAffiliated || needAffiliationFix) { 4139 // If this is a simple non-affiliated task, or we had some failure trying to 4140 // handle it as part of an affilated task, then just place it at the top. 4141 mRecentTasks.add(0, task); 4142 } else if (isAffiliated) { 4143 // If this is a new affiliated task, then move all of the affiliated tasks 4144 // to the front and insert this new one. 4145 TaskRecord other = task.mNextAffiliate; 4146 if (other == null) { 4147 other = task.mPrevAffiliate; 4148 } 4149 if (other != null) { 4150 int otherIndex = mRecentTasks.indexOf(other); 4151 if (otherIndex >= 0) { 4152 // Insert new task at appropriate location. 4153 int taskIndex; 4154 if (other == task.mNextAffiliate) { 4155 // We found the index of our next affiliation, which is who is 4156 // before us in the list, so add after that point. 4157 taskIndex = otherIndex+1; 4158 } else { 4159 // We found the index of our previous affiliation, which is who is 4160 // after us in the list, so add at their position. 4161 taskIndex = otherIndex; 4162 } 4163 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: new affiliated task added at " 4164 + taskIndex + ": " + task); 4165 mRecentTasks.add(taskIndex, task); 4166 4167 // Now move everything to the front. 4168 if (moveAffiliatedTasksToFront(task, taskIndex)) { 4169 // All went well. 4170 return; 4171 } 4172 4173 // Uh oh... something bad in the affiliation chain, try to rebuild 4174 // everything and then go through our general path of adding a new task. 4175 needAffiliationFix = true; 4176 } else { 4177 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: couldn't find other affiliation " 4178 + other); 4179 needAffiliationFix = true; 4180 } 4181 } else { 4182 if (DEBUG_RECENTS) Slog.d(TAG, 4183 "addRecent: adding affiliated task without next/prev:" + task); 4184 needAffiliationFix = true; 4185 } 4186 } 4187 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: adding " + task); 4188 4189 if (needAffiliationFix) { 4190 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: regrouping affiliations"); 4191 cleanupRecentTasksLocked(task.userId); 4192 } 4193 } 4194 4195 /** 4196 * If needed, remove oldest existing entries in recents that are for the same kind 4197 * of task as the given one. 4198 */ 4199 int trimRecentsForTask(TaskRecord task, boolean doTrim) { 4200 int N = mRecentTasks.size(); 4201 final Intent intent = task.intent; 4202 final boolean document = intent != null && intent.isDocument(); 4203 4204 int maxRecents = task.maxRecents - 1; 4205 for (int i=0; i<N; i++) { 4206 final TaskRecord tr = mRecentTasks.get(i); 4207 if (task != tr) { 4208 if (task.userId != tr.userId) { 4209 continue; 4210 } 4211 if (i > MAX_RECENT_BITMAPS) { 4212 tr.freeLastThumbnail(); 4213 } 4214 final Intent trIntent = tr.intent; 4215 if ((task.affinity == null || !task.affinity.equals(tr.affinity)) && 4216 (intent == null || !intent.filterEquals(trIntent))) { 4217 continue; 4218 } 4219 final boolean trIsDocument = trIntent != null && trIntent.isDocument(); 4220 if (document && trIsDocument) { 4221 // These are the same document activity (not necessarily the same doc). 4222 if (maxRecents > 0) { 4223 --maxRecents; 4224 continue; 4225 } 4226 // Hit the maximum number of documents for this task. Fall through 4227 // and remove this document from recents. 4228 } else if (document || trIsDocument) { 4229 // Only one of these is a document. Not the droid we're looking for. 4230 continue; 4231 } 4232 } 4233 4234 if (!doTrim) { 4235 // If the caller is not actually asking for a trim, just tell them we reached 4236 // a point where the trim would happen. 4237 return i; 4238 } 4239 4240 // Either task and tr are the same or, their affinities match or their intents match 4241 // and neither of them is a document, or they are documents using the same activity 4242 // and their maxRecents has been reached. 4243 tr.disposeThumbnail(); 4244 mRecentTasks.remove(i); 4245 if (task != tr) { 4246 tr.removedFromRecents(mTaskPersister); 4247 } 4248 i--; 4249 N--; 4250 if (task.intent == null) { 4251 // If the new recent task we are adding is not fully 4252 // specified, then replace it with the existing recent task. 4253 task = tr; 4254 } 4255 notifyTaskPersisterLocked(tr, false); 4256 } 4257 4258 return -1; 4259 } 4260 4261 @Override 4262 public void reportActivityFullyDrawn(IBinder token) { 4263 synchronized (this) { 4264 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4265 if (r == null) { 4266 return; 4267 } 4268 r.reportFullyDrawnLocked(); 4269 } 4270 } 4271 4272 @Override 4273 public void setRequestedOrientation(IBinder token, int requestedOrientation) { 4274 synchronized (this) { 4275 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4276 if (r == null) { 4277 return; 4278 } 4279 final long origId = Binder.clearCallingIdentity(); 4280 mWindowManager.setAppOrientation(r.appToken, requestedOrientation); 4281 Configuration config = mWindowManager.updateOrientationFromAppTokens( 4282 mConfiguration, r.mayFreezeScreenLocked(r.app) ? r.appToken : null); 4283 if (config != null) { 4284 r.frozenBeforeDestroy = true; 4285 if (!updateConfigurationLocked(config, r, false, false)) { 4286 mStackSupervisor.resumeTopActivitiesLocked(); 4287 } 4288 } 4289 Binder.restoreCallingIdentity(origId); 4290 } 4291 } 4292 4293 @Override 4294 public int getRequestedOrientation(IBinder token) { 4295 synchronized (this) { 4296 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4297 if (r == null) { 4298 return ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED; 4299 } 4300 return mWindowManager.getAppOrientation(r.appToken); 4301 } 4302 } 4303 4304 /** 4305 * This is the internal entry point for handling Activity.finish(). 4306 * 4307 * @param token The Binder token referencing the Activity we want to finish. 4308 * @param resultCode Result code, if any, from this Activity. 4309 * @param resultData Result data (Intent), if any, from this Activity. 4310 * @param finishTask Whether to finish the task associated with this Activity. Only applies to 4311 * the root Activity in the task. 4312 * 4313 * @return Returns true if the activity successfully finished, or false if it is still running. 4314 */ 4315 @Override 4316 public final boolean finishActivity(IBinder token, int resultCode, Intent resultData, 4317 boolean finishTask) { 4318 // Refuse possible leaked file descriptors 4319 if (resultData != null && resultData.hasFileDescriptors() == true) { 4320 throw new IllegalArgumentException("File descriptors passed in Intent"); 4321 } 4322 4323 synchronized(this) { 4324 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4325 if (r == null) { 4326 return true; 4327 } 4328 // Keep track of the root activity of the task before we finish it 4329 TaskRecord tr = r.task; 4330 ActivityRecord rootR = tr.getRootActivity(); 4331 // Do not allow task to finish in Lock Task mode. 4332 if (tr == mStackSupervisor.mLockTaskModeTask) { 4333 if (rootR == r) { 4334 mStackSupervisor.showLockTaskToast(); 4335 return false; 4336 } 4337 } 4338 if (mController != null) { 4339 // Find the first activity that is not finishing. 4340 ActivityRecord next = r.task.stack.topRunningActivityLocked(token, 0); 4341 if (next != null) { 4342 // ask watcher if this is allowed 4343 boolean resumeOK = true; 4344 try { 4345 resumeOK = mController.activityResuming(next.packageName); 4346 } catch (RemoteException e) { 4347 mController = null; 4348 Watchdog.getInstance().setActivityController(null); 4349 } 4350 4351 if (!resumeOK) { 4352 return false; 4353 } 4354 } 4355 } 4356 final long origId = Binder.clearCallingIdentity(); 4357 try { 4358 boolean res; 4359 if (finishTask && r == rootR) { 4360 // If requested, remove the task that is associated to this activity only if it 4361 // was the root activity in the task. The result code and data is ignored because 4362 // we don't support returning them across task boundaries. 4363 res = removeTaskByIdLocked(tr.taskId, 0); 4364 } else { 4365 res = tr.stack.requestFinishActivityLocked(token, resultCode, 4366 resultData, "app-request", true); 4367 } 4368 return res; 4369 } finally { 4370 Binder.restoreCallingIdentity(origId); 4371 } 4372 } 4373 } 4374 4375 @Override 4376 public final void finishHeavyWeightApp() { 4377 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4378 != PackageManager.PERMISSION_GRANTED) { 4379 String msg = "Permission Denial: finishHeavyWeightApp() from pid=" 4380 + Binder.getCallingPid() 4381 + ", uid=" + Binder.getCallingUid() 4382 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4383 Slog.w(TAG, msg); 4384 throw new SecurityException(msg); 4385 } 4386 4387 synchronized(this) { 4388 if (mHeavyWeightProcess == null) { 4389 return; 4390 } 4391 4392 ArrayList<ActivityRecord> activities = new ArrayList<ActivityRecord>( 4393 mHeavyWeightProcess.activities); 4394 for (int i=0; i<activities.size(); i++) { 4395 ActivityRecord r = activities.get(i); 4396 if (!r.finishing) { 4397 r.task.stack.finishActivityLocked(r, Activity.RESULT_CANCELED, 4398 null, "finish-heavy", true); 4399 } 4400 } 4401 4402 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 4403 mHeavyWeightProcess.userId, 0)); 4404 mHeavyWeightProcess = null; 4405 } 4406 } 4407 4408 @Override 4409 public void crashApplication(int uid, int initialPid, String packageName, 4410 String message) { 4411 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4412 != PackageManager.PERMISSION_GRANTED) { 4413 String msg = "Permission Denial: crashApplication() from pid=" 4414 + Binder.getCallingPid() 4415 + ", uid=" + Binder.getCallingUid() 4416 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4417 Slog.w(TAG, msg); 4418 throw new SecurityException(msg); 4419 } 4420 4421 synchronized(this) { 4422 ProcessRecord proc = null; 4423 4424 // Figure out which process to kill. We don't trust that initialPid 4425 // still has any relation to current pids, so must scan through the 4426 // list. 4427 synchronized (mPidsSelfLocked) { 4428 for (int i=0; i<mPidsSelfLocked.size(); i++) { 4429 ProcessRecord p = mPidsSelfLocked.valueAt(i); 4430 if (p.uid != uid) { 4431 continue; 4432 } 4433 if (p.pid == initialPid) { 4434 proc = p; 4435 break; 4436 } 4437 if (p.pkgList.containsKey(packageName)) { 4438 proc = p; 4439 } 4440 } 4441 } 4442 4443 if (proc == null) { 4444 Slog.w(TAG, "crashApplication: nothing for uid=" + uid 4445 + " initialPid=" + initialPid 4446 + " packageName=" + packageName); 4447 return; 4448 } 4449 4450 if (proc.thread != null) { 4451 if (proc.pid == Process.myPid()) { 4452 Log.w(TAG, "crashApplication: trying to crash self!"); 4453 return; 4454 } 4455 long ident = Binder.clearCallingIdentity(); 4456 try { 4457 proc.thread.scheduleCrash(message); 4458 } catch (RemoteException e) { 4459 } 4460 Binder.restoreCallingIdentity(ident); 4461 } 4462 } 4463 } 4464 4465 @Override 4466 public final void finishSubActivity(IBinder token, String resultWho, 4467 int requestCode) { 4468 synchronized(this) { 4469 final long origId = Binder.clearCallingIdentity(); 4470 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4471 if (r != null) { 4472 r.task.stack.finishSubActivityLocked(r, resultWho, requestCode); 4473 } 4474 Binder.restoreCallingIdentity(origId); 4475 } 4476 } 4477 4478 @Override 4479 public boolean finishActivityAffinity(IBinder token) { 4480 synchronized(this) { 4481 final long origId = Binder.clearCallingIdentity(); 4482 try { 4483 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4484 4485 ActivityRecord rootR = r.task.getRootActivity(); 4486 // Do not allow task to finish in Lock Task mode. 4487 if (r.task == mStackSupervisor.mLockTaskModeTask) { 4488 if (rootR == r) { 4489 mStackSupervisor.showLockTaskToast(); 4490 return false; 4491 } 4492 } 4493 boolean res = false; 4494 if (r != null) { 4495 res = r.task.stack.finishActivityAffinityLocked(r); 4496 } 4497 return res; 4498 } finally { 4499 Binder.restoreCallingIdentity(origId); 4500 } 4501 } 4502 } 4503 4504 @Override 4505 public void finishVoiceTask(IVoiceInteractionSession session) { 4506 synchronized(this) { 4507 final long origId = Binder.clearCallingIdentity(); 4508 try { 4509 mStackSupervisor.finishVoiceTask(session); 4510 } finally { 4511 Binder.restoreCallingIdentity(origId); 4512 } 4513 } 4514 4515 } 4516 4517 @Override 4518 public boolean releaseActivityInstance(IBinder token) { 4519 synchronized(this) { 4520 final long origId = Binder.clearCallingIdentity(); 4521 try { 4522 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4523 if (r.task == null || r.task.stack == null) { 4524 return false; 4525 } 4526 return r.task.stack.safelyDestroyActivityLocked(r, "app-req"); 4527 } finally { 4528 Binder.restoreCallingIdentity(origId); 4529 } 4530 } 4531 } 4532 4533 @Override 4534 public void releaseSomeActivities(IApplicationThread appInt) { 4535 synchronized(this) { 4536 final long origId = Binder.clearCallingIdentity(); 4537 try { 4538 ProcessRecord app = getRecordForAppLocked(appInt); 4539 mStackSupervisor.releaseSomeActivitiesLocked(app, "low-mem"); 4540 } finally { 4541 Binder.restoreCallingIdentity(origId); 4542 } 4543 } 4544 } 4545 4546 @Override 4547 public boolean willActivityBeVisible(IBinder token) { 4548 synchronized(this) { 4549 ActivityStack stack = ActivityRecord.getStackLocked(token); 4550 if (stack != null) { 4551 return stack.willActivityBeVisibleLocked(token); 4552 } 4553 return false; 4554 } 4555 } 4556 4557 @Override 4558 public void overridePendingTransition(IBinder token, String packageName, 4559 int enterAnim, int exitAnim) { 4560 synchronized(this) { 4561 ActivityRecord self = ActivityRecord.isInStackLocked(token); 4562 if (self == null) { 4563 return; 4564 } 4565 4566 final long origId = Binder.clearCallingIdentity(); 4567 4568 if (self.state == ActivityState.RESUMED 4569 || self.state == ActivityState.PAUSING) { 4570 mWindowManager.overridePendingAppTransition(packageName, 4571 enterAnim, exitAnim, null); 4572 } 4573 4574 Binder.restoreCallingIdentity(origId); 4575 } 4576 } 4577 4578 /** 4579 * Main function for removing an existing process from the activity manager 4580 * as a result of that process going away. Clears out all connections 4581 * to the process. 4582 */ 4583 private final void handleAppDiedLocked(ProcessRecord app, 4584 boolean restarting, boolean allowRestart) { 4585 int pid = app.pid; 4586 cleanUpApplicationRecordLocked(app, restarting, allowRestart, -1); 4587 if (!restarting) { 4588 removeLruProcessLocked(app); 4589 if (pid > 0) { 4590 ProcessList.remove(pid); 4591 } 4592 } 4593 4594 if (mProfileProc == app) { 4595 clearProfilerLocked(); 4596 } 4597 4598 // Remove this application's activities from active lists. 4599 boolean hasVisibleActivities = mStackSupervisor.handleAppDiedLocked(app); 4600 4601 app.activities.clear(); 4602 4603 if (app.instrumentationClass != null) { 4604 Slog.w(TAG, "Crash of app " + app.processName 4605 + " running instrumentation " + app.instrumentationClass); 4606 Bundle info = new Bundle(); 4607 info.putString("shortMsg", "Process crashed."); 4608 finishInstrumentationLocked(app, Activity.RESULT_CANCELED, info); 4609 } 4610 4611 if (!restarting) { 4612 if (!mStackSupervisor.resumeTopActivitiesLocked()) { 4613 // If there was nothing to resume, and we are not already 4614 // restarting this process, but there is a visible activity that 4615 // is hosted by the process... then make sure all visible 4616 // activities are running, taking care of restarting this 4617 // process. 4618 if (hasVisibleActivities) { 4619 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 4620 } 4621 } 4622 } 4623 } 4624 4625 private final int getLRURecordIndexForAppLocked(IApplicationThread thread) { 4626 IBinder threadBinder = thread.asBinder(); 4627 // Find the application record. 4628 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4629 ProcessRecord rec = mLruProcesses.get(i); 4630 if (rec.thread != null && rec.thread.asBinder() == threadBinder) { 4631 return i; 4632 } 4633 } 4634 return -1; 4635 } 4636 4637 final ProcessRecord getRecordForAppLocked( 4638 IApplicationThread thread) { 4639 if (thread == null) { 4640 return null; 4641 } 4642 4643 int appIndex = getLRURecordIndexForAppLocked(thread); 4644 return appIndex >= 0 ? mLruProcesses.get(appIndex) : null; 4645 } 4646 4647 final void doLowMemReportIfNeededLocked(ProcessRecord dyingProc) { 4648 // If there are no longer any background processes running, 4649 // and the app that died was not running instrumentation, 4650 // then tell everyone we are now low on memory. 4651 boolean haveBg = false; 4652 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4653 ProcessRecord rec = mLruProcesses.get(i); 4654 if (rec.thread != null 4655 && rec.setProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 4656 haveBg = true; 4657 break; 4658 } 4659 } 4660 4661 if (!haveBg) { 4662 boolean doReport = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 4663 if (doReport) { 4664 long now = SystemClock.uptimeMillis(); 4665 if (now < (mLastMemUsageReportTime+5*60*1000)) { 4666 doReport = false; 4667 } else { 4668 mLastMemUsageReportTime = now; 4669 } 4670 } 4671 final ArrayList<ProcessMemInfo> memInfos 4672 = doReport ? new ArrayList<ProcessMemInfo>(mLruProcesses.size()) : null; 4673 EventLog.writeEvent(EventLogTags.AM_LOW_MEMORY, mLruProcesses.size()); 4674 long now = SystemClock.uptimeMillis(); 4675 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4676 ProcessRecord rec = mLruProcesses.get(i); 4677 if (rec == dyingProc || rec.thread == null) { 4678 continue; 4679 } 4680 if (doReport) { 4681 memInfos.add(new ProcessMemInfo(rec.processName, rec.pid, rec.setAdj, 4682 rec.setProcState, rec.adjType, rec.makeAdjReason())); 4683 } 4684 if ((rec.lastLowMemory+GC_MIN_INTERVAL) <= now) { 4685 // The low memory report is overriding any current 4686 // state for a GC request. Make sure to do 4687 // heavy/important/visible/foreground processes first. 4688 if (rec.setAdj <= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 4689 rec.lastRequestedGc = 0; 4690 } else { 4691 rec.lastRequestedGc = rec.lastLowMemory; 4692 } 4693 rec.reportLowMemory = true; 4694 rec.lastLowMemory = now; 4695 mProcessesToGc.remove(rec); 4696 addProcessToGcListLocked(rec); 4697 } 4698 } 4699 if (doReport) { 4700 Message msg = mHandler.obtainMessage(REPORT_MEM_USAGE_MSG, memInfos); 4701 mHandler.sendMessage(msg); 4702 } 4703 scheduleAppGcsLocked(); 4704 } 4705 } 4706 4707 final void appDiedLocked(ProcessRecord app) { 4708 appDiedLocked(app, app.pid, app.thread); 4709 } 4710 4711 final void appDiedLocked(ProcessRecord app, int pid, 4712 IApplicationThread thread) { 4713 4714 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 4715 synchronized (stats) { 4716 stats.noteProcessDiedLocked(app.info.uid, pid); 4717 } 4718 4719 Process.killProcessGroup(app.info.uid, pid); 4720 4721 // Clean up already done if the process has been re-started. 4722 if (app.pid == pid && app.thread != null && 4723 app.thread.asBinder() == thread.asBinder()) { 4724 boolean doLowMem = app.instrumentationClass == null; 4725 boolean doOomAdj = doLowMem; 4726 if (!app.killedByAm) { 4727 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4728 + ") has died."); 4729 mAllowLowerMemLevel = true; 4730 } else { 4731 // Note that we always want to do oom adj to update our state with the 4732 // new number of procs. 4733 mAllowLowerMemLevel = false; 4734 doLowMem = false; 4735 } 4736 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4737 if (DEBUG_CLEANUP) Slog.v( 4738 TAG, "Dying app: " + app + ", pid: " + pid 4739 + ", thread: " + thread.asBinder()); 4740 handleAppDiedLocked(app, false, true); 4741 4742 if (doOomAdj) { 4743 updateOomAdjLocked(); 4744 } 4745 if (doLowMem) { 4746 doLowMemReportIfNeededLocked(app); 4747 } 4748 } else if (app.pid != pid) { 4749 // A new process has already been started. 4750 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4751 + ") has died and restarted (pid " + app.pid + ")."); 4752 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4753 } else if (DEBUG_PROCESSES) { 4754 Slog.d(TAG, "Received spurious death notification for thread " 4755 + thread.asBinder()); 4756 } 4757 } 4758 4759 /** 4760 * If a stack trace dump file is configured, dump process stack traces. 4761 * @param clearTraces causes the dump file to be erased prior to the new 4762 * traces being written, if true; when false, the new traces will be 4763 * appended to any existing file content. 4764 * @param firstPids of dalvik VM processes to dump stack traces for first 4765 * @param lastPids of dalvik VM processes to dump stack traces for last 4766 * @param nativeProcs optional list of native process names to dump stack crawls 4767 * @return file containing stack traces, or null if no dump file is configured 4768 */ 4769 public static File dumpStackTraces(boolean clearTraces, ArrayList<Integer> firstPids, 4770 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4771 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4772 if (tracesPath == null || tracesPath.length() == 0) { 4773 return null; 4774 } 4775 4776 File tracesFile = new File(tracesPath); 4777 try { 4778 File tracesDir = tracesFile.getParentFile(); 4779 if (!tracesDir.exists()) { 4780 tracesFile.mkdirs(); 4781 if (!SELinux.restorecon(tracesDir)) { 4782 return null; 4783 } 4784 } 4785 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4786 4787 if (clearTraces && tracesFile.exists()) tracesFile.delete(); 4788 tracesFile.createNewFile(); 4789 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4790 } catch (IOException e) { 4791 Slog.w(TAG, "Unable to prepare ANR traces file: " + tracesPath, e); 4792 return null; 4793 } 4794 4795 dumpStackTraces(tracesPath, firstPids, processCpuTracker, lastPids, nativeProcs); 4796 return tracesFile; 4797 } 4798 4799 private static void dumpStackTraces(String tracesPath, ArrayList<Integer> firstPids, 4800 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4801 // Use a FileObserver to detect when traces finish writing. 4802 // The order of traces is considered important to maintain for legibility. 4803 FileObserver observer = new FileObserver(tracesPath, FileObserver.CLOSE_WRITE) { 4804 @Override 4805 public synchronized void onEvent(int event, String path) { notify(); } 4806 }; 4807 4808 try { 4809 observer.startWatching(); 4810 4811 // First collect all of the stacks of the most important pids. 4812 if (firstPids != null) { 4813 try { 4814 int num = firstPids.size(); 4815 for (int i = 0; i < num; i++) { 4816 synchronized (observer) { 4817 Process.sendSignal(firstPids.get(i), Process.SIGNAL_QUIT); 4818 observer.wait(200); // Wait for write-close, give up after 200msec 4819 } 4820 } 4821 } catch (InterruptedException e) { 4822 Log.wtf(TAG, e); 4823 } 4824 } 4825 4826 // Next collect the stacks of the native pids 4827 if (nativeProcs != null) { 4828 int[] pids = Process.getPidsForCommands(nativeProcs); 4829 if (pids != null) { 4830 for (int pid : pids) { 4831 Debug.dumpNativeBacktraceToFile(pid, tracesPath); 4832 } 4833 } 4834 } 4835 4836 // Lastly, measure CPU usage. 4837 if (processCpuTracker != null) { 4838 processCpuTracker.init(); 4839 System.gc(); 4840 processCpuTracker.update(); 4841 try { 4842 synchronized (processCpuTracker) { 4843 processCpuTracker.wait(500); // measure over 1/2 second. 4844 } 4845 } catch (InterruptedException e) { 4846 } 4847 processCpuTracker.update(); 4848 4849 // We'll take the stack crawls of just the top apps using CPU. 4850 final int N = processCpuTracker.countWorkingStats(); 4851 int numProcs = 0; 4852 for (int i=0; i<N && numProcs<5; i++) { 4853 ProcessCpuTracker.Stats stats = processCpuTracker.getWorkingStats(i); 4854 if (lastPids.indexOfKey(stats.pid) >= 0) { 4855 numProcs++; 4856 try { 4857 synchronized (observer) { 4858 Process.sendSignal(stats.pid, Process.SIGNAL_QUIT); 4859 observer.wait(200); // Wait for write-close, give up after 200msec 4860 } 4861 } catch (InterruptedException e) { 4862 Log.wtf(TAG, e); 4863 } 4864 4865 } 4866 } 4867 } 4868 } finally { 4869 observer.stopWatching(); 4870 } 4871 } 4872 4873 final void logAppTooSlow(ProcessRecord app, long startTime, String msg) { 4874 if (true || IS_USER_BUILD) { 4875 return; 4876 } 4877 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4878 if (tracesPath == null || tracesPath.length() == 0) { 4879 return; 4880 } 4881 4882 StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads(); 4883 StrictMode.allowThreadDiskWrites(); 4884 try { 4885 final File tracesFile = new File(tracesPath); 4886 final File tracesDir = tracesFile.getParentFile(); 4887 final File tracesTmp = new File(tracesDir, "__tmp__"); 4888 try { 4889 if (!tracesDir.exists()) { 4890 tracesFile.mkdirs(); 4891 if (!SELinux.restorecon(tracesDir.getPath())) { 4892 return; 4893 } 4894 } 4895 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4896 4897 if (tracesFile.exists()) { 4898 tracesTmp.delete(); 4899 tracesFile.renameTo(tracesTmp); 4900 } 4901 StringBuilder sb = new StringBuilder(); 4902 Time tobj = new Time(); 4903 tobj.set(System.currentTimeMillis()); 4904 sb.append(tobj.format("%Y-%m-%d %H:%M:%S")); 4905 sb.append(": "); 4906 TimeUtils.formatDuration(SystemClock.uptimeMillis()-startTime, sb); 4907 sb.append(" since "); 4908 sb.append(msg); 4909 FileOutputStream fos = new FileOutputStream(tracesFile); 4910 fos.write(sb.toString().getBytes()); 4911 if (app == null) { 4912 fos.write("\n*** No application process!".getBytes()); 4913 } 4914 fos.close(); 4915 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4916 } catch (IOException e) { 4917 Slog.w(TAG, "Unable to prepare slow app traces file: " + tracesPath, e); 4918 return; 4919 } 4920 4921 if (app != null) { 4922 ArrayList<Integer> firstPids = new ArrayList<Integer>(); 4923 firstPids.add(app.pid); 4924 dumpStackTraces(tracesPath, firstPids, null, null, null); 4925 } 4926 4927 File lastTracesFile = null; 4928 File curTracesFile = null; 4929 for (int i=9; i>=0; i--) { 4930 String name = String.format(Locale.US, "slow%02d.txt", i); 4931 curTracesFile = new File(tracesDir, name); 4932 if (curTracesFile.exists()) { 4933 if (lastTracesFile != null) { 4934 curTracesFile.renameTo(lastTracesFile); 4935 } else { 4936 curTracesFile.delete(); 4937 } 4938 } 4939 lastTracesFile = curTracesFile; 4940 } 4941 tracesFile.renameTo(curTracesFile); 4942 if (tracesTmp.exists()) { 4943 tracesTmp.renameTo(tracesFile); 4944 } 4945 } finally { 4946 StrictMode.setThreadPolicy(oldPolicy); 4947 } 4948 } 4949 4950 final void appNotResponding(ProcessRecord app, ActivityRecord activity, 4951 ActivityRecord parent, boolean aboveSystem, final String annotation) { 4952 ArrayList<Integer> firstPids = new ArrayList<Integer>(5); 4953 SparseArray<Boolean> lastPids = new SparseArray<Boolean>(20); 4954 4955 if (mController != null) { 4956 try { 4957 // 0 == continue, -1 = kill process immediately 4958 int res = mController.appEarlyNotResponding(app.processName, app.pid, annotation); 4959 if (res < 0 && app.pid != MY_PID) { 4960 app.kill("anr", true); 4961 } 4962 } catch (RemoteException e) { 4963 mController = null; 4964 Watchdog.getInstance().setActivityController(null); 4965 } 4966 } 4967 4968 long anrTime = SystemClock.uptimeMillis(); 4969 if (MONITOR_CPU_USAGE) { 4970 updateCpuStatsNow(); 4971 } 4972 4973 synchronized (this) { 4974 // PowerManager.reboot() can block for a long time, so ignore ANRs while shutting down. 4975 if (mShuttingDown) { 4976 Slog.i(TAG, "During shutdown skipping ANR: " + app + " " + annotation); 4977 return; 4978 } else if (app.notResponding) { 4979 Slog.i(TAG, "Skipping duplicate ANR: " + app + " " + annotation); 4980 return; 4981 } else if (app.crashing) { 4982 Slog.i(TAG, "Crashing app skipping ANR: " + app + " " + annotation); 4983 return; 4984 } 4985 4986 // In case we come through here for the same app before completing 4987 // this one, mark as anring now so we will bail out. 4988 app.notResponding = true; 4989 4990 // Log the ANR to the event log. 4991 EventLog.writeEvent(EventLogTags.AM_ANR, app.userId, app.pid, 4992 app.processName, app.info.flags, annotation); 4993 4994 // Dump thread traces as quickly as we can, starting with "interesting" processes. 4995 firstPids.add(app.pid); 4996 4997 int parentPid = app.pid; 4998 if (parent != null && parent.app != null && parent.app.pid > 0) parentPid = parent.app.pid; 4999 if (parentPid != app.pid) firstPids.add(parentPid); 5000 5001 if (MY_PID != app.pid && MY_PID != parentPid) firstPids.add(MY_PID); 5002 5003 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 5004 ProcessRecord r = mLruProcesses.get(i); 5005 if (r != null && r.thread != null) { 5006 int pid = r.pid; 5007 if (pid > 0 && pid != app.pid && pid != parentPid && pid != MY_PID) { 5008 if (r.persistent) { 5009 firstPids.add(pid); 5010 } else { 5011 lastPids.put(pid, Boolean.TRUE); 5012 } 5013 } 5014 } 5015 } 5016 } 5017 5018 // Log the ANR to the main log. 5019 StringBuilder info = new StringBuilder(); 5020 info.setLength(0); 5021 info.append("ANR in ").append(app.processName); 5022 if (activity != null && activity.shortComponentName != null) { 5023 info.append(" (").append(activity.shortComponentName).append(")"); 5024 } 5025 info.append("\n"); 5026 info.append("PID: ").append(app.pid).append("\n"); 5027 if (annotation != null) { 5028 info.append("Reason: ").append(annotation).append("\n"); 5029 } 5030 if (parent != null && parent != activity) { 5031 info.append("Parent: ").append(parent.shortComponentName).append("\n"); 5032 } 5033 5034 final ProcessCpuTracker processCpuTracker = new ProcessCpuTracker(true); 5035 5036 File tracesFile = dumpStackTraces(true, firstPids, processCpuTracker, lastPids, 5037 NATIVE_STACKS_OF_INTEREST); 5038 5039 String cpuInfo = null; 5040 if (MONITOR_CPU_USAGE) { 5041 updateCpuStatsNow(); 5042 synchronized (mProcessCpuThread) { 5043 cpuInfo = mProcessCpuTracker.printCurrentState(anrTime); 5044 } 5045 info.append(processCpuTracker.printCurrentLoad()); 5046 info.append(cpuInfo); 5047 } 5048 5049 info.append(processCpuTracker.printCurrentState(anrTime)); 5050 5051 Slog.e(TAG, info.toString()); 5052 if (tracesFile == null) { 5053 // There is no trace file, so dump (only) the alleged culprit's threads to the log 5054 Process.sendSignal(app.pid, Process.SIGNAL_QUIT); 5055 } 5056 5057 addErrorToDropBox("anr", app, app.processName, activity, parent, annotation, 5058 cpuInfo, tracesFile, null); 5059 5060 if (mController != null) { 5061 try { 5062 // 0 == show dialog, 1 = keep waiting, -1 = kill process immediately 5063 int res = mController.appNotResponding(app.processName, app.pid, info.toString()); 5064 if (res != 0) { 5065 if (res < 0 && app.pid != MY_PID) { 5066 app.kill("anr", true); 5067 } else { 5068 synchronized (this) { 5069 mServices.scheduleServiceTimeoutLocked(app); 5070 } 5071 } 5072 return; 5073 } 5074 } catch (RemoteException e) { 5075 mController = null; 5076 Watchdog.getInstance().setActivityController(null); 5077 } 5078 } 5079 5080 // Unless configured otherwise, swallow ANRs in background processes & kill the process. 5081 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 5082 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 5083 5084 synchronized (this) { 5085 if (!showBackground && !app.isInterestingToUserLocked() && app.pid != MY_PID) { 5086 app.kill("bg anr", true); 5087 return; 5088 } 5089 5090 // Set the app's notResponding state, and look up the errorReportReceiver 5091 makeAppNotRespondingLocked(app, 5092 activity != null ? activity.shortComponentName : null, 5093 annotation != null ? "ANR " + annotation : "ANR", 5094 info.toString()); 5095 5096 // Bring up the infamous App Not Responding dialog 5097 Message msg = Message.obtain(); 5098 HashMap<String, Object> map = new HashMap<String, Object>(); 5099 msg.what = SHOW_NOT_RESPONDING_MSG; 5100 msg.obj = map; 5101 msg.arg1 = aboveSystem ? 1 : 0; 5102 map.put("app", app); 5103 if (activity != null) { 5104 map.put("activity", activity); 5105 } 5106 5107 mHandler.sendMessage(msg); 5108 } 5109 } 5110 5111 final void showLaunchWarningLocked(final ActivityRecord cur, final ActivityRecord next) { 5112 if (!mLaunchWarningShown) { 5113 mLaunchWarningShown = true; 5114 mHandler.post(new Runnable() { 5115 @Override 5116 public void run() { 5117 synchronized (ActivityManagerService.this) { 5118 final Dialog d = new LaunchWarningWindow(mContext, cur, next); 5119 d.show(); 5120 mHandler.postDelayed(new Runnable() { 5121 @Override 5122 public void run() { 5123 synchronized (ActivityManagerService.this) { 5124 d.dismiss(); 5125 mLaunchWarningShown = false; 5126 } 5127 } 5128 }, 4000); 5129 } 5130 } 5131 }); 5132 } 5133 } 5134 5135 @Override 5136 public boolean clearApplicationUserData(final String packageName, 5137 final IPackageDataObserver observer, int userId) { 5138 enforceNotIsolatedCaller("clearApplicationUserData"); 5139 int uid = Binder.getCallingUid(); 5140 int pid = Binder.getCallingPid(); 5141 userId = handleIncomingUser(pid, uid, 5142 userId, false, ALLOW_FULL_ONLY, "clearApplicationUserData", null); 5143 long callingId = Binder.clearCallingIdentity(); 5144 try { 5145 IPackageManager pm = AppGlobals.getPackageManager(); 5146 int pkgUid = -1; 5147 synchronized(this) { 5148 try { 5149 pkgUid = pm.getPackageUid(packageName, userId); 5150 } catch (RemoteException e) { 5151 } 5152 if (pkgUid == -1) { 5153 Slog.w(TAG, "Invalid packageName: " + packageName); 5154 if (observer != null) { 5155 try { 5156 observer.onRemoveCompleted(packageName, false); 5157 } catch (RemoteException e) { 5158 Slog.i(TAG, "Observer no longer exists."); 5159 } 5160 } 5161 return false; 5162 } 5163 if (uid == pkgUid || checkComponentPermission( 5164 android.Manifest.permission.CLEAR_APP_USER_DATA, 5165 pid, uid, -1, true) 5166 == PackageManager.PERMISSION_GRANTED) { 5167 forceStopPackageLocked(packageName, pkgUid, "clear data"); 5168 } else { 5169 throw new SecurityException("PID " + pid + " does not have permission " 5170 + android.Manifest.permission.CLEAR_APP_USER_DATA + " to clear data" 5171 + " of package " + packageName); 5172 } 5173 5174 // Remove all tasks match the cleared application package and user 5175 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 5176 final TaskRecord tr = mRecentTasks.get(i); 5177 final String taskPackageName = 5178 tr.getBaseIntent().getComponent().getPackageName(); 5179 if (tr.userId != userId) continue; 5180 if (!taskPackageName.equals(packageName)) continue; 5181 removeTaskByIdLocked(tr.taskId, 0); 5182 } 5183 } 5184 5185 try { 5186 // Clear application user data 5187 pm.clearApplicationUserData(packageName, observer, userId); 5188 5189 synchronized(this) { 5190 // Remove all permissions granted from/to this package 5191 removeUriPermissionsForPackageLocked(packageName, userId, true); 5192 } 5193 5194 Intent intent = new Intent(Intent.ACTION_PACKAGE_DATA_CLEARED, 5195 Uri.fromParts("package", packageName, null)); 5196 intent.putExtra(Intent.EXTRA_UID, pkgUid); 5197 broadcastIntentInPackage("android", Process.SYSTEM_UID, intent, 5198 null, null, 0, null, null, null, false, false, userId); 5199 } catch (RemoteException e) { 5200 } 5201 } finally { 5202 Binder.restoreCallingIdentity(callingId); 5203 } 5204 return true; 5205 } 5206 5207 @Override 5208 public void killBackgroundProcesses(final String packageName, int userId) { 5209 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 5210 != PackageManager.PERMISSION_GRANTED && 5211 checkCallingPermission(android.Manifest.permission.RESTART_PACKAGES) 5212 != PackageManager.PERMISSION_GRANTED) { 5213 String msg = "Permission Denial: killBackgroundProcesses() from pid=" 5214 + Binder.getCallingPid() 5215 + ", uid=" + Binder.getCallingUid() 5216 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 5217 Slog.w(TAG, msg); 5218 throw new SecurityException(msg); 5219 } 5220 5221 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 5222 userId, true, ALLOW_FULL_ONLY, "killBackgroundProcesses", null); 5223 long callingId = Binder.clearCallingIdentity(); 5224 try { 5225 IPackageManager pm = AppGlobals.getPackageManager(); 5226 synchronized(this) { 5227 int appId = -1; 5228 try { 5229 appId = UserHandle.getAppId(pm.getPackageUid(packageName, 0)); 5230 } catch (RemoteException e) { 5231 } 5232 if (appId == -1) { 5233 Slog.w(TAG, "Invalid packageName: " + packageName); 5234 return; 5235 } 5236 killPackageProcessesLocked(packageName, appId, userId, 5237 ProcessList.SERVICE_ADJ, false, true, true, false, "kill background"); 5238 } 5239 } finally { 5240 Binder.restoreCallingIdentity(callingId); 5241 } 5242 } 5243 5244 @Override 5245 public void killAllBackgroundProcesses() { 5246 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 5247 != PackageManager.PERMISSION_GRANTED) { 5248 String msg = "Permission Denial: killAllBackgroundProcesses() 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 long callingId = Binder.clearCallingIdentity(); 5257 try { 5258 synchronized(this) { 5259 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 5260 final int NP = mProcessNames.getMap().size(); 5261 for (int ip=0; ip<NP; ip++) { 5262 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 5263 final int NA = apps.size(); 5264 for (int ia=0; ia<NA; ia++) { 5265 ProcessRecord app = apps.valueAt(ia); 5266 if (app.persistent) { 5267 // we don't kill persistent processes 5268 continue; 5269 } 5270 if (app.removed) { 5271 procs.add(app); 5272 } else if (app.setAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 5273 app.removed = true; 5274 procs.add(app); 5275 } 5276 } 5277 } 5278 5279 int N = procs.size(); 5280 for (int i=0; i<N; i++) { 5281 removeProcessLocked(procs.get(i), false, true, "kill all background"); 5282 } 5283 mAllowLowerMemLevel = true; 5284 updateOomAdjLocked(); 5285 doLowMemReportIfNeededLocked(null); 5286 } 5287 } finally { 5288 Binder.restoreCallingIdentity(callingId); 5289 } 5290 } 5291 5292 @Override 5293 public void forceStopPackage(final String packageName, int userId) { 5294 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 5295 != PackageManager.PERMISSION_GRANTED) { 5296 String msg = "Permission Denial: forceStopPackage() from pid=" 5297 + Binder.getCallingPid() 5298 + ", uid=" + Binder.getCallingUid() 5299 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 5300 Slog.w(TAG, msg); 5301 throw new SecurityException(msg); 5302 } 5303 final int callingPid = Binder.getCallingPid(); 5304 userId = handleIncomingUser(callingPid, Binder.getCallingUid(), 5305 userId, true, ALLOW_FULL_ONLY, "forceStopPackage", null); 5306 long callingId = Binder.clearCallingIdentity(); 5307 try { 5308 IPackageManager pm = AppGlobals.getPackageManager(); 5309 synchronized(this) { 5310 int[] users = userId == UserHandle.USER_ALL 5311 ? getUsersLocked() : new int[] { userId }; 5312 for (int user : users) { 5313 int pkgUid = -1; 5314 try { 5315 pkgUid = pm.getPackageUid(packageName, user); 5316 } catch (RemoteException e) { 5317 } 5318 if (pkgUid == -1) { 5319 Slog.w(TAG, "Invalid packageName: " + packageName); 5320 continue; 5321 } 5322 try { 5323 pm.setPackageStoppedState(packageName, true, user); 5324 } catch (RemoteException e) { 5325 } catch (IllegalArgumentException e) { 5326 Slog.w(TAG, "Failed trying to unstop package " 5327 + packageName + ": " + e); 5328 } 5329 if (isUserRunningLocked(user, false)) { 5330 forceStopPackageLocked(packageName, pkgUid, "from pid " + callingPid); 5331 } 5332 } 5333 } 5334 } finally { 5335 Binder.restoreCallingIdentity(callingId); 5336 } 5337 } 5338 5339 @Override 5340 public void addPackageDependency(String packageName) { 5341 synchronized (this) { 5342 int callingPid = Binder.getCallingPid(); 5343 if (callingPid == Process.myPid()) { 5344 // Yeah, um, no. 5345 Slog.w(TAG, "Can't addPackageDependency on system process"); 5346 return; 5347 } 5348 ProcessRecord proc; 5349 synchronized (mPidsSelfLocked) { 5350 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 5351 } 5352 if (proc != null) { 5353 if (proc.pkgDeps == null) { 5354 proc.pkgDeps = new ArraySet<String>(1); 5355 } 5356 proc.pkgDeps.add(packageName); 5357 } 5358 } 5359 } 5360 5361 /* 5362 * The pkg name and app id have to be specified. 5363 */ 5364 @Override 5365 public void killApplicationWithAppId(String pkg, int appid, String reason) { 5366 if (pkg == null) { 5367 return; 5368 } 5369 // Make sure the uid is valid. 5370 if (appid < 0) { 5371 Slog.w(TAG, "Invalid appid specified for pkg : " + pkg); 5372 return; 5373 } 5374 int callerUid = Binder.getCallingUid(); 5375 // Only the system server can kill an application 5376 if (callerUid == Process.SYSTEM_UID) { 5377 // Post an aysnc message to kill the application 5378 Message msg = mHandler.obtainMessage(KILL_APPLICATION_MSG); 5379 msg.arg1 = appid; 5380 msg.arg2 = 0; 5381 Bundle bundle = new Bundle(); 5382 bundle.putString("pkg", pkg); 5383 bundle.putString("reason", reason); 5384 msg.obj = bundle; 5385 mHandler.sendMessage(msg); 5386 } else { 5387 throw new SecurityException(callerUid + " cannot kill pkg: " + 5388 pkg); 5389 } 5390 } 5391 5392 @Override 5393 public void closeSystemDialogs(String reason) { 5394 enforceNotIsolatedCaller("closeSystemDialogs"); 5395 5396 final int pid = Binder.getCallingPid(); 5397 final int uid = Binder.getCallingUid(); 5398 final long origId = Binder.clearCallingIdentity(); 5399 try { 5400 synchronized (this) { 5401 // Only allow this from foreground processes, so that background 5402 // applications can't abuse it to prevent system UI from being shown. 5403 if (uid >= Process.FIRST_APPLICATION_UID) { 5404 ProcessRecord proc; 5405 synchronized (mPidsSelfLocked) { 5406 proc = mPidsSelfLocked.get(pid); 5407 } 5408 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 5409 Slog.w(TAG, "Ignoring closeSystemDialogs " + reason 5410 + " from background process " + proc); 5411 return; 5412 } 5413 } 5414 closeSystemDialogsLocked(reason); 5415 } 5416 } finally { 5417 Binder.restoreCallingIdentity(origId); 5418 } 5419 } 5420 5421 void closeSystemDialogsLocked(String reason) { 5422 Intent intent = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS); 5423 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5424 | Intent.FLAG_RECEIVER_FOREGROUND); 5425 if (reason != null) { 5426 intent.putExtra("reason", reason); 5427 } 5428 mWindowManager.closeSystemDialogs(reason); 5429 5430 mStackSupervisor.closeSystemDialogsLocked(); 5431 5432 broadcastIntentLocked(null, null, intent, null, 5433 null, 0, null, null, null, AppOpsManager.OP_NONE, false, false, -1, 5434 Process.SYSTEM_UID, UserHandle.USER_ALL); 5435 } 5436 5437 @Override 5438 public Debug.MemoryInfo[] getProcessMemoryInfo(int[] pids) { 5439 enforceNotIsolatedCaller("getProcessMemoryInfo"); 5440 Debug.MemoryInfo[] infos = new Debug.MemoryInfo[pids.length]; 5441 for (int i=pids.length-1; i>=0; i--) { 5442 ProcessRecord proc; 5443 int oomAdj; 5444 synchronized (this) { 5445 synchronized (mPidsSelfLocked) { 5446 proc = mPidsSelfLocked.get(pids[i]); 5447 oomAdj = proc != null ? proc.setAdj : 0; 5448 } 5449 } 5450 infos[i] = new Debug.MemoryInfo(); 5451 Debug.getMemoryInfo(pids[i], infos[i]); 5452 if (proc != null) { 5453 synchronized (this) { 5454 if (proc.thread != null && proc.setAdj == oomAdj) { 5455 // Record this for posterity if the process has been stable. 5456 proc.baseProcessTracker.addPss(infos[i].getTotalPss(), 5457 infos[i].getTotalUss(), false, proc.pkgList); 5458 } 5459 } 5460 } 5461 } 5462 return infos; 5463 } 5464 5465 @Override 5466 public long[] getProcessPss(int[] pids) { 5467 enforceNotIsolatedCaller("getProcessPss"); 5468 long[] pss = new long[pids.length]; 5469 for (int i=pids.length-1; i>=0; i--) { 5470 ProcessRecord proc; 5471 int oomAdj; 5472 synchronized (this) { 5473 synchronized (mPidsSelfLocked) { 5474 proc = mPidsSelfLocked.get(pids[i]); 5475 oomAdj = proc != null ? proc.setAdj : 0; 5476 } 5477 } 5478 long[] tmpUss = new long[1]; 5479 pss[i] = Debug.getPss(pids[i], tmpUss); 5480 if (proc != null) { 5481 synchronized (this) { 5482 if (proc.thread != null && proc.setAdj == oomAdj) { 5483 // Record this for posterity if the process has been stable. 5484 proc.baseProcessTracker.addPss(pss[i], tmpUss[0], false, proc.pkgList); 5485 } 5486 } 5487 } 5488 } 5489 return pss; 5490 } 5491 5492 @Override 5493 public void killApplicationProcess(String processName, int uid) { 5494 if (processName == null) { 5495 return; 5496 } 5497 5498 int callerUid = Binder.getCallingUid(); 5499 // Only the system server can kill an application 5500 if (callerUid == Process.SYSTEM_UID) { 5501 synchronized (this) { 5502 ProcessRecord app = getProcessRecordLocked(processName, uid, true); 5503 if (app != null && app.thread != null) { 5504 try { 5505 app.thread.scheduleSuicide(); 5506 } catch (RemoteException e) { 5507 // If the other end already died, then our work here is done. 5508 } 5509 } else { 5510 Slog.w(TAG, "Process/uid not found attempting kill of " 5511 + processName + " / " + uid); 5512 } 5513 } 5514 } else { 5515 throw new SecurityException(callerUid + " cannot kill app process: " + 5516 processName); 5517 } 5518 } 5519 5520 private void forceStopPackageLocked(final String packageName, int uid, String reason) { 5521 forceStopPackageLocked(packageName, UserHandle.getAppId(uid), false, 5522 false, true, false, false, UserHandle.getUserId(uid), reason); 5523 Intent intent = new Intent(Intent.ACTION_PACKAGE_RESTARTED, 5524 Uri.fromParts("package", packageName, null)); 5525 if (!mProcessesReady) { 5526 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5527 | Intent.FLAG_RECEIVER_FOREGROUND); 5528 } 5529 intent.putExtra(Intent.EXTRA_UID, uid); 5530 intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(uid)); 5531 broadcastIntentLocked(null, null, intent, 5532 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 5533 false, false, 5534 MY_PID, Process.SYSTEM_UID, UserHandle.getUserId(uid)); 5535 } 5536 5537 private void forceStopUserLocked(int userId, String reason) { 5538 forceStopPackageLocked(null, -1, false, false, true, false, false, userId, reason); 5539 Intent intent = new Intent(Intent.ACTION_USER_STOPPED); 5540 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5541 | Intent.FLAG_RECEIVER_FOREGROUND); 5542 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 5543 broadcastIntentLocked(null, null, intent, 5544 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 5545 false, false, 5546 MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 5547 } 5548 5549 private final boolean killPackageProcessesLocked(String packageName, int appId, 5550 int userId, int minOomAdj, boolean callerWillRestart, boolean allowRestart, 5551 boolean doit, boolean evenPersistent, String reason) { 5552 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 5553 5554 // Remove all processes this package may have touched: all with the 5555 // same UID (except for the system or root user), and all whose name 5556 // matches the package name. 5557 final int NP = mProcessNames.getMap().size(); 5558 for (int ip=0; ip<NP; ip++) { 5559 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 5560 final int NA = apps.size(); 5561 for (int ia=0; ia<NA; ia++) { 5562 ProcessRecord app = apps.valueAt(ia); 5563 if (app.persistent && !evenPersistent) { 5564 // we don't kill persistent processes 5565 continue; 5566 } 5567 if (app.removed) { 5568 if (doit) { 5569 procs.add(app); 5570 } 5571 continue; 5572 } 5573 5574 // Skip process if it doesn't meet our oom adj requirement. 5575 if (app.setAdj < minOomAdj) { 5576 continue; 5577 } 5578 5579 // If no package is specified, we call all processes under the 5580 // give user id. 5581 if (packageName == null) { 5582 if (app.userId != userId) { 5583 continue; 5584 } 5585 if (appId >= 0 && UserHandle.getAppId(app.uid) != appId) { 5586 continue; 5587 } 5588 // Package has been specified, we want to hit all processes 5589 // that match it. We need to qualify this by the processes 5590 // that are running under the specified app and user ID. 5591 } else { 5592 final boolean isDep = app.pkgDeps != null 5593 && app.pkgDeps.contains(packageName); 5594 if (!isDep && UserHandle.getAppId(app.uid) != appId) { 5595 continue; 5596 } 5597 if (userId != UserHandle.USER_ALL && app.userId != userId) { 5598 continue; 5599 } 5600 if (!app.pkgList.containsKey(packageName) && !isDep) { 5601 continue; 5602 } 5603 } 5604 5605 // Process has passed all conditions, kill it! 5606 if (!doit) { 5607 return true; 5608 } 5609 app.removed = true; 5610 procs.add(app); 5611 } 5612 } 5613 5614 int N = procs.size(); 5615 for (int i=0; i<N; i++) { 5616 removeProcessLocked(procs.get(i), callerWillRestart, allowRestart, reason); 5617 } 5618 updateOomAdjLocked(); 5619 return N > 0; 5620 } 5621 5622 private final boolean forceStopPackageLocked(String name, int appId, 5623 boolean callerWillRestart, boolean purgeCache, boolean doit, 5624 boolean evenPersistent, boolean uninstalling, int userId, String reason) { 5625 int i; 5626 int N; 5627 5628 if (userId == UserHandle.USER_ALL && name == null) { 5629 Slog.w(TAG, "Can't force stop all processes of all users, that is insane!"); 5630 } 5631 5632 if (appId < 0 && name != null) { 5633 try { 5634 appId = UserHandle.getAppId( 5635 AppGlobals.getPackageManager().getPackageUid(name, 0)); 5636 } catch (RemoteException e) { 5637 } 5638 } 5639 5640 if (doit) { 5641 if (name != null) { 5642 Slog.i(TAG, "Force stopping " + name + " appid=" + appId 5643 + " user=" + userId + ": " + reason); 5644 } else { 5645 Slog.i(TAG, "Force stopping u" + userId + ": " + reason); 5646 } 5647 5648 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 5649 for (int ip=pmap.size()-1; ip>=0; ip--) { 5650 SparseArray<Long> ba = pmap.valueAt(ip); 5651 for (i=ba.size()-1; i>=0; i--) { 5652 boolean remove = false; 5653 final int entUid = ba.keyAt(i); 5654 if (name != null) { 5655 if (userId == UserHandle.USER_ALL) { 5656 if (UserHandle.getAppId(entUid) == appId) { 5657 remove = true; 5658 } 5659 } else { 5660 if (entUid == UserHandle.getUid(userId, appId)) { 5661 remove = true; 5662 } 5663 } 5664 } else if (UserHandle.getUserId(entUid) == userId) { 5665 remove = true; 5666 } 5667 if (remove) { 5668 ba.removeAt(i); 5669 } 5670 } 5671 if (ba.size() == 0) { 5672 pmap.removeAt(ip); 5673 } 5674 } 5675 } 5676 5677 boolean didSomething = killPackageProcessesLocked(name, appId, userId, 5678 -100, callerWillRestart, true, doit, evenPersistent, 5679 name == null ? ("stop user " + userId) : ("stop " + name)); 5680 5681 if (mStackSupervisor.forceStopPackageLocked(name, doit, evenPersistent, userId)) { 5682 if (!doit) { 5683 return true; 5684 } 5685 didSomething = true; 5686 } 5687 5688 if (mServices.forceStopLocked(name, userId, evenPersistent, doit)) { 5689 if (!doit) { 5690 return true; 5691 } 5692 didSomething = true; 5693 } 5694 5695 if (name == null) { 5696 // Remove all sticky broadcasts from this user. 5697 mStickyBroadcasts.remove(userId); 5698 } 5699 5700 ArrayList<ContentProviderRecord> providers = new ArrayList<ContentProviderRecord>(); 5701 if (mProviderMap.collectForceStopProviders(name, appId, doit, evenPersistent, 5702 userId, providers)) { 5703 if (!doit) { 5704 return true; 5705 } 5706 didSomething = true; 5707 } 5708 N = providers.size(); 5709 for (i=0; i<N; i++) { 5710 removeDyingProviderLocked(null, providers.get(i), true); 5711 } 5712 5713 // Remove transient permissions granted from/to this package/user 5714 removeUriPermissionsForPackageLocked(name, userId, false); 5715 5716 if (name == null || uninstalling) { 5717 // Remove pending intents. For now we only do this when force 5718 // stopping users, because we have some problems when doing this 5719 // for packages -- app widgets are not currently cleaned up for 5720 // such packages, so they can be left with bad pending intents. 5721 if (mIntentSenderRecords.size() > 0) { 5722 Iterator<WeakReference<PendingIntentRecord>> it 5723 = mIntentSenderRecords.values().iterator(); 5724 while (it.hasNext()) { 5725 WeakReference<PendingIntentRecord> wpir = it.next(); 5726 if (wpir == null) { 5727 it.remove(); 5728 continue; 5729 } 5730 PendingIntentRecord pir = wpir.get(); 5731 if (pir == null) { 5732 it.remove(); 5733 continue; 5734 } 5735 if (name == null) { 5736 // Stopping user, remove all objects for the user. 5737 if (pir.key.userId != userId) { 5738 // Not the same user, skip it. 5739 continue; 5740 } 5741 } else { 5742 if (UserHandle.getAppId(pir.uid) != appId) { 5743 // Different app id, skip it. 5744 continue; 5745 } 5746 if (userId != UserHandle.USER_ALL && pir.key.userId != userId) { 5747 // Different user, skip it. 5748 continue; 5749 } 5750 if (!pir.key.packageName.equals(name)) { 5751 // Different package, skip it. 5752 continue; 5753 } 5754 } 5755 if (!doit) { 5756 return true; 5757 } 5758 didSomething = true; 5759 it.remove(); 5760 pir.canceled = true; 5761 if (pir.key.activity != null) { 5762 pir.key.activity.pendingResults.remove(pir.ref); 5763 } 5764 } 5765 } 5766 } 5767 5768 if (doit) { 5769 if (purgeCache && name != null) { 5770 AttributeCache ac = AttributeCache.instance(); 5771 if (ac != null) { 5772 ac.removePackage(name); 5773 } 5774 } 5775 if (mBooted) { 5776 mStackSupervisor.resumeTopActivitiesLocked(); 5777 mStackSupervisor.scheduleIdleLocked(); 5778 } 5779 } 5780 5781 return didSomething; 5782 } 5783 5784 private final boolean removeProcessLocked(ProcessRecord app, 5785 boolean callerWillRestart, boolean allowRestart, String reason) { 5786 final String name = app.processName; 5787 final int uid = app.uid; 5788 if (DEBUG_PROCESSES) Slog.d( 5789 TAG, "Force removing proc " + app.toShortString() + " (" + name 5790 + "/" + uid + ")"); 5791 5792 mProcessNames.remove(name, uid); 5793 mIsolatedProcesses.remove(app.uid); 5794 if (mHeavyWeightProcess == app) { 5795 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5796 mHeavyWeightProcess.userId, 0)); 5797 mHeavyWeightProcess = null; 5798 } 5799 boolean needRestart = false; 5800 if (app.pid > 0 && app.pid != MY_PID) { 5801 int pid = app.pid; 5802 synchronized (mPidsSelfLocked) { 5803 mPidsSelfLocked.remove(pid); 5804 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5805 } 5806 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 5807 if (app.isolated) { 5808 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5809 } 5810 app.kill(reason, true); 5811 handleAppDiedLocked(app, true, allowRestart); 5812 removeLruProcessLocked(app); 5813 5814 if (app.persistent && !app.isolated) { 5815 if (!callerWillRestart) { 5816 addAppLocked(app.info, false, null /* ABI override */); 5817 } else { 5818 needRestart = true; 5819 } 5820 } 5821 } else { 5822 mRemovedProcesses.add(app); 5823 } 5824 5825 return needRestart; 5826 } 5827 5828 private final void processStartTimedOutLocked(ProcessRecord app) { 5829 final int pid = app.pid; 5830 boolean gone = false; 5831 synchronized (mPidsSelfLocked) { 5832 ProcessRecord knownApp = mPidsSelfLocked.get(pid); 5833 if (knownApp != null && knownApp.thread == null) { 5834 mPidsSelfLocked.remove(pid); 5835 gone = true; 5836 } 5837 } 5838 5839 if (gone) { 5840 Slog.w(TAG, "Process " + app + " failed to attach"); 5841 EventLog.writeEvent(EventLogTags.AM_PROCESS_START_TIMEOUT, app.userId, 5842 pid, app.uid, app.processName); 5843 mProcessNames.remove(app.processName, app.uid); 5844 mIsolatedProcesses.remove(app.uid); 5845 if (mHeavyWeightProcess == app) { 5846 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5847 mHeavyWeightProcess.userId, 0)); 5848 mHeavyWeightProcess = null; 5849 } 5850 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 5851 if (app.isolated) { 5852 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5853 } 5854 // Take care of any launching providers waiting for this process. 5855 checkAppInLaunchingProvidersLocked(app, true); 5856 // Take care of any services that are waiting for the process. 5857 mServices.processStartTimedOutLocked(app); 5858 app.kill("start timeout", true); 5859 if (mBackupTarget != null && mBackupTarget.app.pid == pid) { 5860 Slog.w(TAG, "Unattached app died before backup, skipping"); 5861 try { 5862 IBackupManager bm = IBackupManager.Stub.asInterface( 5863 ServiceManager.getService(Context.BACKUP_SERVICE)); 5864 bm.agentDisconnected(app.info.packageName); 5865 } catch (RemoteException e) { 5866 // Can't happen; the backup manager is local 5867 } 5868 } 5869 if (isPendingBroadcastProcessLocked(pid)) { 5870 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 5871 skipPendingBroadcastLocked(pid); 5872 } 5873 } else { 5874 Slog.w(TAG, "Spurious process start timeout - pid not known for " + app); 5875 } 5876 } 5877 5878 private final boolean attachApplicationLocked(IApplicationThread thread, 5879 int pid) { 5880 5881 // Find the application record that is being attached... either via 5882 // the pid if we are running in multiple processes, or just pull the 5883 // next app record if we are emulating process with anonymous threads. 5884 ProcessRecord app; 5885 if (pid != MY_PID && pid >= 0) { 5886 synchronized (mPidsSelfLocked) { 5887 app = mPidsSelfLocked.get(pid); 5888 } 5889 } else { 5890 app = null; 5891 } 5892 5893 if (app == null) { 5894 Slog.w(TAG, "No pending application record for pid " + pid 5895 + " (IApplicationThread " + thread + "); dropping process"); 5896 EventLog.writeEvent(EventLogTags.AM_DROP_PROCESS, pid); 5897 if (pid > 0 && pid != MY_PID) { 5898 Process.killProcessQuiet(pid); 5899 //TODO: Process.killProcessGroup(app.info.uid, pid); 5900 } else { 5901 try { 5902 thread.scheduleExit(); 5903 } catch (Exception e) { 5904 // Ignore exceptions. 5905 } 5906 } 5907 return false; 5908 } 5909 5910 // If this application record is still attached to a previous 5911 // process, clean it up now. 5912 if (app.thread != null) { 5913 handleAppDiedLocked(app, true, true); 5914 } 5915 5916 // Tell the process all about itself. 5917 5918 if (localLOGV) Slog.v( 5919 TAG, "Binding process pid " + pid + " to record " + app); 5920 5921 final String processName = app.processName; 5922 try { 5923 AppDeathRecipient adr = new AppDeathRecipient( 5924 app, pid, thread); 5925 thread.asBinder().linkToDeath(adr, 0); 5926 app.deathRecipient = adr; 5927 } catch (RemoteException e) { 5928 app.resetPackageList(mProcessStats); 5929 startProcessLocked(app, "link fail", processName); 5930 return false; 5931 } 5932 5933 EventLog.writeEvent(EventLogTags.AM_PROC_BOUND, app.userId, app.pid, app.processName); 5934 5935 app.makeActive(thread, mProcessStats); 5936 app.curAdj = app.setAdj = -100; 5937 app.curSchedGroup = app.setSchedGroup = Process.THREAD_GROUP_DEFAULT; 5938 app.forcingToForeground = null; 5939 updateProcessForegroundLocked(app, false, false); 5940 app.hasShownUi = false; 5941 app.debugging = false; 5942 app.cached = false; 5943 5944 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5945 5946 boolean normalMode = mProcessesReady || isAllowedWhileBooting(app.info); 5947 List<ProviderInfo> providers = normalMode ? generateApplicationProvidersLocked(app) : null; 5948 5949 if (!normalMode) { 5950 Slog.i(TAG, "Launching preboot mode app: " + app); 5951 } 5952 5953 if (localLOGV) Slog.v( 5954 TAG, "New app record " + app 5955 + " thread=" + thread.asBinder() + " pid=" + pid); 5956 try { 5957 int testMode = IApplicationThread.DEBUG_OFF; 5958 if (mDebugApp != null && mDebugApp.equals(processName)) { 5959 testMode = mWaitForDebugger 5960 ? IApplicationThread.DEBUG_WAIT 5961 : IApplicationThread.DEBUG_ON; 5962 app.debugging = true; 5963 if (mDebugTransient) { 5964 mDebugApp = mOrigDebugApp; 5965 mWaitForDebugger = mOrigWaitForDebugger; 5966 } 5967 } 5968 String profileFile = app.instrumentationProfileFile; 5969 ParcelFileDescriptor profileFd = null; 5970 int samplingInterval = 0; 5971 boolean profileAutoStop = false; 5972 if (mProfileApp != null && mProfileApp.equals(processName)) { 5973 mProfileProc = app; 5974 profileFile = mProfileFile; 5975 profileFd = mProfileFd; 5976 samplingInterval = mSamplingInterval; 5977 profileAutoStop = mAutoStopProfiler; 5978 } 5979 boolean enableOpenGlTrace = false; 5980 if (mOpenGlTraceApp != null && mOpenGlTraceApp.equals(processName)) { 5981 enableOpenGlTrace = true; 5982 mOpenGlTraceApp = null; 5983 } 5984 5985 // If the app is being launched for restore or full backup, set it up specially 5986 boolean isRestrictedBackupMode = false; 5987 if (mBackupTarget != null && mBackupAppName.equals(processName)) { 5988 isRestrictedBackupMode = (mBackupTarget.backupMode == BackupRecord.RESTORE) 5989 || (mBackupTarget.backupMode == BackupRecord.RESTORE_FULL) 5990 || (mBackupTarget.backupMode == BackupRecord.BACKUP_FULL); 5991 } 5992 5993 ensurePackageDexOpt(app.instrumentationInfo != null 5994 ? app.instrumentationInfo.packageName 5995 : app.info.packageName); 5996 if (app.instrumentationClass != null) { 5997 ensurePackageDexOpt(app.instrumentationClass.getPackageName()); 5998 } 5999 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Binding proc " 6000 + processName + " with config " + mConfiguration); 6001 ApplicationInfo appInfo = app.instrumentationInfo != null 6002 ? app.instrumentationInfo : app.info; 6003 app.compat = compatibilityInfoForPackageLocked(appInfo); 6004 if (profileFd != null) { 6005 profileFd = profileFd.dup(); 6006 } 6007 ProfilerInfo profilerInfo = profileFile == null ? null 6008 : new ProfilerInfo(profileFile, profileFd, samplingInterval, profileAutoStop); 6009 thread.bindApplication(processName, appInfo, providers, app.instrumentationClass, 6010 profilerInfo, app.instrumentationArguments, app.instrumentationWatcher, 6011 app.instrumentationUiAutomationConnection, testMode, enableOpenGlTrace, 6012 isRestrictedBackupMode || !normalMode, app.persistent, 6013 new Configuration(mConfiguration), app.compat, getCommonServicesLocked(), 6014 mCoreSettingsObserver.getCoreSettingsLocked()); 6015 updateLruProcessLocked(app, false, null); 6016 app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis(); 6017 } catch (Exception e) { 6018 // todo: Yikes! What should we do? For now we will try to 6019 // start another process, but that could easily get us in 6020 // an infinite loop of restarting processes... 6021 Slog.w(TAG, "Exception thrown during bind!", e); 6022 6023 app.resetPackageList(mProcessStats); 6024 app.unlinkDeathRecipient(); 6025 startProcessLocked(app, "bind fail", processName); 6026 return false; 6027 } 6028 6029 // Remove this record from the list of starting applications. 6030 mPersistentStartingProcesses.remove(app); 6031 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 6032 "Attach application locked removing on hold: " + app); 6033 mProcessesOnHold.remove(app); 6034 6035 boolean badApp = false; 6036 boolean didSomething = false; 6037 6038 // See if the top visible activity is waiting to run in this process... 6039 if (normalMode) { 6040 try { 6041 if (mStackSupervisor.attachApplicationLocked(app)) { 6042 didSomething = true; 6043 } 6044 } catch (Exception e) { 6045 badApp = true; 6046 } 6047 } 6048 6049 // Find any services that should be running in this process... 6050 if (!badApp) { 6051 try { 6052 didSomething |= mServices.attachApplicationLocked(app, processName); 6053 } catch (Exception e) { 6054 badApp = true; 6055 } 6056 } 6057 6058 // Check if a next-broadcast receiver is in this process... 6059 if (!badApp && isPendingBroadcastProcessLocked(pid)) { 6060 try { 6061 didSomething |= sendPendingBroadcastsLocked(app); 6062 } catch (Exception e) { 6063 // If the app died trying to launch the receiver we declare it 'bad' 6064 badApp = true; 6065 } 6066 } 6067 6068 // Check whether the next backup agent is in this process... 6069 if (!badApp && mBackupTarget != null && mBackupTarget.appInfo.uid == app.uid) { 6070 if (DEBUG_BACKUP) Slog.v(TAG, "New app is backup target, launching agent for " + app); 6071 ensurePackageDexOpt(mBackupTarget.appInfo.packageName); 6072 try { 6073 thread.scheduleCreateBackupAgent(mBackupTarget.appInfo, 6074 compatibilityInfoForPackageLocked(mBackupTarget.appInfo), 6075 mBackupTarget.backupMode); 6076 } catch (Exception e) { 6077 Slog.w(TAG, "Exception scheduling backup agent creation: "); 6078 e.printStackTrace(); 6079 } 6080 } 6081 6082 if (badApp) { 6083 // todo: Also need to kill application to deal with all 6084 // kinds of exceptions. 6085 handleAppDiedLocked(app, false, true); 6086 return false; 6087 } 6088 6089 if (!didSomething) { 6090 updateOomAdjLocked(); 6091 } 6092 6093 return true; 6094 } 6095 6096 @Override 6097 public final void attachApplication(IApplicationThread thread) { 6098 synchronized (this) { 6099 int callingPid = Binder.getCallingPid(); 6100 final long origId = Binder.clearCallingIdentity(); 6101 attachApplicationLocked(thread, callingPid); 6102 Binder.restoreCallingIdentity(origId); 6103 } 6104 } 6105 6106 @Override 6107 public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) { 6108 final long origId = Binder.clearCallingIdentity(); 6109 synchronized (this) { 6110 ActivityStack stack = ActivityRecord.getStackLocked(token); 6111 if (stack != null) { 6112 ActivityRecord r = 6113 mStackSupervisor.activityIdleInternalLocked(token, false, config); 6114 if (stopProfiling) { 6115 if ((mProfileProc == r.app) && (mProfileFd != null)) { 6116 try { 6117 mProfileFd.close(); 6118 } catch (IOException e) { 6119 } 6120 clearProfilerLocked(); 6121 } 6122 } 6123 } 6124 } 6125 Binder.restoreCallingIdentity(origId); 6126 } 6127 6128 void postEnableScreenAfterBootLocked() { 6129 mHandler.sendEmptyMessage(ENABLE_SCREEN_AFTER_BOOT_MSG); 6130 } 6131 6132 void enableScreenAfterBoot() { 6133 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN, 6134 SystemClock.uptimeMillis()); 6135 mWindowManager.enableScreenAfterBoot(); 6136 6137 synchronized (this) { 6138 updateEventDispatchingLocked(); 6139 } 6140 } 6141 6142 @Override 6143 public void showBootMessage(final CharSequence msg, final boolean always) { 6144 enforceNotIsolatedCaller("showBootMessage"); 6145 mWindowManager.showBootMessage(msg, always); 6146 } 6147 6148 @Override 6149 public void keyguardWaitingForActivityDrawn() { 6150 enforceNotIsolatedCaller("keyguardWaitingForActivityDrawn"); 6151 final long token = Binder.clearCallingIdentity(); 6152 try { 6153 synchronized (this) { 6154 if (DEBUG_LOCKSCREEN) logLockScreen(""); 6155 mWindowManager.keyguardWaitingForActivityDrawn(); 6156 } 6157 } finally { 6158 Binder.restoreCallingIdentity(token); 6159 } 6160 } 6161 6162 final void finishBooting() { 6163 // Register receivers to handle package update events 6164 mPackageMonitor.register(mContext, Looper.getMainLooper(), false); 6165 6166 // Let system services know. 6167 mSystemServiceManager.startBootPhase(SystemService.PHASE_BOOT_COMPLETED); 6168 6169 synchronized (this) { 6170 // Ensure that any processes we had put on hold are now started 6171 // up. 6172 final int NP = mProcessesOnHold.size(); 6173 if (NP > 0) { 6174 ArrayList<ProcessRecord> procs = 6175 new ArrayList<ProcessRecord>(mProcessesOnHold); 6176 for (int ip=0; ip<NP; ip++) { 6177 if (DEBUG_PROCESSES) Slog.v(TAG, "Starting process on hold: " 6178 + procs.get(ip)); 6179 startProcessLocked(procs.get(ip), "on-hold", null); 6180 } 6181 } 6182 6183 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 6184 // Start looking for apps that are abusing wake locks. 6185 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 6186 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 6187 // Tell anyone interested that we are done booting! 6188 SystemProperties.set("sys.boot_completed", "1"); 6189 SystemProperties.set("dev.bootcomplete", "1"); 6190 for (int i=0; i<mStartedUsers.size(); i++) { 6191 UserStartedState uss = mStartedUsers.valueAt(i); 6192 if (uss.mState == UserStartedState.STATE_BOOTING) { 6193 uss.mState = UserStartedState.STATE_RUNNING; 6194 final int userId = mStartedUsers.keyAt(i); 6195 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 6196 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 6197 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 6198 broadcastIntentLocked(null, null, intent, null, 6199 new IIntentReceiver.Stub() { 6200 @Override 6201 public void performReceive(Intent intent, int resultCode, 6202 String data, Bundle extras, boolean ordered, 6203 boolean sticky, int sendingUser) { 6204 synchronized (ActivityManagerService.this) { 6205 requestPssAllProcsLocked(SystemClock.uptimeMillis(), 6206 true, false); 6207 } 6208 } 6209 }, 6210 0, null, null, 6211 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, 6212 AppOpsManager.OP_NONE, true, false, MY_PID, Process.SYSTEM_UID, 6213 userId); 6214 } 6215 } 6216 scheduleStartProfilesLocked(); 6217 } 6218 } 6219 } 6220 6221 final void ensureBootCompleted() { 6222 boolean booting; 6223 boolean enableScreen; 6224 synchronized (this) { 6225 booting = mBooting; 6226 mBooting = false; 6227 enableScreen = !mBooted; 6228 mBooted = true; 6229 } 6230 6231 if (booting) { 6232 finishBooting(); 6233 } 6234 6235 if (enableScreen) { 6236 enableScreenAfterBoot(); 6237 } 6238 } 6239 6240 @Override 6241 public final void activityResumed(IBinder token) { 6242 final long origId = Binder.clearCallingIdentity(); 6243 synchronized(this) { 6244 ActivityStack stack = ActivityRecord.getStackLocked(token); 6245 if (stack != null) { 6246 ActivityRecord.activityResumedLocked(token); 6247 } 6248 } 6249 Binder.restoreCallingIdentity(origId); 6250 } 6251 6252 @Override 6253 public final void activityPaused(IBinder token, PersistableBundle persistentState) { 6254 final long origId = Binder.clearCallingIdentity(); 6255 synchronized(this) { 6256 ActivityStack stack = ActivityRecord.getStackLocked(token); 6257 if (stack != null) { 6258 stack.activityPausedLocked(token, false, persistentState); 6259 } 6260 } 6261 Binder.restoreCallingIdentity(origId); 6262 } 6263 6264 @Override 6265 public final void activityStopped(IBinder token, Bundle icicle, 6266 PersistableBundle persistentState, CharSequence description) { 6267 if (localLOGV) Slog.v(TAG, "Activity stopped: token=" + token); 6268 6269 // Refuse possible leaked file descriptors 6270 if (icicle != null && icicle.hasFileDescriptors()) { 6271 throw new IllegalArgumentException("File descriptors passed in Bundle"); 6272 } 6273 6274 final long origId = Binder.clearCallingIdentity(); 6275 6276 synchronized (this) { 6277 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6278 if (r != null) { 6279 r.task.stack.activityStoppedLocked(r, icicle, persistentState, description); 6280 } 6281 } 6282 6283 trimApplications(); 6284 6285 Binder.restoreCallingIdentity(origId); 6286 } 6287 6288 @Override 6289 public final void activityDestroyed(IBinder token) { 6290 if (DEBUG_SWITCH) Slog.v(TAG, "ACTIVITY DESTROYED: " + token); 6291 synchronized (this) { 6292 ActivityStack stack = ActivityRecord.getStackLocked(token); 6293 if (stack != null) { 6294 stack.activityDestroyedLocked(token); 6295 } 6296 } 6297 } 6298 6299 @Override 6300 public final void backgroundResourcesReleased(IBinder token) { 6301 final long origId = Binder.clearCallingIdentity(); 6302 try { 6303 synchronized (this) { 6304 ActivityStack stack = ActivityRecord.getStackLocked(token); 6305 if (stack != null) { 6306 stack.backgroundResourcesReleased(token); 6307 } 6308 } 6309 } finally { 6310 Binder.restoreCallingIdentity(origId); 6311 } 6312 } 6313 6314 @Override 6315 public final void notifyLaunchTaskBehindComplete(IBinder token) { 6316 mStackSupervisor.scheduleLaunchTaskBehindComplete(token); 6317 } 6318 6319 @Override 6320 public final void notifyEnterAnimationComplete(IBinder token) { 6321 mHandler.sendMessage(mHandler.obtainMessage(ENTER_ANIMATION_COMPLETE_MSG, token)); 6322 } 6323 6324 @Override 6325 public String getCallingPackage(IBinder token) { 6326 synchronized (this) { 6327 ActivityRecord r = getCallingRecordLocked(token); 6328 return r != null ? r.info.packageName : null; 6329 } 6330 } 6331 6332 @Override 6333 public ComponentName getCallingActivity(IBinder token) { 6334 synchronized (this) { 6335 ActivityRecord r = getCallingRecordLocked(token); 6336 return r != null ? r.intent.getComponent() : null; 6337 } 6338 } 6339 6340 private ActivityRecord getCallingRecordLocked(IBinder token) { 6341 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6342 if (r == null) { 6343 return null; 6344 } 6345 return r.resultTo; 6346 } 6347 6348 @Override 6349 public ComponentName getActivityClassForToken(IBinder token) { 6350 synchronized(this) { 6351 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6352 if (r == null) { 6353 return null; 6354 } 6355 return r.intent.getComponent(); 6356 } 6357 } 6358 6359 @Override 6360 public String getPackageForToken(IBinder token) { 6361 synchronized(this) { 6362 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6363 if (r == null) { 6364 return null; 6365 } 6366 return r.packageName; 6367 } 6368 } 6369 6370 @Override 6371 public IIntentSender getIntentSender(int type, 6372 String packageName, IBinder token, String resultWho, 6373 int requestCode, Intent[] intents, String[] resolvedTypes, 6374 int flags, Bundle options, int userId) { 6375 enforceNotIsolatedCaller("getIntentSender"); 6376 // Refuse possible leaked file descriptors 6377 if (intents != null) { 6378 if (intents.length < 1) { 6379 throw new IllegalArgumentException("Intents array length must be >= 1"); 6380 } 6381 for (int i=0; i<intents.length; i++) { 6382 Intent intent = intents[i]; 6383 if (intent != null) { 6384 if (intent.hasFileDescriptors()) { 6385 throw new IllegalArgumentException("File descriptors passed in Intent"); 6386 } 6387 if (type == ActivityManager.INTENT_SENDER_BROADCAST && 6388 (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 6389 throw new IllegalArgumentException( 6390 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 6391 } 6392 intents[i] = new Intent(intent); 6393 } 6394 } 6395 if (resolvedTypes != null && resolvedTypes.length != intents.length) { 6396 throw new IllegalArgumentException( 6397 "Intent array length does not match resolvedTypes length"); 6398 } 6399 } 6400 if (options != null) { 6401 if (options.hasFileDescriptors()) { 6402 throw new IllegalArgumentException("File descriptors passed in options"); 6403 } 6404 } 6405 6406 synchronized(this) { 6407 int callingUid = Binder.getCallingUid(); 6408 int origUserId = userId; 6409 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 6410 type == ActivityManager.INTENT_SENDER_BROADCAST, 6411 ALLOW_NON_FULL, "getIntentSender", null); 6412 if (origUserId == UserHandle.USER_CURRENT) { 6413 // We don't want to evaluate this until the pending intent is 6414 // actually executed. However, we do want to always do the 6415 // security checking for it above. 6416 userId = UserHandle.USER_CURRENT; 6417 } 6418 try { 6419 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 6420 int uid = AppGlobals.getPackageManager() 6421 .getPackageUid(packageName, UserHandle.getUserId(callingUid)); 6422 if (!UserHandle.isSameApp(callingUid, uid)) { 6423 String msg = "Permission Denial: getIntentSender() from pid=" 6424 + Binder.getCallingPid() 6425 + ", uid=" + Binder.getCallingUid() 6426 + ", (need uid=" + uid + ")" 6427 + " is not allowed to send as package " + packageName; 6428 Slog.w(TAG, msg); 6429 throw new SecurityException(msg); 6430 } 6431 } 6432 6433 return getIntentSenderLocked(type, packageName, callingUid, userId, 6434 token, resultWho, requestCode, intents, resolvedTypes, flags, options); 6435 6436 } catch (RemoteException e) { 6437 throw new SecurityException(e); 6438 } 6439 } 6440 } 6441 6442 IIntentSender getIntentSenderLocked(int type, String packageName, 6443 int callingUid, int userId, IBinder token, String resultWho, 6444 int requestCode, Intent[] intents, String[] resolvedTypes, int flags, 6445 Bundle options) { 6446 if (DEBUG_MU) 6447 Slog.v(TAG_MU, "getIntentSenderLocked(): uid=" + callingUid); 6448 ActivityRecord activity = null; 6449 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 6450 activity = ActivityRecord.isInStackLocked(token); 6451 if (activity == null) { 6452 return null; 6453 } 6454 if (activity.finishing) { 6455 return null; 6456 } 6457 } 6458 6459 final boolean noCreate = (flags&PendingIntent.FLAG_NO_CREATE) != 0; 6460 final boolean cancelCurrent = (flags&PendingIntent.FLAG_CANCEL_CURRENT) != 0; 6461 final boolean updateCurrent = (flags&PendingIntent.FLAG_UPDATE_CURRENT) != 0; 6462 flags &= ~(PendingIntent.FLAG_NO_CREATE|PendingIntent.FLAG_CANCEL_CURRENT 6463 |PendingIntent.FLAG_UPDATE_CURRENT); 6464 6465 PendingIntentRecord.Key key = new PendingIntentRecord.Key( 6466 type, packageName, activity, resultWho, 6467 requestCode, intents, resolvedTypes, flags, options, userId); 6468 WeakReference<PendingIntentRecord> ref; 6469 ref = mIntentSenderRecords.get(key); 6470 PendingIntentRecord rec = ref != null ? ref.get() : null; 6471 if (rec != null) { 6472 if (!cancelCurrent) { 6473 if (updateCurrent) { 6474 if (rec.key.requestIntent != null) { 6475 rec.key.requestIntent.replaceExtras(intents != null ? 6476 intents[intents.length - 1] : null); 6477 } 6478 if (intents != null) { 6479 intents[intents.length-1] = rec.key.requestIntent; 6480 rec.key.allIntents = intents; 6481 rec.key.allResolvedTypes = resolvedTypes; 6482 } else { 6483 rec.key.allIntents = null; 6484 rec.key.allResolvedTypes = null; 6485 } 6486 } 6487 return rec; 6488 } 6489 rec.canceled = true; 6490 mIntentSenderRecords.remove(key); 6491 } 6492 if (noCreate) { 6493 return rec; 6494 } 6495 rec = new PendingIntentRecord(this, key, callingUid); 6496 mIntentSenderRecords.put(key, rec.ref); 6497 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 6498 if (activity.pendingResults == null) { 6499 activity.pendingResults 6500 = new HashSet<WeakReference<PendingIntentRecord>>(); 6501 } 6502 activity.pendingResults.add(rec.ref); 6503 } 6504 return rec; 6505 } 6506 6507 @Override 6508 public void cancelIntentSender(IIntentSender sender) { 6509 if (!(sender instanceof PendingIntentRecord)) { 6510 return; 6511 } 6512 synchronized(this) { 6513 PendingIntentRecord rec = (PendingIntentRecord)sender; 6514 try { 6515 int uid = AppGlobals.getPackageManager() 6516 .getPackageUid(rec.key.packageName, UserHandle.getCallingUserId()); 6517 if (!UserHandle.isSameApp(uid, Binder.getCallingUid())) { 6518 String msg = "Permission Denial: cancelIntentSender() from pid=" 6519 + Binder.getCallingPid() 6520 + ", uid=" + Binder.getCallingUid() 6521 + " is not allowed to cancel packges " 6522 + rec.key.packageName; 6523 Slog.w(TAG, msg); 6524 throw new SecurityException(msg); 6525 } 6526 } catch (RemoteException e) { 6527 throw new SecurityException(e); 6528 } 6529 cancelIntentSenderLocked(rec, true); 6530 } 6531 } 6532 6533 void cancelIntentSenderLocked(PendingIntentRecord rec, boolean cleanActivity) { 6534 rec.canceled = true; 6535 mIntentSenderRecords.remove(rec.key); 6536 if (cleanActivity && rec.key.activity != null) { 6537 rec.key.activity.pendingResults.remove(rec.ref); 6538 } 6539 } 6540 6541 @Override 6542 public String getPackageForIntentSender(IIntentSender pendingResult) { 6543 if (!(pendingResult instanceof PendingIntentRecord)) { 6544 return null; 6545 } 6546 try { 6547 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6548 return res.key.packageName; 6549 } catch (ClassCastException e) { 6550 } 6551 return null; 6552 } 6553 6554 @Override 6555 public int getUidForIntentSender(IIntentSender sender) { 6556 if (sender instanceof PendingIntentRecord) { 6557 try { 6558 PendingIntentRecord res = (PendingIntentRecord)sender; 6559 return res.uid; 6560 } catch (ClassCastException e) { 6561 } 6562 } 6563 return -1; 6564 } 6565 6566 @Override 6567 public boolean isIntentSenderTargetedToPackage(IIntentSender pendingResult) { 6568 if (!(pendingResult instanceof PendingIntentRecord)) { 6569 return false; 6570 } 6571 try { 6572 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6573 if (res.key.allIntents == null) { 6574 return false; 6575 } 6576 for (int i=0; i<res.key.allIntents.length; i++) { 6577 Intent intent = res.key.allIntents[i]; 6578 if (intent.getPackage() != null && intent.getComponent() != null) { 6579 return false; 6580 } 6581 } 6582 return true; 6583 } catch (ClassCastException e) { 6584 } 6585 return false; 6586 } 6587 6588 @Override 6589 public boolean isIntentSenderAnActivity(IIntentSender pendingResult) { 6590 if (!(pendingResult instanceof PendingIntentRecord)) { 6591 return false; 6592 } 6593 try { 6594 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6595 if (res.key.type == ActivityManager.INTENT_SENDER_ACTIVITY) { 6596 return true; 6597 } 6598 return false; 6599 } catch (ClassCastException e) { 6600 } 6601 return false; 6602 } 6603 6604 @Override 6605 public Intent getIntentForIntentSender(IIntentSender pendingResult) { 6606 if (!(pendingResult instanceof PendingIntentRecord)) { 6607 return null; 6608 } 6609 try { 6610 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6611 return res.key.requestIntent != null ? new Intent(res.key.requestIntent) : null; 6612 } catch (ClassCastException e) { 6613 } 6614 return null; 6615 } 6616 6617 @Override 6618 public String getTagForIntentSender(IIntentSender pendingResult, String prefix) { 6619 if (!(pendingResult instanceof PendingIntentRecord)) { 6620 return null; 6621 } 6622 try { 6623 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6624 Intent intent = res.key.requestIntent; 6625 if (intent != null) { 6626 if (res.lastTag != null && res.lastTagPrefix == prefix && (res.lastTagPrefix == null 6627 || res.lastTagPrefix.equals(prefix))) { 6628 return res.lastTag; 6629 } 6630 res.lastTagPrefix = prefix; 6631 StringBuilder sb = new StringBuilder(128); 6632 if (prefix != null) { 6633 sb.append(prefix); 6634 } 6635 if (intent.getAction() != null) { 6636 sb.append(intent.getAction()); 6637 } else if (intent.getComponent() != null) { 6638 intent.getComponent().appendShortString(sb); 6639 } else { 6640 sb.append("?"); 6641 } 6642 return res.lastTag = sb.toString(); 6643 } 6644 } catch (ClassCastException e) { 6645 } 6646 return null; 6647 } 6648 6649 @Override 6650 public void setProcessLimit(int max) { 6651 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 6652 "setProcessLimit()"); 6653 synchronized (this) { 6654 mProcessLimit = max < 0 ? ProcessList.MAX_CACHED_APPS : max; 6655 mProcessLimitOverride = max; 6656 } 6657 trimApplications(); 6658 } 6659 6660 @Override 6661 public int getProcessLimit() { 6662 synchronized (this) { 6663 return mProcessLimitOverride; 6664 } 6665 } 6666 6667 void foregroundTokenDied(ForegroundToken token) { 6668 synchronized (ActivityManagerService.this) { 6669 synchronized (mPidsSelfLocked) { 6670 ForegroundToken cur 6671 = mForegroundProcesses.get(token.pid); 6672 if (cur != token) { 6673 return; 6674 } 6675 mForegroundProcesses.remove(token.pid); 6676 ProcessRecord pr = mPidsSelfLocked.get(token.pid); 6677 if (pr == null) { 6678 return; 6679 } 6680 pr.forcingToForeground = null; 6681 updateProcessForegroundLocked(pr, false, false); 6682 } 6683 updateOomAdjLocked(); 6684 } 6685 } 6686 6687 @Override 6688 public void setProcessForeground(IBinder token, int pid, boolean isForeground) { 6689 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 6690 "setProcessForeground()"); 6691 synchronized(this) { 6692 boolean changed = false; 6693 6694 synchronized (mPidsSelfLocked) { 6695 ProcessRecord pr = mPidsSelfLocked.get(pid); 6696 if (pr == null && isForeground) { 6697 Slog.w(TAG, "setProcessForeground called on unknown pid: " + pid); 6698 return; 6699 } 6700 ForegroundToken oldToken = mForegroundProcesses.get(pid); 6701 if (oldToken != null) { 6702 oldToken.token.unlinkToDeath(oldToken, 0); 6703 mForegroundProcesses.remove(pid); 6704 if (pr != null) { 6705 pr.forcingToForeground = null; 6706 } 6707 changed = true; 6708 } 6709 if (isForeground && token != null) { 6710 ForegroundToken newToken = new ForegroundToken() { 6711 @Override 6712 public void binderDied() { 6713 foregroundTokenDied(this); 6714 } 6715 }; 6716 newToken.pid = pid; 6717 newToken.token = token; 6718 try { 6719 token.linkToDeath(newToken, 0); 6720 mForegroundProcesses.put(pid, newToken); 6721 pr.forcingToForeground = token; 6722 changed = true; 6723 } catch (RemoteException e) { 6724 // If the process died while doing this, we will later 6725 // do the cleanup with the process death link. 6726 } 6727 } 6728 } 6729 6730 if (changed) { 6731 updateOomAdjLocked(); 6732 } 6733 } 6734 } 6735 6736 // ========================================================= 6737 // PERMISSIONS 6738 // ========================================================= 6739 6740 static class PermissionController extends IPermissionController.Stub { 6741 ActivityManagerService mActivityManagerService; 6742 PermissionController(ActivityManagerService activityManagerService) { 6743 mActivityManagerService = activityManagerService; 6744 } 6745 6746 @Override 6747 public boolean checkPermission(String permission, int pid, int uid) { 6748 return mActivityManagerService.checkPermission(permission, pid, 6749 uid) == PackageManager.PERMISSION_GRANTED; 6750 } 6751 } 6752 6753 class IntentFirewallInterface implements IntentFirewall.AMSInterface { 6754 @Override 6755 public int checkComponentPermission(String permission, int pid, int uid, 6756 int owningUid, boolean exported) { 6757 return ActivityManagerService.this.checkComponentPermission(permission, pid, uid, 6758 owningUid, exported); 6759 } 6760 6761 @Override 6762 public Object getAMSLock() { 6763 return ActivityManagerService.this; 6764 } 6765 } 6766 6767 /** 6768 * This can be called with or without the global lock held. 6769 */ 6770 int checkComponentPermission(String permission, int pid, int uid, 6771 int owningUid, boolean exported) { 6772 // We might be performing an operation on behalf of an indirect binder 6773 // invocation, e.g. via {@link #openContentUri}. Check and adjust the 6774 // client identity accordingly before proceeding. 6775 Identity tlsIdentity = sCallerIdentity.get(); 6776 if (tlsIdentity != null) { 6777 Slog.d(TAG, "checkComponentPermission() adjusting {pid,uid} to {" 6778 + tlsIdentity.pid + "," + tlsIdentity.uid + "}"); 6779 uid = tlsIdentity.uid; 6780 pid = tlsIdentity.pid; 6781 } 6782 6783 if (pid == MY_PID) { 6784 return PackageManager.PERMISSION_GRANTED; 6785 } 6786 6787 return ActivityManager.checkComponentPermission(permission, uid, 6788 owningUid, exported); 6789 } 6790 6791 /** 6792 * As the only public entry point for permissions checking, this method 6793 * can enforce the semantic that requesting a check on a null global 6794 * permission is automatically denied. (Internally a null permission 6795 * string is used when calling {@link #checkComponentPermission} in cases 6796 * when only uid-based security is needed.) 6797 * 6798 * This can be called with or without the global lock held. 6799 */ 6800 @Override 6801 public int checkPermission(String permission, int pid, int uid) { 6802 if (permission == null) { 6803 return PackageManager.PERMISSION_DENIED; 6804 } 6805 return checkComponentPermission(permission, pid, UserHandle.getAppId(uid), -1, true); 6806 } 6807 6808 /** 6809 * Binder IPC calls go through the public entry point. 6810 * This can be called with or without the global lock held. 6811 */ 6812 int checkCallingPermission(String permission) { 6813 return checkPermission(permission, 6814 Binder.getCallingPid(), 6815 UserHandle.getAppId(Binder.getCallingUid())); 6816 } 6817 6818 /** 6819 * This can be called with or without the global lock held. 6820 */ 6821 void enforceCallingPermission(String permission, String func) { 6822 if (checkCallingPermission(permission) 6823 == PackageManager.PERMISSION_GRANTED) { 6824 return; 6825 } 6826 6827 String msg = "Permission Denial: " + func + " from pid=" 6828 + Binder.getCallingPid() 6829 + ", uid=" + Binder.getCallingUid() 6830 + " requires " + permission; 6831 Slog.w(TAG, msg); 6832 throw new SecurityException(msg); 6833 } 6834 6835 /** 6836 * Determine if UID is holding permissions required to access {@link Uri} in 6837 * the given {@link ProviderInfo}. Final permission checking is always done 6838 * in {@link ContentProvider}. 6839 */ 6840 private final boolean checkHoldingPermissionsLocked( 6841 IPackageManager pm, ProviderInfo pi, GrantUri grantUri, int uid, final int modeFlags) { 6842 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6843 "checkHoldingPermissionsLocked: uri=" + grantUri + " uid=" + uid); 6844 if (UserHandle.getUserId(uid) != grantUri.sourceUserId) { 6845 if (ActivityManager.checkComponentPermission(INTERACT_ACROSS_USERS, uid, -1, true) 6846 != PERMISSION_GRANTED) { 6847 return false; 6848 } 6849 } 6850 return checkHoldingPermissionsInternalLocked(pm, pi, grantUri, uid, modeFlags, true); 6851 } 6852 6853 private final boolean checkHoldingPermissionsInternalLocked(IPackageManager pm, ProviderInfo pi, 6854 GrantUri grantUri, int uid, final int modeFlags, boolean considerUidPermissions) { 6855 if (pi.applicationInfo.uid == uid) { 6856 return true; 6857 } else if (!pi.exported) { 6858 return false; 6859 } 6860 6861 boolean readMet = (modeFlags & Intent.FLAG_GRANT_READ_URI_PERMISSION) == 0; 6862 boolean writeMet = (modeFlags & Intent.FLAG_GRANT_WRITE_URI_PERMISSION) == 0; 6863 try { 6864 // check if target holds top-level <provider> permissions 6865 if (!readMet && pi.readPermission != null && considerUidPermissions 6866 && (pm.checkUidPermission(pi.readPermission, uid) == PERMISSION_GRANTED)) { 6867 readMet = true; 6868 } 6869 if (!writeMet && pi.writePermission != null && considerUidPermissions 6870 && (pm.checkUidPermission(pi.writePermission, uid) == PERMISSION_GRANTED)) { 6871 writeMet = true; 6872 } 6873 6874 // track if unprotected read/write is allowed; any denied 6875 // <path-permission> below removes this ability 6876 boolean allowDefaultRead = pi.readPermission == null; 6877 boolean allowDefaultWrite = pi.writePermission == null; 6878 6879 // check if target holds any <path-permission> that match uri 6880 final PathPermission[] pps = pi.pathPermissions; 6881 if (pps != null) { 6882 final String path = grantUri.uri.getPath(); 6883 int i = pps.length; 6884 while (i > 0 && (!readMet || !writeMet)) { 6885 i--; 6886 PathPermission pp = pps[i]; 6887 if (pp.match(path)) { 6888 if (!readMet) { 6889 final String pprperm = pp.getReadPermission(); 6890 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking read perm for " 6891 + pprperm + " for " + pp.getPath() 6892 + ": match=" + pp.match(path) 6893 + " check=" + pm.checkUidPermission(pprperm, uid)); 6894 if (pprperm != null) { 6895 if (considerUidPermissions && pm.checkUidPermission(pprperm, uid) 6896 == PERMISSION_GRANTED) { 6897 readMet = true; 6898 } else { 6899 allowDefaultRead = false; 6900 } 6901 } 6902 } 6903 if (!writeMet) { 6904 final String ppwperm = pp.getWritePermission(); 6905 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking write perm " 6906 + ppwperm + " for " + pp.getPath() 6907 + ": match=" + pp.match(path) 6908 + " check=" + pm.checkUidPermission(ppwperm, uid)); 6909 if (ppwperm != null) { 6910 if (considerUidPermissions && pm.checkUidPermission(ppwperm, uid) 6911 == PERMISSION_GRANTED) { 6912 writeMet = true; 6913 } else { 6914 allowDefaultWrite = false; 6915 } 6916 } 6917 } 6918 } 6919 } 6920 } 6921 6922 // grant unprotected <provider> read/write, if not blocked by 6923 // <path-permission> above 6924 if (allowDefaultRead) readMet = true; 6925 if (allowDefaultWrite) writeMet = true; 6926 6927 } catch (RemoteException e) { 6928 return false; 6929 } 6930 6931 return readMet && writeMet; 6932 } 6933 6934 private ProviderInfo getProviderInfoLocked(String authority, int userHandle) { 6935 ProviderInfo pi = null; 6936 ContentProviderRecord cpr = mProviderMap.getProviderByName(authority, userHandle); 6937 if (cpr != null) { 6938 pi = cpr.info; 6939 } else { 6940 try { 6941 pi = AppGlobals.getPackageManager().resolveContentProvider( 6942 authority, PackageManager.GET_URI_PERMISSION_PATTERNS, userHandle); 6943 } catch (RemoteException ex) { 6944 } 6945 } 6946 return pi; 6947 } 6948 6949 private UriPermission findUriPermissionLocked(int targetUid, GrantUri grantUri) { 6950 final ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6951 if (targetUris != null) { 6952 return targetUris.get(grantUri); 6953 } 6954 return null; 6955 } 6956 6957 private UriPermission findOrCreateUriPermissionLocked(String sourcePkg, 6958 String targetPkg, int targetUid, GrantUri grantUri) { 6959 ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6960 if (targetUris == null) { 6961 targetUris = Maps.newArrayMap(); 6962 mGrantedUriPermissions.put(targetUid, targetUris); 6963 } 6964 6965 UriPermission perm = targetUris.get(grantUri); 6966 if (perm == null) { 6967 perm = new UriPermission(sourcePkg, targetPkg, targetUid, grantUri); 6968 targetUris.put(grantUri, perm); 6969 } 6970 6971 return perm; 6972 } 6973 6974 private final boolean checkUriPermissionLocked(GrantUri grantUri, int uid, 6975 final int modeFlags) { 6976 final boolean persistable = (modeFlags & Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION) != 0; 6977 final int minStrength = persistable ? UriPermission.STRENGTH_PERSISTABLE 6978 : UriPermission.STRENGTH_OWNED; 6979 6980 // Root gets to do everything. 6981 if (uid == 0) { 6982 return true; 6983 } 6984 6985 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 6986 if (perms == null) return false; 6987 6988 // First look for exact match 6989 final UriPermission exactPerm = perms.get(grantUri); 6990 if (exactPerm != null && exactPerm.getStrength(modeFlags) >= minStrength) { 6991 return true; 6992 } 6993 6994 // No exact match, look for prefixes 6995 final int N = perms.size(); 6996 for (int i = 0; i < N; i++) { 6997 final UriPermission perm = perms.valueAt(i); 6998 if (perm.uri.prefix && grantUri.uri.isPathPrefixMatch(perm.uri.uri) 6999 && perm.getStrength(modeFlags) >= minStrength) { 7000 return true; 7001 } 7002 } 7003 7004 return false; 7005 } 7006 7007 /** 7008 * @param uri This uri must NOT contain an embedded userId. 7009 * @param userId The userId in which the uri is to be resolved. 7010 */ 7011 @Override 7012 public int checkUriPermission(Uri uri, int pid, int uid, 7013 final int modeFlags, int userId) { 7014 enforceNotIsolatedCaller("checkUriPermission"); 7015 7016 // Another redirected-binder-call permissions check as in 7017 // {@link checkComponentPermission}. 7018 Identity tlsIdentity = sCallerIdentity.get(); 7019 if (tlsIdentity != null) { 7020 uid = tlsIdentity.uid; 7021 pid = tlsIdentity.pid; 7022 } 7023 7024 // Our own process gets to do everything. 7025 if (pid == MY_PID) { 7026 return PackageManager.PERMISSION_GRANTED; 7027 } 7028 synchronized (this) { 7029 return checkUriPermissionLocked(new GrantUri(userId, uri, false), uid, modeFlags) 7030 ? PackageManager.PERMISSION_GRANTED 7031 : PackageManager.PERMISSION_DENIED; 7032 } 7033 } 7034 7035 /** 7036 * Check if the targetPkg can be granted permission to access uri by 7037 * the callingUid using the given modeFlags. Throws a security exception 7038 * if callingUid is not allowed to do this. Returns the uid of the target 7039 * if the URI permission grant should be performed; returns -1 if it is not 7040 * needed (for example targetPkg already has permission to access the URI). 7041 * If you already know the uid of the target, you can supply it in 7042 * lastTargetUid else set that to -1. 7043 */ 7044 int checkGrantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 7045 final int modeFlags, int lastTargetUid) { 7046 if (!Intent.isAccessUriMode(modeFlags)) { 7047 return -1; 7048 } 7049 7050 if (targetPkg != null) { 7051 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7052 "Checking grant " + targetPkg + " permission to " + grantUri); 7053 } 7054 7055 final IPackageManager pm = AppGlobals.getPackageManager(); 7056 7057 // If this is not a content: uri, we can't do anything with it. 7058 if (!ContentResolver.SCHEME_CONTENT.equals(grantUri.uri.getScheme())) { 7059 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7060 "Can't grant URI permission for non-content URI: " + grantUri); 7061 return -1; 7062 } 7063 7064 final String authority = grantUri.uri.getAuthority(); 7065 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 7066 if (pi == null) { 7067 Slog.w(TAG, "No content provider found for permission check: " + 7068 grantUri.uri.toSafeString()); 7069 return -1; 7070 } 7071 7072 int targetUid = lastTargetUid; 7073 if (targetUid < 0 && targetPkg != null) { 7074 try { 7075 targetUid = pm.getPackageUid(targetPkg, UserHandle.getUserId(callingUid)); 7076 if (targetUid < 0) { 7077 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7078 "Can't grant URI permission no uid for: " + targetPkg); 7079 return -1; 7080 } 7081 } catch (RemoteException ex) { 7082 return -1; 7083 } 7084 } 7085 7086 if (targetUid >= 0) { 7087 // First... does the target actually need this permission? 7088 if (checkHoldingPermissionsLocked(pm, pi, grantUri, targetUid, modeFlags)) { 7089 // No need to grant the target this permission. 7090 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7091 "Target " + targetPkg + " already has full permission to " + grantUri); 7092 return -1; 7093 } 7094 } else { 7095 // First... there is no target package, so can anyone access it? 7096 boolean allowed = pi.exported; 7097 if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) { 7098 if (pi.readPermission != null) { 7099 allowed = false; 7100 } 7101 } 7102 if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) { 7103 if (pi.writePermission != null) { 7104 allowed = false; 7105 } 7106 } 7107 if (allowed) { 7108 return -1; 7109 } 7110 } 7111 7112 /* There is a special cross user grant if: 7113 * - The target is on another user. 7114 * - Apps on the current user can access the uri without any uid permissions. 7115 * In this case, we grant a uri permission, even if the ContentProvider does not normally 7116 * grant uri permissions. 7117 */ 7118 boolean specialCrossUserGrant = UserHandle.getUserId(targetUid) != grantUri.sourceUserId 7119 && checkHoldingPermissionsInternalLocked(pm, pi, grantUri, callingUid, 7120 modeFlags, false /*without considering the uid permissions*/); 7121 7122 // Second... is the provider allowing granting of URI permissions? 7123 if (!specialCrossUserGrant) { 7124 if (!pi.grantUriPermissions) { 7125 throw new SecurityException("Provider " + pi.packageName 7126 + "/" + pi.name 7127 + " does not allow granting of Uri permissions (uri " 7128 + grantUri + ")"); 7129 } 7130 if (pi.uriPermissionPatterns != null) { 7131 final int N = pi.uriPermissionPatterns.length; 7132 boolean allowed = false; 7133 for (int i=0; i<N; i++) { 7134 if (pi.uriPermissionPatterns[i] != null 7135 && pi.uriPermissionPatterns[i].match(grantUri.uri.getPath())) { 7136 allowed = true; 7137 break; 7138 } 7139 } 7140 if (!allowed) { 7141 throw new SecurityException("Provider " + pi.packageName 7142 + "/" + pi.name 7143 + " does not allow granting of permission to path of Uri " 7144 + grantUri); 7145 } 7146 } 7147 } 7148 7149 // Third... does the caller itself have permission to access 7150 // this uri? 7151 if (UserHandle.getAppId(callingUid) != Process.SYSTEM_UID) { 7152 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 7153 // Require they hold a strong enough Uri permission 7154 if (!checkUriPermissionLocked(grantUri, callingUid, modeFlags)) { 7155 throw new SecurityException("Uid " + callingUid 7156 + " does not have permission to uri " + grantUri); 7157 } 7158 } 7159 } 7160 return targetUid; 7161 } 7162 7163 /** 7164 * @param uri This uri must NOT contain an embedded userId. 7165 * @param userId The userId in which the uri is to be resolved. 7166 */ 7167 @Override 7168 public int checkGrantUriPermission(int callingUid, String targetPkg, Uri uri, 7169 final int modeFlags, int userId) { 7170 enforceNotIsolatedCaller("checkGrantUriPermission"); 7171 synchronized(this) { 7172 return checkGrantUriPermissionLocked(callingUid, targetPkg, 7173 new GrantUri(userId, uri, false), modeFlags, -1); 7174 } 7175 } 7176 7177 void grantUriPermissionUncheckedLocked(int targetUid, String targetPkg, GrantUri grantUri, 7178 final int modeFlags, UriPermissionOwner owner) { 7179 if (!Intent.isAccessUriMode(modeFlags)) { 7180 return; 7181 } 7182 7183 // So here we are: the caller has the assumed permission 7184 // to the uri, and the target doesn't. Let's now give this to 7185 // the target. 7186 7187 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7188 "Granting " + targetPkg + "/" + targetUid + " permission to " + grantUri); 7189 7190 final String authority = grantUri.uri.getAuthority(); 7191 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 7192 if (pi == null) { 7193 Slog.w(TAG, "No content provider found for grant: " + grantUri.toSafeString()); 7194 return; 7195 } 7196 7197 if ((modeFlags & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0) { 7198 grantUri.prefix = true; 7199 } 7200 final UriPermission perm = findOrCreateUriPermissionLocked( 7201 pi.packageName, targetPkg, targetUid, grantUri); 7202 perm.grantModes(modeFlags, owner); 7203 } 7204 7205 void grantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 7206 final int modeFlags, UriPermissionOwner owner, int targetUserId) { 7207 if (targetPkg == null) { 7208 throw new NullPointerException("targetPkg"); 7209 } 7210 int targetUid; 7211 final IPackageManager pm = AppGlobals.getPackageManager(); 7212 try { 7213 targetUid = pm.getPackageUid(targetPkg, targetUserId); 7214 } catch (RemoteException ex) { 7215 return; 7216 } 7217 7218 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, modeFlags, 7219 targetUid); 7220 if (targetUid < 0) { 7221 return; 7222 } 7223 7224 grantUriPermissionUncheckedLocked(targetUid, targetPkg, grantUri, modeFlags, 7225 owner); 7226 } 7227 7228 static class NeededUriGrants extends ArrayList<GrantUri> { 7229 final String targetPkg; 7230 final int targetUid; 7231 final int flags; 7232 7233 NeededUriGrants(String targetPkg, int targetUid, int flags) { 7234 this.targetPkg = targetPkg; 7235 this.targetUid = targetUid; 7236 this.flags = flags; 7237 } 7238 } 7239 7240 /** 7241 * Like checkGrantUriPermissionLocked, but takes an Intent. 7242 */ 7243 NeededUriGrants checkGrantUriPermissionFromIntentLocked(int callingUid, 7244 String targetPkg, Intent intent, int mode, NeededUriGrants needed, int targetUserId) { 7245 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7246 "Checking URI perm to data=" + (intent != null ? intent.getData() : null) 7247 + " clip=" + (intent != null ? intent.getClipData() : null) 7248 + " from " + intent + "; flags=0x" 7249 + Integer.toHexString(intent != null ? intent.getFlags() : 0)); 7250 7251 if (targetPkg == null) { 7252 throw new NullPointerException("targetPkg"); 7253 } 7254 7255 if (intent == null) { 7256 return null; 7257 } 7258 Uri data = intent.getData(); 7259 ClipData clip = intent.getClipData(); 7260 if (data == null && clip == null) { 7261 return null; 7262 } 7263 // Default userId for uris in the intent (if they don't specify it themselves) 7264 int contentUserHint = intent.getContentUserHint(); 7265 if (contentUserHint == UserHandle.USER_CURRENT) { 7266 contentUserHint = UserHandle.getUserId(callingUid); 7267 } 7268 final IPackageManager pm = AppGlobals.getPackageManager(); 7269 int targetUid; 7270 if (needed != null) { 7271 targetUid = needed.targetUid; 7272 } else { 7273 try { 7274 targetUid = pm.getPackageUid(targetPkg, targetUserId); 7275 } catch (RemoteException ex) { 7276 return null; 7277 } 7278 if (targetUid < 0) { 7279 if (DEBUG_URI_PERMISSION) { 7280 Slog.v(TAG, "Can't grant URI permission no uid for: " + targetPkg 7281 + " on user " + targetUserId); 7282 } 7283 return null; 7284 } 7285 } 7286 if (data != null) { 7287 GrantUri grantUri = GrantUri.resolve(contentUserHint, data); 7288 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 7289 targetUid); 7290 if (targetUid > 0) { 7291 if (needed == null) { 7292 needed = new NeededUriGrants(targetPkg, targetUid, mode); 7293 } 7294 needed.add(grantUri); 7295 } 7296 } 7297 if (clip != null) { 7298 for (int i=0; i<clip.getItemCount(); i++) { 7299 Uri uri = clip.getItemAt(i).getUri(); 7300 if (uri != null) { 7301 GrantUri grantUri = GrantUri.resolve(contentUserHint, uri); 7302 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 7303 targetUid); 7304 if (targetUid > 0) { 7305 if (needed == null) { 7306 needed = new NeededUriGrants(targetPkg, targetUid, mode); 7307 } 7308 needed.add(grantUri); 7309 } 7310 } else { 7311 Intent clipIntent = clip.getItemAt(i).getIntent(); 7312 if (clipIntent != null) { 7313 NeededUriGrants newNeeded = checkGrantUriPermissionFromIntentLocked( 7314 callingUid, targetPkg, clipIntent, mode, needed, targetUserId); 7315 if (newNeeded != null) { 7316 needed = newNeeded; 7317 } 7318 } 7319 } 7320 } 7321 } 7322 7323 return needed; 7324 } 7325 7326 /** 7327 * Like grantUriPermissionUncheckedLocked, but takes an Intent. 7328 */ 7329 void grantUriPermissionUncheckedFromIntentLocked(NeededUriGrants needed, 7330 UriPermissionOwner owner) { 7331 if (needed != null) { 7332 for (int i=0; i<needed.size(); i++) { 7333 GrantUri grantUri = needed.get(i); 7334 grantUriPermissionUncheckedLocked(needed.targetUid, needed.targetPkg, 7335 grantUri, needed.flags, owner); 7336 } 7337 } 7338 } 7339 7340 void grantUriPermissionFromIntentLocked(int callingUid, 7341 String targetPkg, Intent intent, UriPermissionOwner owner, int targetUserId) { 7342 NeededUriGrants needed = checkGrantUriPermissionFromIntentLocked(callingUid, targetPkg, 7343 intent, intent != null ? intent.getFlags() : 0, null, targetUserId); 7344 if (needed == null) { 7345 return; 7346 } 7347 7348 grantUriPermissionUncheckedFromIntentLocked(needed, owner); 7349 } 7350 7351 /** 7352 * @param uri This uri must NOT contain an embedded userId. 7353 * @param userId The userId in which the uri is to be resolved. 7354 */ 7355 @Override 7356 public void grantUriPermission(IApplicationThread caller, String targetPkg, Uri uri, 7357 final int modeFlags, int userId) { 7358 enforceNotIsolatedCaller("grantUriPermission"); 7359 GrantUri grantUri = new GrantUri(userId, uri, false); 7360 synchronized(this) { 7361 final ProcessRecord r = getRecordForAppLocked(caller); 7362 if (r == null) { 7363 throw new SecurityException("Unable to find app for caller " 7364 + caller 7365 + " when granting permission to uri " + grantUri); 7366 } 7367 if (targetPkg == null) { 7368 throw new IllegalArgumentException("null target"); 7369 } 7370 if (grantUri == null) { 7371 throw new IllegalArgumentException("null uri"); 7372 } 7373 7374 Preconditions.checkFlagsArgument(modeFlags, Intent.FLAG_GRANT_READ_URI_PERMISSION 7375 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION 7376 | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION 7377 | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION); 7378 7379 grantUriPermissionLocked(r.uid, targetPkg, grantUri, modeFlags, null, 7380 UserHandle.getUserId(r.uid)); 7381 } 7382 } 7383 7384 void removeUriPermissionIfNeededLocked(UriPermission perm) { 7385 if (perm.modeFlags == 0) { 7386 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 7387 perm.targetUid); 7388 if (perms != null) { 7389 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7390 "Removing " + perm.targetUid + " permission to " + perm.uri); 7391 7392 perms.remove(perm.uri); 7393 if (perms.isEmpty()) { 7394 mGrantedUriPermissions.remove(perm.targetUid); 7395 } 7396 } 7397 } 7398 } 7399 7400 private void revokeUriPermissionLocked(int callingUid, GrantUri grantUri, final int modeFlags) { 7401 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Revoking all granted permissions to " + grantUri); 7402 7403 final IPackageManager pm = AppGlobals.getPackageManager(); 7404 final String authority = grantUri.uri.getAuthority(); 7405 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 7406 if (pi == null) { 7407 Slog.w(TAG, "No content provider found for permission revoke: " 7408 + grantUri.toSafeString()); 7409 return; 7410 } 7411 7412 // Does the caller have this permission on the URI? 7413 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 7414 // Right now, if you are not the original owner of the permission, 7415 // you are not allowed to revoke it. 7416 //if (!checkUriPermissionLocked(uri, callingUid, modeFlags)) { 7417 throw new SecurityException("Uid " + callingUid 7418 + " does not have permission to uri " + grantUri); 7419 //} 7420 } 7421 7422 boolean persistChanged = false; 7423 7424 // Go through all of the permissions and remove any that match. 7425 int N = mGrantedUriPermissions.size(); 7426 for (int i = 0; i < N; i++) { 7427 final int targetUid = mGrantedUriPermissions.keyAt(i); 7428 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 7429 7430 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 7431 final UriPermission perm = it.next(); 7432 if (perm.uri.sourceUserId == grantUri.sourceUserId 7433 && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) { 7434 if (DEBUG_URI_PERMISSION) 7435 Slog.v(TAG, 7436 "Revoking " + perm.targetUid + " permission to " + perm.uri); 7437 persistChanged |= perm.revokeModes( 7438 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 7439 if (perm.modeFlags == 0) { 7440 it.remove(); 7441 } 7442 } 7443 } 7444 7445 if (perms.isEmpty()) { 7446 mGrantedUriPermissions.remove(targetUid); 7447 N--; 7448 i--; 7449 } 7450 } 7451 7452 if (persistChanged) { 7453 schedulePersistUriGrants(); 7454 } 7455 } 7456 7457 /** 7458 * @param uri This uri must NOT contain an embedded userId. 7459 * @param userId The userId in which the uri is to be resolved. 7460 */ 7461 @Override 7462 public void revokeUriPermission(IApplicationThread caller, Uri uri, final int modeFlags, 7463 int userId) { 7464 enforceNotIsolatedCaller("revokeUriPermission"); 7465 synchronized(this) { 7466 final ProcessRecord r = getRecordForAppLocked(caller); 7467 if (r == null) { 7468 throw new SecurityException("Unable to find app for caller " 7469 + caller 7470 + " when revoking permission to uri " + uri); 7471 } 7472 if (uri == null) { 7473 Slog.w(TAG, "revokeUriPermission: null uri"); 7474 return; 7475 } 7476 7477 if (!Intent.isAccessUriMode(modeFlags)) { 7478 return; 7479 } 7480 7481 final IPackageManager pm = AppGlobals.getPackageManager(); 7482 final String authority = uri.getAuthority(); 7483 final ProviderInfo pi = getProviderInfoLocked(authority, userId); 7484 if (pi == null) { 7485 Slog.w(TAG, "No content provider found for permission revoke: " 7486 + uri.toSafeString()); 7487 return; 7488 } 7489 7490 revokeUriPermissionLocked(r.uid, new GrantUri(userId, uri, false), modeFlags); 7491 } 7492 } 7493 7494 /** 7495 * Remove any {@link UriPermission} granted <em>from</em> or <em>to</em> the 7496 * given package. 7497 * 7498 * @param packageName Package name to match, or {@code null} to apply to all 7499 * packages. 7500 * @param userHandle User to match, or {@link UserHandle#USER_ALL} to apply 7501 * to all users. 7502 * @param persistable If persistable grants should be removed. 7503 */ 7504 private void removeUriPermissionsForPackageLocked( 7505 String packageName, int userHandle, boolean persistable) { 7506 if (userHandle == UserHandle.USER_ALL && packageName == null) { 7507 throw new IllegalArgumentException("Must narrow by either package or user"); 7508 } 7509 7510 boolean persistChanged = false; 7511 7512 int N = mGrantedUriPermissions.size(); 7513 for (int i = 0; i < N; i++) { 7514 final int targetUid = mGrantedUriPermissions.keyAt(i); 7515 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 7516 7517 // Only inspect grants matching user 7518 if (userHandle == UserHandle.USER_ALL 7519 || userHandle == UserHandle.getUserId(targetUid)) { 7520 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 7521 final UriPermission perm = it.next(); 7522 7523 // Only inspect grants matching package 7524 if (packageName == null || perm.sourcePkg.equals(packageName) 7525 || perm.targetPkg.equals(packageName)) { 7526 persistChanged |= perm.revokeModes( 7527 persistable ? ~0 : ~Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 7528 7529 // Only remove when no modes remain; any persisted grants 7530 // will keep this alive. 7531 if (perm.modeFlags == 0) { 7532 it.remove(); 7533 } 7534 } 7535 } 7536 7537 if (perms.isEmpty()) { 7538 mGrantedUriPermissions.remove(targetUid); 7539 N--; 7540 i--; 7541 } 7542 } 7543 } 7544 7545 if (persistChanged) { 7546 schedulePersistUriGrants(); 7547 } 7548 } 7549 7550 @Override 7551 public IBinder newUriPermissionOwner(String name) { 7552 enforceNotIsolatedCaller("newUriPermissionOwner"); 7553 synchronized(this) { 7554 UriPermissionOwner owner = new UriPermissionOwner(this, name); 7555 return owner.getExternalTokenLocked(); 7556 } 7557 } 7558 7559 /** 7560 * @param uri This uri must NOT contain an embedded userId. 7561 * @param sourceUserId The userId in which the uri is to be resolved. 7562 * @param targetUserId The userId of the app that receives the grant. 7563 */ 7564 @Override 7565 public void grantUriPermissionFromOwner(IBinder token, int fromUid, String targetPkg, Uri uri, 7566 final int modeFlags, int sourceUserId, int targetUserId) { 7567 targetUserId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 7568 targetUserId, false, ALLOW_FULL_ONLY, "grantUriPermissionFromOwner", null); 7569 synchronized(this) { 7570 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 7571 if (owner == null) { 7572 throw new IllegalArgumentException("Unknown owner: " + token); 7573 } 7574 if (fromUid != Binder.getCallingUid()) { 7575 if (Binder.getCallingUid() != Process.myUid()) { 7576 // Only system code can grant URI permissions on behalf 7577 // of other users. 7578 throw new SecurityException("nice try"); 7579 } 7580 } 7581 if (targetPkg == null) { 7582 throw new IllegalArgumentException("null target"); 7583 } 7584 if (uri == null) { 7585 throw new IllegalArgumentException("null uri"); 7586 } 7587 7588 grantUriPermissionLocked(fromUid, targetPkg, new GrantUri(sourceUserId, uri, false), 7589 modeFlags, owner, targetUserId); 7590 } 7591 } 7592 7593 /** 7594 * @param uri This uri must NOT contain an embedded userId. 7595 * @param userId The userId in which the uri is to be resolved. 7596 */ 7597 @Override 7598 public void revokeUriPermissionFromOwner(IBinder token, Uri uri, int mode, int userId) { 7599 synchronized(this) { 7600 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 7601 if (owner == null) { 7602 throw new IllegalArgumentException("Unknown owner: " + token); 7603 } 7604 7605 if (uri == null) { 7606 owner.removeUriPermissionsLocked(mode); 7607 } else { 7608 owner.removeUriPermissionLocked(new GrantUri(userId, uri, false), mode); 7609 } 7610 } 7611 } 7612 7613 private void schedulePersistUriGrants() { 7614 if (!mHandler.hasMessages(PERSIST_URI_GRANTS_MSG)) { 7615 mHandler.sendMessageDelayed(mHandler.obtainMessage(PERSIST_URI_GRANTS_MSG), 7616 10 * DateUtils.SECOND_IN_MILLIS); 7617 } 7618 } 7619 7620 private void writeGrantedUriPermissions() { 7621 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "writeGrantedUriPermissions()"); 7622 7623 // Snapshot permissions so we can persist without lock 7624 ArrayList<UriPermission.Snapshot> persist = Lists.newArrayList(); 7625 synchronized (this) { 7626 final int size = mGrantedUriPermissions.size(); 7627 for (int i = 0; i < size; i++) { 7628 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 7629 for (UriPermission perm : perms.values()) { 7630 if (perm.persistedModeFlags != 0) { 7631 persist.add(perm.snapshot()); 7632 } 7633 } 7634 } 7635 } 7636 7637 FileOutputStream fos = null; 7638 try { 7639 fos = mGrantFile.startWrite(); 7640 7641 XmlSerializer out = new FastXmlSerializer(); 7642 out.setOutput(fos, "utf-8"); 7643 out.startDocument(null, true); 7644 out.startTag(null, TAG_URI_GRANTS); 7645 for (UriPermission.Snapshot perm : persist) { 7646 out.startTag(null, TAG_URI_GRANT); 7647 writeIntAttribute(out, ATTR_SOURCE_USER_ID, perm.uri.sourceUserId); 7648 writeIntAttribute(out, ATTR_TARGET_USER_ID, perm.targetUserId); 7649 out.attribute(null, ATTR_SOURCE_PKG, perm.sourcePkg); 7650 out.attribute(null, ATTR_TARGET_PKG, perm.targetPkg); 7651 out.attribute(null, ATTR_URI, String.valueOf(perm.uri.uri)); 7652 writeBooleanAttribute(out, ATTR_PREFIX, perm.uri.prefix); 7653 writeIntAttribute(out, ATTR_MODE_FLAGS, perm.persistedModeFlags); 7654 writeLongAttribute(out, ATTR_CREATED_TIME, perm.persistedCreateTime); 7655 out.endTag(null, TAG_URI_GRANT); 7656 } 7657 out.endTag(null, TAG_URI_GRANTS); 7658 out.endDocument(); 7659 7660 mGrantFile.finishWrite(fos); 7661 } catch (IOException e) { 7662 if (fos != null) { 7663 mGrantFile.failWrite(fos); 7664 } 7665 } 7666 } 7667 7668 private void readGrantedUriPermissionsLocked() { 7669 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "readGrantedUriPermissions()"); 7670 7671 final long now = System.currentTimeMillis(); 7672 7673 FileInputStream fis = null; 7674 try { 7675 fis = mGrantFile.openRead(); 7676 final XmlPullParser in = Xml.newPullParser(); 7677 in.setInput(fis, null); 7678 7679 int type; 7680 while ((type = in.next()) != END_DOCUMENT) { 7681 final String tag = in.getName(); 7682 if (type == START_TAG) { 7683 if (TAG_URI_GRANT.equals(tag)) { 7684 final int sourceUserId; 7685 final int targetUserId; 7686 final int userHandle = readIntAttribute(in, 7687 ATTR_USER_HANDLE, UserHandle.USER_NULL); 7688 if (userHandle != UserHandle.USER_NULL) { 7689 // For backwards compatibility. 7690 sourceUserId = userHandle; 7691 targetUserId = userHandle; 7692 } else { 7693 sourceUserId = readIntAttribute(in, ATTR_SOURCE_USER_ID); 7694 targetUserId = readIntAttribute(in, ATTR_TARGET_USER_ID); 7695 } 7696 final String sourcePkg = in.getAttributeValue(null, ATTR_SOURCE_PKG); 7697 final String targetPkg = in.getAttributeValue(null, ATTR_TARGET_PKG); 7698 final Uri uri = Uri.parse(in.getAttributeValue(null, ATTR_URI)); 7699 final boolean prefix = readBooleanAttribute(in, ATTR_PREFIX); 7700 final int modeFlags = readIntAttribute(in, ATTR_MODE_FLAGS); 7701 final long createdTime = readLongAttribute(in, ATTR_CREATED_TIME, now); 7702 7703 // Sanity check that provider still belongs to source package 7704 final ProviderInfo pi = getProviderInfoLocked( 7705 uri.getAuthority(), sourceUserId); 7706 if (pi != null && sourcePkg.equals(pi.packageName)) { 7707 int targetUid = -1; 7708 try { 7709 targetUid = AppGlobals.getPackageManager() 7710 .getPackageUid(targetPkg, targetUserId); 7711 } catch (RemoteException e) { 7712 } 7713 if (targetUid != -1) { 7714 final UriPermission perm = findOrCreateUriPermissionLocked( 7715 sourcePkg, targetPkg, targetUid, 7716 new GrantUri(sourceUserId, uri, prefix)); 7717 perm.initPersistedModes(modeFlags, createdTime); 7718 } 7719 } else { 7720 Slog.w(TAG, "Persisted grant for " + uri + " had source " + sourcePkg 7721 + " but instead found " + pi); 7722 } 7723 } 7724 } 7725 } 7726 } catch (FileNotFoundException e) { 7727 // Missing grants is okay 7728 } catch (IOException e) { 7729 Log.wtf(TAG, "Failed reading Uri grants", e); 7730 } catch (XmlPullParserException e) { 7731 Log.wtf(TAG, "Failed reading Uri grants", e); 7732 } finally { 7733 IoUtils.closeQuietly(fis); 7734 } 7735 } 7736 7737 /** 7738 * @param uri This uri must NOT contain an embedded userId. 7739 * @param userId The userId in which the uri is to be resolved. 7740 */ 7741 @Override 7742 public void takePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 7743 enforceNotIsolatedCaller("takePersistableUriPermission"); 7744 7745 Preconditions.checkFlagsArgument(modeFlags, 7746 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 7747 7748 synchronized (this) { 7749 final int callingUid = Binder.getCallingUid(); 7750 boolean persistChanged = false; 7751 GrantUri grantUri = new GrantUri(userId, uri, false); 7752 7753 UriPermission exactPerm = findUriPermissionLocked(callingUid, 7754 new GrantUri(userId, uri, false)); 7755 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 7756 new GrantUri(userId, uri, true)); 7757 7758 final boolean exactValid = (exactPerm != null) 7759 && ((modeFlags & exactPerm.persistableModeFlags) == modeFlags); 7760 final boolean prefixValid = (prefixPerm != null) 7761 && ((modeFlags & prefixPerm.persistableModeFlags) == modeFlags); 7762 7763 if (!(exactValid || prefixValid)) { 7764 throw new SecurityException("No persistable permission grants found for UID " 7765 + callingUid + " and Uri " + grantUri.toSafeString()); 7766 } 7767 7768 if (exactValid) { 7769 persistChanged |= exactPerm.takePersistableModes(modeFlags); 7770 } 7771 if (prefixValid) { 7772 persistChanged |= prefixPerm.takePersistableModes(modeFlags); 7773 } 7774 7775 persistChanged |= maybePrunePersistedUriGrantsLocked(callingUid); 7776 7777 if (persistChanged) { 7778 schedulePersistUriGrants(); 7779 } 7780 } 7781 } 7782 7783 /** 7784 * @param uri This uri must NOT contain an embedded userId. 7785 * @param userId The userId in which the uri is to be resolved. 7786 */ 7787 @Override 7788 public void releasePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 7789 enforceNotIsolatedCaller("releasePersistableUriPermission"); 7790 7791 Preconditions.checkFlagsArgument(modeFlags, 7792 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 7793 7794 synchronized (this) { 7795 final int callingUid = Binder.getCallingUid(); 7796 boolean persistChanged = false; 7797 7798 UriPermission exactPerm = findUriPermissionLocked(callingUid, 7799 new GrantUri(userId, uri, false)); 7800 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 7801 new GrantUri(userId, uri, true)); 7802 if (exactPerm == null && prefixPerm == null) { 7803 throw new SecurityException("No permission grants found for UID " + callingUid 7804 + " and Uri " + uri.toSafeString()); 7805 } 7806 7807 if (exactPerm != null) { 7808 persistChanged |= exactPerm.releasePersistableModes(modeFlags); 7809 removeUriPermissionIfNeededLocked(exactPerm); 7810 } 7811 if (prefixPerm != null) { 7812 persistChanged |= prefixPerm.releasePersistableModes(modeFlags); 7813 removeUriPermissionIfNeededLocked(prefixPerm); 7814 } 7815 7816 if (persistChanged) { 7817 schedulePersistUriGrants(); 7818 } 7819 } 7820 } 7821 7822 /** 7823 * Prune any older {@link UriPermission} for the given UID until outstanding 7824 * persisted grants are below {@link #MAX_PERSISTED_URI_GRANTS}. 7825 * 7826 * @return if any mutations occured that require persisting. 7827 */ 7828 private boolean maybePrunePersistedUriGrantsLocked(int uid) { 7829 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 7830 if (perms == null) return false; 7831 if (perms.size() < MAX_PERSISTED_URI_GRANTS) return false; 7832 7833 final ArrayList<UriPermission> persisted = Lists.newArrayList(); 7834 for (UriPermission perm : perms.values()) { 7835 if (perm.persistedModeFlags != 0) { 7836 persisted.add(perm); 7837 } 7838 } 7839 7840 final int trimCount = persisted.size() - MAX_PERSISTED_URI_GRANTS; 7841 if (trimCount <= 0) return false; 7842 7843 Collections.sort(persisted, new UriPermission.PersistedTimeComparator()); 7844 for (int i = 0; i < trimCount; i++) { 7845 final UriPermission perm = persisted.get(i); 7846 7847 if (DEBUG_URI_PERMISSION) { 7848 Slog.v(TAG, "Trimming grant created at " + perm.persistedCreateTime); 7849 } 7850 7851 perm.releasePersistableModes(~0); 7852 removeUriPermissionIfNeededLocked(perm); 7853 } 7854 7855 return true; 7856 } 7857 7858 @Override 7859 public ParceledListSlice<android.content.UriPermission> getPersistedUriPermissions( 7860 String packageName, boolean incoming) { 7861 enforceNotIsolatedCaller("getPersistedUriPermissions"); 7862 Preconditions.checkNotNull(packageName, "packageName"); 7863 7864 final int callingUid = Binder.getCallingUid(); 7865 final IPackageManager pm = AppGlobals.getPackageManager(); 7866 try { 7867 final int packageUid = pm.getPackageUid(packageName, UserHandle.getUserId(callingUid)); 7868 if (packageUid != callingUid) { 7869 throw new SecurityException( 7870 "Package " + packageName + " does not belong to calling UID " + callingUid); 7871 } 7872 } catch (RemoteException e) { 7873 throw new SecurityException("Failed to verify package name ownership"); 7874 } 7875 7876 final ArrayList<android.content.UriPermission> result = Lists.newArrayList(); 7877 synchronized (this) { 7878 if (incoming) { 7879 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 7880 callingUid); 7881 if (perms == null) { 7882 Slog.w(TAG, "No permission grants found for " + packageName); 7883 } else { 7884 for (UriPermission perm : perms.values()) { 7885 if (packageName.equals(perm.targetPkg) && perm.persistedModeFlags != 0) { 7886 result.add(perm.buildPersistedPublicApiObject()); 7887 } 7888 } 7889 } 7890 } else { 7891 final int size = mGrantedUriPermissions.size(); 7892 for (int i = 0; i < size; i++) { 7893 final ArrayMap<GrantUri, UriPermission> perms = 7894 mGrantedUriPermissions.valueAt(i); 7895 for (UriPermission perm : perms.values()) { 7896 if (packageName.equals(perm.sourcePkg) && perm.persistedModeFlags != 0) { 7897 result.add(perm.buildPersistedPublicApiObject()); 7898 } 7899 } 7900 } 7901 } 7902 } 7903 return new ParceledListSlice<android.content.UriPermission>(result); 7904 } 7905 7906 @Override 7907 public void showWaitingForDebugger(IApplicationThread who, boolean waiting) { 7908 synchronized (this) { 7909 ProcessRecord app = 7910 who != null ? getRecordForAppLocked(who) : null; 7911 if (app == null) return; 7912 7913 Message msg = Message.obtain(); 7914 msg.what = WAIT_FOR_DEBUGGER_MSG; 7915 msg.obj = app; 7916 msg.arg1 = waiting ? 1 : 0; 7917 mHandler.sendMessage(msg); 7918 } 7919 } 7920 7921 @Override 7922 public void getMemoryInfo(ActivityManager.MemoryInfo outInfo) { 7923 final long homeAppMem = mProcessList.getMemLevel(ProcessList.HOME_APP_ADJ); 7924 final long cachedAppMem = mProcessList.getMemLevel(ProcessList.CACHED_APP_MIN_ADJ); 7925 outInfo.availMem = Process.getFreeMemory(); 7926 outInfo.totalMem = Process.getTotalMemory(); 7927 outInfo.threshold = homeAppMem; 7928 outInfo.lowMemory = outInfo.availMem < (homeAppMem + ((cachedAppMem-homeAppMem)/2)); 7929 outInfo.hiddenAppThreshold = cachedAppMem; 7930 outInfo.secondaryServerThreshold = mProcessList.getMemLevel( 7931 ProcessList.SERVICE_ADJ); 7932 outInfo.visibleAppThreshold = mProcessList.getMemLevel( 7933 ProcessList.VISIBLE_APP_ADJ); 7934 outInfo.foregroundAppThreshold = mProcessList.getMemLevel( 7935 ProcessList.FOREGROUND_APP_ADJ); 7936 } 7937 7938 // ========================================================= 7939 // TASK MANAGEMENT 7940 // ========================================================= 7941 7942 @Override 7943 public List<IAppTask> getAppTasks(String callingPackage) { 7944 int callingUid = Binder.getCallingUid(); 7945 long ident = Binder.clearCallingIdentity(); 7946 7947 synchronized(this) { 7948 ArrayList<IAppTask> list = new ArrayList<IAppTask>(); 7949 try { 7950 if (localLOGV) Slog.v(TAG, "getAppTasks"); 7951 7952 final int N = mRecentTasks.size(); 7953 for (int i = 0; i < N; i++) { 7954 TaskRecord tr = mRecentTasks.get(i); 7955 // Skip tasks that do not match the caller. We don't need to verify 7956 // callingPackage, because we are also limiting to callingUid and know 7957 // that will limit to the correct security sandbox. 7958 if (tr.effectiveUid != callingUid) { 7959 continue; 7960 } 7961 Intent intent = tr.getBaseIntent(); 7962 if (intent == null || 7963 !callingPackage.equals(intent.getComponent().getPackageName())) { 7964 continue; 7965 } 7966 ActivityManager.RecentTaskInfo taskInfo = 7967 createRecentTaskInfoFromTaskRecord(tr); 7968 AppTaskImpl taskImpl = new AppTaskImpl(taskInfo.persistentId, callingUid); 7969 list.add(taskImpl); 7970 } 7971 } finally { 7972 Binder.restoreCallingIdentity(ident); 7973 } 7974 return list; 7975 } 7976 } 7977 7978 @Override 7979 public List<RunningTaskInfo> getTasks(int maxNum, int flags) { 7980 final int callingUid = Binder.getCallingUid(); 7981 ArrayList<RunningTaskInfo> list = new ArrayList<RunningTaskInfo>(); 7982 7983 synchronized(this) { 7984 if (localLOGV) Slog.v( 7985 TAG, "getTasks: max=" + maxNum + ", flags=" + flags); 7986 7987 final boolean allowed = checkCallingPermission( 7988 android.Manifest.permission.GET_TASKS) 7989 == PackageManager.PERMISSION_GRANTED; 7990 if (!allowed) { 7991 Slog.w(TAG, "getTasks: caller " + callingUid 7992 + " does not hold GET_TASKS; limiting output"); 7993 } 7994 7995 // TODO: Improve with MRU list from all ActivityStacks. 7996 mStackSupervisor.getTasksLocked(maxNum, list, callingUid, allowed); 7997 } 7998 7999 return list; 8000 } 8001 8002 TaskRecord getMostRecentTask() { 8003 return mRecentTasks.get(0); 8004 } 8005 8006 /** 8007 * Creates a new RecentTaskInfo from a TaskRecord. 8008 */ 8009 private ActivityManager.RecentTaskInfo createRecentTaskInfoFromTaskRecord(TaskRecord tr) { 8010 // Update the task description to reflect any changes in the task stack 8011 tr.updateTaskDescription(); 8012 8013 // Compose the recent task info 8014 ActivityManager.RecentTaskInfo rti = new ActivityManager.RecentTaskInfo(); 8015 rti.id = tr.getTopActivity() == null ? -1 : tr.taskId; 8016 rti.persistentId = tr.taskId; 8017 rti.baseIntent = new Intent(tr.getBaseIntent()); 8018 rti.origActivity = tr.origActivity; 8019 rti.description = tr.lastDescription; 8020 rti.stackId = tr.stack != null ? tr.stack.mStackId : -1; 8021 rti.userId = tr.userId; 8022 rti.taskDescription = new ActivityManager.TaskDescription(tr.lastTaskDescription); 8023 rti.firstActiveTime = tr.firstActiveTime; 8024 rti.lastActiveTime = tr.lastActiveTime; 8025 rti.affiliatedTaskId = tr.mAffiliatedTaskId; 8026 rti.affiliatedTaskColor = tr.mAffiliatedTaskColor; 8027 return rti; 8028 } 8029 8030 @Override 8031 public List<ActivityManager.RecentTaskInfo> getRecentTasks(int maxNum, int flags, int userId) { 8032 final int callingUid = Binder.getCallingUid(); 8033 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 8034 false, ALLOW_FULL_ONLY, "getRecentTasks", null); 8035 8036 final boolean includeProfiles = (flags & ActivityManager.RECENT_INCLUDE_PROFILES) != 0; 8037 final boolean withExcluded = (flags&ActivityManager.RECENT_WITH_EXCLUDED) != 0; 8038 synchronized (this) { 8039 final boolean allowed = checkCallingPermission(android.Manifest.permission.GET_TASKS) 8040 == PackageManager.PERMISSION_GRANTED; 8041 if (!allowed) { 8042 Slog.w(TAG, "getRecentTasks: caller " + callingUid 8043 + " does not hold GET_TASKS; limiting output"); 8044 } 8045 final boolean detailed = checkCallingPermission( 8046 android.Manifest.permission.GET_DETAILED_TASKS) 8047 == PackageManager.PERMISSION_GRANTED; 8048 8049 final int N = mRecentTasks.size(); 8050 ArrayList<ActivityManager.RecentTaskInfo> res 8051 = new ArrayList<ActivityManager.RecentTaskInfo>( 8052 maxNum < N ? maxNum : N); 8053 8054 final Set<Integer> includedUsers; 8055 if (includeProfiles) { 8056 includedUsers = getProfileIdsLocked(userId); 8057 } else { 8058 includedUsers = new HashSet<Integer>(); 8059 } 8060 includedUsers.add(Integer.valueOf(userId)); 8061 8062 for (int i=0; i<N && maxNum > 0; i++) { 8063 TaskRecord tr = mRecentTasks.get(i); 8064 // Only add calling user or related users recent tasks 8065 if (!includedUsers.contains(Integer.valueOf(tr.userId))) { 8066 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, not user: " + tr); 8067 continue; 8068 } 8069 8070 // Return the entry if desired by the caller. We always return 8071 // the first entry, because callers always expect this to be the 8072 // foreground app. We may filter others if the caller has 8073 // not supplied RECENT_WITH_EXCLUDED and there is some reason 8074 // we should exclude the entry. 8075 8076 if (i == 0 8077 || withExcluded 8078 || (tr.intent == null) 8079 || ((tr.intent.getFlags() & Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS) 8080 == 0)) { 8081 if (!allowed) { 8082 // If the caller doesn't have the GET_TASKS permission, then only 8083 // allow them to see a small subset of tasks -- their own and home. 8084 if (!tr.isHomeTask() && tr.effectiveUid != callingUid) { 8085 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, not allowed: " + tr); 8086 continue; 8087 } 8088 } 8089 if ((flags & ActivityManager.RECENT_IGNORE_HOME_STACK_TASKS) != 0) { 8090 if (tr.stack != null && tr.stack.isHomeStack()) { 8091 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, home stack task: " + tr); 8092 continue; 8093 } 8094 } 8095 if (tr.autoRemoveRecents && tr.getTopActivity() == null) { 8096 // Don't include auto remove tasks that are finished or finishing. 8097 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, auto-remove without activity: " 8098 + tr); 8099 continue; 8100 } 8101 if ((flags&ActivityManager.RECENT_IGNORE_UNAVAILABLE) != 0 8102 && !tr.isAvailable) { 8103 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, unavail real act: " + tr); 8104 continue; 8105 } 8106 8107 ActivityManager.RecentTaskInfo rti = createRecentTaskInfoFromTaskRecord(tr); 8108 if (!detailed) { 8109 rti.baseIntent.replaceExtras((Bundle)null); 8110 } 8111 8112 res.add(rti); 8113 maxNum--; 8114 } 8115 } 8116 return res; 8117 } 8118 } 8119 8120 private TaskRecord recentTaskForIdLocked(int id) { 8121 final int N = mRecentTasks.size(); 8122 for (int i=0; i<N; i++) { 8123 TaskRecord tr = mRecentTasks.get(i); 8124 if (tr.taskId == id) { 8125 return tr; 8126 } 8127 } 8128 return null; 8129 } 8130 8131 @Override 8132 public ActivityManager.TaskThumbnail getTaskThumbnail(int id) { 8133 synchronized (this) { 8134 enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER, 8135 "getTaskThumbnail()"); 8136 TaskRecord tr = recentTaskForIdLocked(id); 8137 if (tr != null) { 8138 return tr.getTaskThumbnailLocked(); 8139 } 8140 } 8141 return null; 8142 } 8143 8144 @Override 8145 public int addAppTask(IBinder activityToken, Intent intent, 8146 ActivityManager.TaskDescription description, Bitmap thumbnail) throws RemoteException { 8147 final int callingUid = Binder.getCallingUid(); 8148 final long callingIdent = Binder.clearCallingIdentity(); 8149 8150 try { 8151 synchronized (this) { 8152 ActivityRecord r = ActivityRecord.isInStackLocked(activityToken); 8153 if (r == null) { 8154 throw new IllegalArgumentException("Activity does not exist; token=" 8155 + activityToken); 8156 } 8157 ComponentName comp = intent.getComponent(); 8158 if (comp == null) { 8159 throw new IllegalArgumentException("Intent " + intent 8160 + " must specify explicit component"); 8161 } 8162 if (thumbnail.getWidth() != mThumbnailWidth 8163 || thumbnail.getHeight() != mThumbnailHeight) { 8164 throw new IllegalArgumentException("Bad thumbnail size: got " 8165 + thumbnail.getWidth() + "x" + thumbnail.getHeight() + ", require " 8166 + mThumbnailWidth + "x" + mThumbnailHeight); 8167 } 8168 if (intent.getSelector() != null) { 8169 intent.setSelector(null); 8170 } 8171 if (intent.getSourceBounds() != null) { 8172 intent.setSourceBounds(null); 8173 } 8174 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_DOCUMENT) != 0) { 8175 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS) == 0) { 8176 // The caller has added this as an auto-remove task... that makes no 8177 // sense, so turn off auto-remove. 8178 intent.addFlags(Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS); 8179 } 8180 } else if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_TASK) != 0) { 8181 // Must be a new task. 8182 intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 8183 } 8184 if (!comp.equals(mLastAddedTaskComponent) || callingUid != mLastAddedTaskUid) { 8185 mLastAddedTaskActivity = null; 8186 } 8187 ActivityInfo ainfo = mLastAddedTaskActivity; 8188 if (ainfo == null) { 8189 ainfo = mLastAddedTaskActivity = AppGlobals.getPackageManager().getActivityInfo( 8190 comp, 0, UserHandle.getUserId(callingUid)); 8191 if (ainfo.applicationInfo.uid != callingUid) { 8192 throw new SecurityException( 8193 "Can't add task for another application: target uid=" 8194 + ainfo.applicationInfo.uid + ", calling uid=" + callingUid); 8195 } 8196 } 8197 8198 TaskRecord task = new TaskRecord(this, mStackSupervisor.getNextTaskId(), ainfo, 8199 intent, description); 8200 8201 int trimIdx = trimRecentsForTask(task, false); 8202 if (trimIdx >= 0) { 8203 // If this would have caused a trim, then we'll abort because that 8204 // means it would be added at the end of the list but then just removed. 8205 return -1; 8206 } 8207 8208 final int N = mRecentTasks.size(); 8209 if (N >= (ActivityManager.getMaxRecentTasksStatic()-1)) { 8210 final TaskRecord tr = mRecentTasks.remove(N - 1); 8211 tr.removedFromRecents(mTaskPersister); 8212 } 8213 8214 task.inRecents = true; 8215 mRecentTasks.add(task); 8216 r.task.stack.addTask(task, false, false); 8217 8218 task.setLastThumbnail(thumbnail); 8219 task.freeLastThumbnail(); 8220 8221 return task.taskId; 8222 } 8223 } finally { 8224 Binder.restoreCallingIdentity(callingIdent); 8225 } 8226 } 8227 8228 @Override 8229 public Point getAppTaskThumbnailSize() { 8230 synchronized (this) { 8231 return new Point(mThumbnailWidth, mThumbnailHeight); 8232 } 8233 } 8234 8235 @Override 8236 public void setTaskDescription(IBinder token, ActivityManager.TaskDescription td) { 8237 synchronized (this) { 8238 ActivityRecord r = ActivityRecord.isInStackLocked(token); 8239 if (r != null) { 8240 r.taskDescription = td; 8241 r.task.updateTaskDescription(); 8242 } 8243 } 8244 } 8245 8246 private void cleanUpRemovedTaskLocked(TaskRecord tr, int flags) { 8247 mRecentTasks.remove(tr); 8248 tr.removedFromRecents(mTaskPersister); 8249 final boolean killProcesses = (flags&ActivityManager.REMOVE_TASK_KILL_PROCESS) != 0; 8250 Intent baseIntent = new Intent( 8251 tr.intent != null ? tr.intent : tr.affinityIntent); 8252 ComponentName component = baseIntent.getComponent(); 8253 if (component == null) { 8254 Slog.w(TAG, "Now component for base intent of task: " + tr); 8255 return; 8256 } 8257 8258 // Find any running services associated with this app. 8259 mServices.cleanUpRemovedTaskLocked(tr, component, baseIntent); 8260 8261 if (killProcesses) { 8262 // Find any running processes associated with this app. 8263 final String pkg = component.getPackageName(); 8264 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 8265 ArrayMap<String, SparseArray<ProcessRecord>> pmap = mProcessNames.getMap(); 8266 for (int i=0; i<pmap.size(); i++) { 8267 SparseArray<ProcessRecord> uids = pmap.valueAt(i); 8268 for (int j=0; j<uids.size(); j++) { 8269 ProcessRecord proc = uids.valueAt(j); 8270 if (proc.userId != tr.userId) { 8271 continue; 8272 } 8273 if (!proc.pkgList.containsKey(pkg)) { 8274 continue; 8275 } 8276 procs.add(proc); 8277 } 8278 } 8279 8280 // Kill the running processes. 8281 for (int i=0; i<procs.size(); i++) { 8282 ProcessRecord pr = procs.get(i); 8283 if (pr == mHomeProcess) { 8284 // Don't kill the home process along with tasks from the same package. 8285 continue; 8286 } 8287 if (pr.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 8288 pr.kill("remove task", true); 8289 } else { 8290 pr.waitingToKill = "remove task"; 8291 } 8292 } 8293 } 8294 } 8295 8296 /** 8297 * Removes the task with the specified task id. 8298 * 8299 * @param taskId Identifier of the task to be removed. 8300 * @param flags Additional operational flags. May be 0 or 8301 * {@link ActivityManager#REMOVE_TASK_KILL_PROCESS}. 8302 * @return Returns true if the given task was found and removed. 8303 */ 8304 private boolean removeTaskByIdLocked(int taskId, int flags) { 8305 TaskRecord tr = recentTaskForIdLocked(taskId); 8306 if (tr != null) { 8307 tr.removeTaskActivitiesLocked(); 8308 cleanUpRemovedTaskLocked(tr, flags); 8309 if (tr.isPersistable) { 8310 notifyTaskPersisterLocked(null, true); 8311 } 8312 return true; 8313 } 8314 return false; 8315 } 8316 8317 @Override 8318 public boolean removeTask(int taskId, int flags) { 8319 synchronized (this) { 8320 enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, 8321 "removeTask()"); 8322 long ident = Binder.clearCallingIdentity(); 8323 try { 8324 return removeTaskByIdLocked(taskId, flags); 8325 } finally { 8326 Binder.restoreCallingIdentity(ident); 8327 } 8328 } 8329 } 8330 8331 /** 8332 * TODO: Add mController hook 8333 */ 8334 @Override 8335 public void moveTaskToFront(int taskId, int flags, Bundle options) { 8336 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 8337 "moveTaskToFront()"); 8338 8339 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToFront: moving taskId=" + taskId); 8340 synchronized(this) { 8341 moveTaskToFrontLocked(taskId, flags, options); 8342 } 8343 } 8344 8345 void moveTaskToFrontLocked(int taskId, int flags, Bundle options) { 8346 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 8347 Binder.getCallingUid(), "Task to front")) { 8348 ActivityOptions.abort(options); 8349 return; 8350 } 8351 final long origId = Binder.clearCallingIdentity(); 8352 try { 8353 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 8354 if (task == null) { 8355 return; 8356 } 8357 if (mStackSupervisor.isLockTaskModeViolation(task)) { 8358 mStackSupervisor.showLockTaskToast(); 8359 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode"); 8360 return; 8361 } 8362 final ActivityRecord prev = mStackSupervisor.topRunningActivityLocked(); 8363 if (prev != null && prev.isRecentsActivity()) { 8364 task.setTaskToReturnTo(ActivityRecord.RECENTS_ACTIVITY_TYPE); 8365 } 8366 mStackSupervisor.findTaskToMoveToFrontLocked(task, flags, options); 8367 } finally { 8368 Binder.restoreCallingIdentity(origId); 8369 } 8370 ActivityOptions.abort(options); 8371 } 8372 8373 @Override 8374 public void moveTaskToBack(int taskId) { 8375 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 8376 "moveTaskToBack()"); 8377 8378 synchronized(this) { 8379 TaskRecord tr = recentTaskForIdLocked(taskId); 8380 if (tr != null) { 8381 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToBack: moving task=" + tr); 8382 ActivityStack stack = tr.stack; 8383 if (stack.mResumedActivity != null && stack.mResumedActivity.task == tr) { 8384 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 8385 Binder.getCallingUid(), "Task to back")) { 8386 return; 8387 } 8388 } 8389 final long origId = Binder.clearCallingIdentity(); 8390 try { 8391 stack.moveTaskToBackLocked(taskId, null); 8392 } finally { 8393 Binder.restoreCallingIdentity(origId); 8394 } 8395 } 8396 } 8397 } 8398 8399 /** 8400 * Moves an activity, and all of the other activities within the same task, to the bottom 8401 * of the history stack. The activity's order within the task is unchanged. 8402 * 8403 * @param token A reference to the activity we wish to move 8404 * @param nonRoot If false then this only works if the activity is the root 8405 * of a task; if true it will work for any activity in a task. 8406 * @return Returns true if the move completed, false if not. 8407 */ 8408 @Override 8409 public boolean moveActivityTaskToBack(IBinder token, boolean nonRoot) { 8410 enforceNotIsolatedCaller("moveActivityTaskToBack"); 8411 synchronized(this) { 8412 final long origId = Binder.clearCallingIdentity(); 8413 int taskId = ActivityRecord.getTaskForActivityLocked(token, !nonRoot); 8414 if (taskId >= 0) { 8415 return ActivityRecord.getStackLocked(token).moveTaskToBackLocked(taskId, null); 8416 } 8417 Binder.restoreCallingIdentity(origId); 8418 } 8419 return false; 8420 } 8421 8422 @Override 8423 public void moveTaskBackwards(int task) { 8424 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 8425 "moveTaskBackwards()"); 8426 8427 synchronized(this) { 8428 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 8429 Binder.getCallingUid(), "Task backwards")) { 8430 return; 8431 } 8432 final long origId = Binder.clearCallingIdentity(); 8433 moveTaskBackwardsLocked(task); 8434 Binder.restoreCallingIdentity(origId); 8435 } 8436 } 8437 8438 private final void moveTaskBackwardsLocked(int task) { 8439 Slog.e(TAG, "moveTaskBackwards not yet implemented!"); 8440 } 8441 8442 @Override 8443 public IBinder getHomeActivityToken() throws RemoteException { 8444 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8445 "getHomeActivityToken()"); 8446 synchronized (this) { 8447 return mStackSupervisor.getHomeActivityToken(); 8448 } 8449 } 8450 8451 @Override 8452 public IActivityContainer createActivityContainer(IBinder parentActivityToken, 8453 IActivityContainerCallback callback) throws RemoteException { 8454 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8455 "createActivityContainer()"); 8456 synchronized (this) { 8457 if (parentActivityToken == null) { 8458 throw new IllegalArgumentException("parent token must not be null"); 8459 } 8460 ActivityRecord r = ActivityRecord.forToken(parentActivityToken); 8461 if (r == null) { 8462 return null; 8463 } 8464 if (callback == null) { 8465 throw new IllegalArgumentException("callback must not be null"); 8466 } 8467 return mStackSupervisor.createActivityContainer(r, callback); 8468 } 8469 } 8470 8471 @Override 8472 public void deleteActivityContainer(IActivityContainer container) throws RemoteException { 8473 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8474 "deleteActivityContainer()"); 8475 synchronized (this) { 8476 mStackSupervisor.deleteActivityContainer(container); 8477 } 8478 } 8479 8480 @Override 8481 public IActivityContainer getEnclosingActivityContainer(IBinder activityToken) 8482 throws RemoteException { 8483 synchronized (this) { 8484 ActivityStack stack = ActivityRecord.getStackLocked(activityToken); 8485 if (stack != null) { 8486 return stack.mActivityContainer; 8487 } 8488 return null; 8489 } 8490 } 8491 8492 @Override 8493 public void moveTaskToStack(int taskId, int stackId, boolean toTop) { 8494 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8495 "moveTaskToStack()"); 8496 if (stackId == HOME_STACK_ID) { 8497 Slog.e(TAG, "moveTaskToStack: Attempt to move task " + taskId + " to home stack", 8498 new RuntimeException("here").fillInStackTrace()); 8499 } 8500 synchronized (this) { 8501 long ident = Binder.clearCallingIdentity(); 8502 try { 8503 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToStack: moving task=" + taskId + " to stackId=" 8504 + stackId + " toTop=" + toTop); 8505 mStackSupervisor.moveTaskToStack(taskId, stackId, toTop); 8506 } finally { 8507 Binder.restoreCallingIdentity(ident); 8508 } 8509 } 8510 } 8511 8512 @Override 8513 public void resizeStack(int stackBoxId, Rect bounds) { 8514 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8515 "resizeStackBox()"); 8516 long ident = Binder.clearCallingIdentity(); 8517 try { 8518 mWindowManager.resizeStack(stackBoxId, bounds); 8519 } finally { 8520 Binder.restoreCallingIdentity(ident); 8521 } 8522 } 8523 8524 @Override 8525 public List<StackInfo> getAllStackInfos() { 8526 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8527 "getAllStackInfos()"); 8528 long ident = Binder.clearCallingIdentity(); 8529 try { 8530 synchronized (this) { 8531 return mStackSupervisor.getAllStackInfosLocked(); 8532 } 8533 } finally { 8534 Binder.restoreCallingIdentity(ident); 8535 } 8536 } 8537 8538 @Override 8539 public StackInfo getStackInfo(int stackId) { 8540 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8541 "getStackInfo()"); 8542 long ident = Binder.clearCallingIdentity(); 8543 try { 8544 synchronized (this) { 8545 return mStackSupervisor.getStackInfoLocked(stackId); 8546 } 8547 } finally { 8548 Binder.restoreCallingIdentity(ident); 8549 } 8550 } 8551 8552 @Override 8553 public boolean isInHomeStack(int taskId) { 8554 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8555 "getStackInfo()"); 8556 long ident = Binder.clearCallingIdentity(); 8557 try { 8558 synchronized (this) { 8559 TaskRecord tr = recentTaskForIdLocked(taskId); 8560 return tr != null && tr.stack != null && tr.stack.isHomeStack(); 8561 } 8562 } finally { 8563 Binder.restoreCallingIdentity(ident); 8564 } 8565 } 8566 8567 @Override 8568 public int getTaskForActivity(IBinder token, boolean onlyRoot) { 8569 synchronized(this) { 8570 return ActivityRecord.getTaskForActivityLocked(token, onlyRoot); 8571 } 8572 } 8573 8574 private boolean isLockTaskAuthorized(String pkg) { 8575 final DevicePolicyManager dpm = (DevicePolicyManager) 8576 mContext.getSystemService(Context.DEVICE_POLICY_SERVICE); 8577 try { 8578 int uid = mContext.getPackageManager().getPackageUid(pkg, 8579 Binder.getCallingUserHandle().getIdentifier()); 8580 return (uid == Binder.getCallingUid()) && dpm != null && dpm.isLockTaskPermitted(pkg); 8581 } catch (NameNotFoundException e) { 8582 return false; 8583 } 8584 } 8585 8586 void startLockTaskMode(TaskRecord task) { 8587 final String pkg; 8588 synchronized (this) { 8589 pkg = task.intent.getComponent().getPackageName(); 8590 } 8591 boolean isSystemInitiated = Binder.getCallingUid() == Process.SYSTEM_UID; 8592 if (!isSystemInitiated && !isLockTaskAuthorized(pkg)) { 8593 final TaskRecord taskRecord = task; 8594 mHandler.post(new Runnable() { 8595 @Override 8596 public void run() { 8597 mLockToAppRequest.showLockTaskPrompt(taskRecord); 8598 } 8599 }); 8600 return; 8601 } 8602 long ident = Binder.clearCallingIdentity(); 8603 try { 8604 synchronized (this) { 8605 // Since we lost lock on task, make sure it is still there. 8606 task = mStackSupervisor.anyTaskForIdLocked(task.taskId); 8607 if (task != null) { 8608 if (!isSystemInitiated 8609 && ((mFocusedActivity == null) || (task != mFocusedActivity.task))) { 8610 throw new IllegalArgumentException("Invalid task, not in foreground"); 8611 } 8612 mStackSupervisor.setLockTaskModeLocked(task, !isSystemInitiated); 8613 } 8614 } 8615 } finally { 8616 Binder.restoreCallingIdentity(ident); 8617 } 8618 } 8619 8620 @Override 8621 public void startLockTaskMode(int taskId) { 8622 final TaskRecord task; 8623 long ident = Binder.clearCallingIdentity(); 8624 try { 8625 synchronized (this) { 8626 task = mStackSupervisor.anyTaskForIdLocked(taskId); 8627 } 8628 } finally { 8629 Binder.restoreCallingIdentity(ident); 8630 } 8631 if (task != null) { 8632 startLockTaskMode(task); 8633 } 8634 } 8635 8636 @Override 8637 public void startLockTaskMode(IBinder token) { 8638 final TaskRecord task; 8639 long ident = Binder.clearCallingIdentity(); 8640 try { 8641 synchronized (this) { 8642 final ActivityRecord r = ActivityRecord.forToken(token); 8643 if (r == null) { 8644 return; 8645 } 8646 task = r.task; 8647 } 8648 } finally { 8649 Binder.restoreCallingIdentity(ident); 8650 } 8651 if (task != null) { 8652 startLockTaskMode(task); 8653 } 8654 } 8655 8656 @Override 8657 public void startLockTaskModeOnCurrent() throws RemoteException { 8658 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8659 "startLockTaskModeOnCurrent"); 8660 ActivityRecord r = null; 8661 synchronized (this) { 8662 r = mStackSupervisor.topRunningActivityLocked(); 8663 } 8664 startLockTaskMode(r.task); 8665 } 8666 8667 @Override 8668 public void stopLockTaskMode() { 8669 // Verify that the user matches the package of the intent for the TaskRecord 8670 // we are locked to or systtem. This will ensure the same caller for startLockTaskMode 8671 // and stopLockTaskMode. 8672 final int callingUid = Binder.getCallingUid(); 8673 if (callingUid != Process.SYSTEM_UID) { 8674 try { 8675 String pkg = 8676 mStackSupervisor.mLockTaskModeTask.intent.getComponent().getPackageName(); 8677 int uid = mContext.getPackageManager().getPackageUid(pkg, 8678 Binder.getCallingUserHandle().getIdentifier()); 8679 if (uid != callingUid) { 8680 throw new SecurityException("Invalid uid, expected " + uid); 8681 } 8682 } catch (NameNotFoundException e) { 8683 Log.d(TAG, "stopLockTaskMode " + e); 8684 return; 8685 } 8686 } 8687 long ident = Binder.clearCallingIdentity(); 8688 try { 8689 Log.d(TAG, "stopLockTaskMode"); 8690 // Stop lock task 8691 synchronized (this) { 8692 mStackSupervisor.setLockTaskModeLocked(null, false); 8693 } 8694 } finally { 8695 Binder.restoreCallingIdentity(ident); 8696 } 8697 } 8698 8699 @Override 8700 public void stopLockTaskModeOnCurrent() throws RemoteException { 8701 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8702 "stopLockTaskModeOnCurrent"); 8703 long ident = Binder.clearCallingIdentity(); 8704 try { 8705 stopLockTaskMode(); 8706 } finally { 8707 Binder.restoreCallingIdentity(ident); 8708 } 8709 } 8710 8711 @Override 8712 public boolean isInLockTaskMode() { 8713 synchronized (this) { 8714 return mStackSupervisor.isInLockTaskMode(); 8715 } 8716 } 8717 8718 // ========================================================= 8719 // CONTENT PROVIDERS 8720 // ========================================================= 8721 8722 private final List<ProviderInfo> generateApplicationProvidersLocked(ProcessRecord app) { 8723 List<ProviderInfo> providers = null; 8724 try { 8725 providers = AppGlobals.getPackageManager(). 8726 queryContentProviders(app.processName, app.uid, 8727 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS); 8728 } catch (RemoteException ex) { 8729 } 8730 if (DEBUG_MU) 8731 Slog.v(TAG_MU, "generateApplicationProvidersLocked, app.info.uid = " + app.uid); 8732 int userId = app.userId; 8733 if (providers != null) { 8734 int N = providers.size(); 8735 app.pubProviders.ensureCapacity(N + app.pubProviders.size()); 8736 for (int i=0; i<N; i++) { 8737 ProviderInfo cpi = 8738 (ProviderInfo)providers.get(i); 8739 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo, 8740 cpi.name, cpi.flags); 8741 if (singleton && UserHandle.getUserId(app.uid) != 0) { 8742 // This is a singleton provider, but a user besides the 8743 // default user is asking to initialize a process it runs 8744 // in... well, no, it doesn't actually run in this process, 8745 // it runs in the process of the default user. Get rid of it. 8746 providers.remove(i); 8747 N--; 8748 i--; 8749 continue; 8750 } 8751 8752 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 8753 ContentProviderRecord cpr = mProviderMap.getProviderByClass(comp, userId); 8754 if (cpr == null) { 8755 cpr = new ContentProviderRecord(this, cpi, app.info, comp, singleton); 8756 mProviderMap.putProviderByClass(comp, cpr); 8757 } 8758 if (DEBUG_MU) 8759 Slog.v(TAG_MU, "generateApplicationProvidersLocked, cpi.uid = " + cpr.uid); 8760 app.pubProviders.put(cpi.name, cpr); 8761 if (!cpi.multiprocess || !"android".equals(cpi.packageName)) { 8762 // Don't add this if it is a platform component that is marked 8763 // to run in multiple processes, because this is actually 8764 // part of the framework so doesn't make sense to track as a 8765 // separate apk in the process. 8766 app.addPackage(cpi.applicationInfo.packageName, cpi.applicationInfo.versionCode, 8767 mProcessStats); 8768 } 8769 ensurePackageDexOpt(cpi.applicationInfo.packageName); 8770 } 8771 } 8772 return providers; 8773 } 8774 8775 /** 8776 * Check if {@link ProcessRecord} has a possible chance at accessing the 8777 * given {@link ProviderInfo}. Final permission checking is always done 8778 * in {@link ContentProvider}. 8779 */ 8780 private final String checkContentProviderPermissionLocked( 8781 ProviderInfo cpi, ProcessRecord r, int userId, boolean checkUser) { 8782 final int callingPid = (r != null) ? r.pid : Binder.getCallingPid(); 8783 final int callingUid = (r != null) ? r.uid : Binder.getCallingUid(); 8784 boolean checkedGrants = false; 8785 if (checkUser) { 8786 // Looking for cross-user grants before enforcing the typical cross-users permissions 8787 int tmpTargetUserId = unsafeConvertIncomingUser(userId); 8788 if (tmpTargetUserId != UserHandle.getUserId(callingUid)) { 8789 if (checkAuthorityGrants(callingUid, cpi, tmpTargetUserId, checkUser)) { 8790 return null; 8791 } 8792 checkedGrants = true; 8793 } 8794 userId = handleIncomingUser(callingPid, callingUid, userId, 8795 false, ALLOW_NON_FULL, 8796 "checkContentProviderPermissionLocked " + cpi.authority, null); 8797 if (userId != tmpTargetUserId) { 8798 // When we actually went to determine the final targer user ID, this ended 8799 // up different than our initial check for the authority. This is because 8800 // they had asked for USER_CURRENT_OR_SELF and we ended up switching to 8801 // SELF. So we need to re-check the grants again. 8802 checkedGrants = false; 8803 } 8804 } 8805 if (checkComponentPermission(cpi.readPermission, callingPid, callingUid, 8806 cpi.applicationInfo.uid, cpi.exported) 8807 == PackageManager.PERMISSION_GRANTED) { 8808 return null; 8809 } 8810 if (checkComponentPermission(cpi.writePermission, callingPid, callingUid, 8811 cpi.applicationInfo.uid, cpi.exported) 8812 == PackageManager.PERMISSION_GRANTED) { 8813 return null; 8814 } 8815 8816 PathPermission[] pps = cpi.pathPermissions; 8817 if (pps != null) { 8818 int i = pps.length; 8819 while (i > 0) { 8820 i--; 8821 PathPermission pp = pps[i]; 8822 String pprperm = pp.getReadPermission(); 8823 if (pprperm != null && checkComponentPermission(pprperm, callingPid, callingUid, 8824 cpi.applicationInfo.uid, cpi.exported) 8825 == PackageManager.PERMISSION_GRANTED) { 8826 return null; 8827 } 8828 String ppwperm = pp.getWritePermission(); 8829 if (ppwperm != null && checkComponentPermission(ppwperm, callingPid, callingUid, 8830 cpi.applicationInfo.uid, cpi.exported) 8831 == PackageManager.PERMISSION_GRANTED) { 8832 return null; 8833 } 8834 } 8835 } 8836 if (!checkedGrants && checkAuthorityGrants(callingUid, cpi, userId, checkUser)) { 8837 return null; 8838 } 8839 8840 String msg; 8841 if (!cpi.exported) { 8842 msg = "Permission Denial: opening provider " + cpi.name 8843 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 8844 + ", uid=" + callingUid + ") that is not exported from uid " 8845 + cpi.applicationInfo.uid; 8846 } else { 8847 msg = "Permission Denial: opening provider " + cpi.name 8848 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 8849 + ", uid=" + callingUid + ") requires " 8850 + cpi.readPermission + " or " + cpi.writePermission; 8851 } 8852 Slog.w(TAG, msg); 8853 return msg; 8854 } 8855 8856 /** 8857 * Returns if the ContentProvider has granted a uri to callingUid 8858 */ 8859 boolean checkAuthorityGrants(int callingUid, ProviderInfo cpi, int userId, boolean checkUser) { 8860 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 8861 if (perms != null) { 8862 for (int i=perms.size()-1; i>=0; i--) { 8863 GrantUri grantUri = perms.keyAt(i); 8864 if (grantUri.sourceUserId == userId || !checkUser) { 8865 if (matchesProvider(grantUri.uri, cpi)) { 8866 return true; 8867 } 8868 } 8869 } 8870 } 8871 return false; 8872 } 8873 8874 /** 8875 * Returns true if the uri authority is one of the authorities specified in the provider. 8876 */ 8877 boolean matchesProvider(Uri uri, ProviderInfo cpi) { 8878 String uriAuth = uri.getAuthority(); 8879 String cpiAuth = cpi.authority; 8880 if (cpiAuth.indexOf(';') == -1) { 8881 return cpiAuth.equals(uriAuth); 8882 } 8883 String[] cpiAuths = cpiAuth.split(";"); 8884 int length = cpiAuths.length; 8885 for (int i = 0; i < length; i++) { 8886 if (cpiAuths[i].equals(uriAuth)) return true; 8887 } 8888 return false; 8889 } 8890 8891 ContentProviderConnection incProviderCountLocked(ProcessRecord r, 8892 final ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 8893 if (r != null) { 8894 for (int i=0; i<r.conProviders.size(); i++) { 8895 ContentProviderConnection conn = r.conProviders.get(i); 8896 if (conn.provider == cpr) { 8897 if (DEBUG_PROVIDER) Slog.v(TAG, 8898 "Adding provider requested by " 8899 + r.processName + " from process " 8900 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 8901 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 8902 if (stable) { 8903 conn.stableCount++; 8904 conn.numStableIncs++; 8905 } else { 8906 conn.unstableCount++; 8907 conn.numUnstableIncs++; 8908 } 8909 return conn; 8910 } 8911 } 8912 ContentProviderConnection conn = new ContentProviderConnection(cpr, r); 8913 if (stable) { 8914 conn.stableCount = 1; 8915 conn.numStableIncs = 1; 8916 } else { 8917 conn.unstableCount = 1; 8918 conn.numUnstableIncs = 1; 8919 } 8920 cpr.connections.add(conn); 8921 r.conProviders.add(conn); 8922 return conn; 8923 } 8924 cpr.addExternalProcessHandleLocked(externalProcessToken); 8925 return null; 8926 } 8927 8928 boolean decProviderCountLocked(ContentProviderConnection conn, 8929 ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 8930 if (conn != null) { 8931 cpr = conn.provider; 8932 if (DEBUG_PROVIDER) Slog.v(TAG, 8933 "Removing provider requested by " 8934 + conn.client.processName + " from process " 8935 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 8936 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 8937 if (stable) { 8938 conn.stableCount--; 8939 } else { 8940 conn.unstableCount--; 8941 } 8942 if (conn.stableCount == 0 && conn.unstableCount == 0) { 8943 cpr.connections.remove(conn); 8944 conn.client.conProviders.remove(conn); 8945 return true; 8946 } 8947 return false; 8948 } 8949 cpr.removeExternalProcessHandleLocked(externalProcessToken); 8950 return false; 8951 } 8952 8953 private void checkTime(long startTime, String where) { 8954 long now = SystemClock.elapsedRealtime(); 8955 if ((now-startTime) > 1000) { 8956 // If we are taking more than a second, log about it. 8957 Slog.w(TAG, "Slow operation: " + (now-startTime) + "ms so far, now at " + where); 8958 } 8959 } 8960 8961 private final ContentProviderHolder getContentProviderImpl(IApplicationThread caller, 8962 String name, IBinder token, boolean stable, int userId) { 8963 ContentProviderRecord cpr; 8964 ContentProviderConnection conn = null; 8965 ProviderInfo cpi = null; 8966 8967 synchronized(this) { 8968 long startTime = SystemClock.elapsedRealtime(); 8969 8970 ProcessRecord r = null; 8971 if (caller != null) { 8972 r = getRecordForAppLocked(caller); 8973 if (r == null) { 8974 throw new SecurityException( 8975 "Unable to find app for caller " + caller 8976 + " (pid=" + Binder.getCallingPid() 8977 + ") when getting content provider " + name); 8978 } 8979 } 8980 8981 boolean checkCrossUser = true; 8982 8983 checkTime(startTime, "getContentProviderImpl: getProviderByName"); 8984 8985 // First check if this content provider has been published... 8986 cpr = mProviderMap.getProviderByName(name, userId); 8987 // If that didn't work, check if it exists for user 0 and then 8988 // verify that it's a singleton provider before using it. 8989 if (cpr == null && userId != UserHandle.USER_OWNER) { 8990 cpr = mProviderMap.getProviderByName(name, UserHandle.USER_OWNER); 8991 if (cpr != null) { 8992 cpi = cpr.info; 8993 if (isSingleton(cpi.processName, cpi.applicationInfo, 8994 cpi.name, cpi.flags) 8995 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid)) { 8996 userId = UserHandle.USER_OWNER; 8997 checkCrossUser = false; 8998 } else { 8999 cpr = null; 9000 cpi = null; 9001 } 9002 } 9003 } 9004 9005 boolean providerRunning = cpr != null; 9006 if (providerRunning) { 9007 cpi = cpr.info; 9008 String msg; 9009 checkTime(startTime, "getContentProviderImpl: before checkContentProviderPermission"); 9010 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, checkCrossUser)) 9011 != null) { 9012 throw new SecurityException(msg); 9013 } 9014 checkTime(startTime, "getContentProviderImpl: after checkContentProviderPermission"); 9015 9016 if (r != null && cpr.canRunHere(r)) { 9017 // This provider has been published or is in the process 9018 // of being published... but it is also allowed to run 9019 // in the caller's process, so don't make a connection 9020 // and just let the caller instantiate its own instance. 9021 ContentProviderHolder holder = cpr.newHolder(null); 9022 // don't give caller the provider object, it needs 9023 // to make its own. 9024 holder.provider = null; 9025 return holder; 9026 } 9027 9028 final long origId = Binder.clearCallingIdentity(); 9029 9030 checkTime(startTime, "getContentProviderImpl: incProviderCountLocked"); 9031 9032 // In this case the provider instance already exists, so we can 9033 // return it right away. 9034 conn = incProviderCountLocked(r, cpr, token, stable); 9035 if (conn != null && (conn.stableCount+conn.unstableCount) == 1) { 9036 if (cpr.proc != null && r.setAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 9037 // If this is a perceptible app accessing the provider, 9038 // make sure to count it as being accessed and thus 9039 // back up on the LRU list. This is good because 9040 // content providers are often expensive to start. 9041 checkTime(startTime, "getContentProviderImpl: before updateLruProcess"); 9042 updateLruProcessLocked(cpr.proc, false, null); 9043 checkTime(startTime, "getContentProviderImpl: after updateLruProcess"); 9044 } 9045 } 9046 9047 if (cpr.proc != null) { 9048 if (false) { 9049 if (cpr.name.flattenToShortString().equals( 9050 "com.android.providers.calendar/.CalendarProvider2")) { 9051 Slog.v(TAG, "****************** KILLING " 9052 + cpr.name.flattenToShortString()); 9053 Process.killProcess(cpr.proc.pid); 9054 } 9055 } 9056 checkTime(startTime, "getContentProviderImpl: before updateOomAdj"); 9057 boolean success = updateOomAdjLocked(cpr.proc); 9058 checkTime(startTime, "getContentProviderImpl: after updateOomAdj"); 9059 if (DEBUG_PROVIDER) Slog.i(TAG, "Adjust success: " + success); 9060 // NOTE: there is still a race here where a signal could be 9061 // pending on the process even though we managed to update its 9062 // adj level. Not sure what to do about this, but at least 9063 // the race is now smaller. 9064 if (!success) { 9065 // Uh oh... it looks like the provider's process 9066 // has been killed on us. We need to wait for a new 9067 // process to be started, and make sure its death 9068 // doesn't kill our process. 9069 Slog.i(TAG, 9070 "Existing provider " + cpr.name.flattenToShortString() 9071 + " is crashing; detaching " + r); 9072 boolean lastRef = decProviderCountLocked(conn, cpr, token, stable); 9073 checkTime(startTime, "getContentProviderImpl: before appDied"); 9074 appDiedLocked(cpr.proc); 9075 checkTime(startTime, "getContentProviderImpl: after appDied"); 9076 if (!lastRef) { 9077 // This wasn't the last ref our process had on 9078 // the provider... we have now been killed, bail. 9079 return null; 9080 } 9081 providerRunning = false; 9082 conn = null; 9083 } 9084 } 9085 9086 Binder.restoreCallingIdentity(origId); 9087 } 9088 9089 boolean singleton; 9090 if (!providerRunning) { 9091 try { 9092 checkTime(startTime, "getContentProviderImpl: before resolveContentProvider"); 9093 cpi = AppGlobals.getPackageManager(). 9094 resolveContentProvider(name, 9095 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS, userId); 9096 checkTime(startTime, "getContentProviderImpl: after resolveContentProvider"); 9097 } catch (RemoteException ex) { 9098 } 9099 if (cpi == null) { 9100 return null; 9101 } 9102 // If the provider is a singleton AND 9103 // (it's a call within the same user || the provider is a 9104 // privileged app) 9105 // Then allow connecting to the singleton provider 9106 singleton = isSingleton(cpi.processName, cpi.applicationInfo, 9107 cpi.name, cpi.flags) 9108 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid); 9109 if (singleton) { 9110 userId = UserHandle.USER_OWNER; 9111 } 9112 cpi.applicationInfo = getAppInfoForUser(cpi.applicationInfo, userId); 9113 checkTime(startTime, "getContentProviderImpl: got app info for user"); 9114 9115 String msg; 9116 checkTime(startTime, "getContentProviderImpl: before checkContentProviderPermission"); 9117 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, !singleton)) 9118 != null) { 9119 throw new SecurityException(msg); 9120 } 9121 checkTime(startTime, "getContentProviderImpl: after checkContentProviderPermission"); 9122 9123 if (!mProcessesReady && !mDidUpdate && !mWaitingUpdate 9124 && !cpi.processName.equals("system")) { 9125 // If this content provider does not run in the system 9126 // process, and the system is not yet ready to run other 9127 // processes, then fail fast instead of hanging. 9128 throw new IllegalArgumentException( 9129 "Attempt to launch content provider before system ready"); 9130 } 9131 9132 // Make sure that the user who owns this provider is started. If not, 9133 // we don't want to allow it to run. 9134 if (mStartedUsers.get(userId) == null) { 9135 Slog.w(TAG, "Unable to launch app " 9136 + cpi.applicationInfo.packageName + "/" 9137 + cpi.applicationInfo.uid + " for provider " 9138 + name + ": user " + userId + " is stopped"); 9139 return null; 9140 } 9141 9142 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 9143 checkTime(startTime, "getContentProviderImpl: before getProviderByClass"); 9144 cpr = mProviderMap.getProviderByClass(comp, userId); 9145 checkTime(startTime, "getContentProviderImpl: after getProviderByClass"); 9146 final boolean firstClass = cpr == null; 9147 if (firstClass) { 9148 try { 9149 checkTime(startTime, "getContentProviderImpl: before getApplicationInfo"); 9150 ApplicationInfo ai = 9151 AppGlobals.getPackageManager(). 9152 getApplicationInfo( 9153 cpi.applicationInfo.packageName, 9154 STOCK_PM_FLAGS, userId); 9155 checkTime(startTime, "getContentProviderImpl: after getApplicationInfo"); 9156 if (ai == null) { 9157 Slog.w(TAG, "No package info for content provider " 9158 + cpi.name); 9159 return null; 9160 } 9161 ai = getAppInfoForUser(ai, userId); 9162 cpr = new ContentProviderRecord(this, cpi, ai, comp, singleton); 9163 } catch (RemoteException ex) { 9164 // pm is in same process, this will never happen. 9165 } 9166 } 9167 9168 checkTime(startTime, "getContentProviderImpl: now have ContentProviderRecord"); 9169 9170 if (r != null && cpr.canRunHere(r)) { 9171 // If this is a multiprocess provider, then just return its 9172 // info and allow the caller to instantiate it. Only do 9173 // this if the provider is the same user as the caller's 9174 // process, or can run as root (so can be in any process). 9175 return cpr.newHolder(null); 9176 } 9177 9178 if (DEBUG_PROVIDER) { 9179 RuntimeException e = new RuntimeException("here"); 9180 Slog.w(TAG, "LAUNCHING REMOTE PROVIDER (myuid " + (r != null ? r.uid : null) 9181 + " pruid " + cpr.appInfo.uid + "): " + cpr.info.name, e); 9182 } 9183 9184 // This is single process, and our app is now connecting to it. 9185 // See if we are already in the process of launching this 9186 // provider. 9187 final int N = mLaunchingProviders.size(); 9188 int i; 9189 for (i=0; i<N; i++) { 9190 if (mLaunchingProviders.get(i) == cpr) { 9191 break; 9192 } 9193 } 9194 9195 // If the provider is not already being launched, then get it 9196 // started. 9197 if (i >= N) { 9198 final long origId = Binder.clearCallingIdentity(); 9199 9200 try { 9201 // Content provider is now in use, its package can't be stopped. 9202 try { 9203 checkTime(startTime, "getContentProviderImpl: before set stopped state"); 9204 AppGlobals.getPackageManager().setPackageStoppedState( 9205 cpr.appInfo.packageName, false, userId); 9206 checkTime(startTime, "getContentProviderImpl: after set stopped state"); 9207 } catch (RemoteException e) { 9208 } catch (IllegalArgumentException e) { 9209 Slog.w(TAG, "Failed trying to unstop package " 9210 + cpr.appInfo.packageName + ": " + e); 9211 } 9212 9213 // Use existing process if already started 9214 checkTime(startTime, "getContentProviderImpl: looking for process record"); 9215 ProcessRecord proc = getProcessRecordLocked( 9216 cpi.processName, cpr.appInfo.uid, false); 9217 if (proc != null && proc.thread != null) { 9218 if (DEBUG_PROVIDER) { 9219 Slog.d(TAG, "Installing in existing process " + proc); 9220 } 9221 checkTime(startTime, "getContentProviderImpl: scheduling install"); 9222 proc.pubProviders.put(cpi.name, cpr); 9223 try { 9224 proc.thread.scheduleInstallProvider(cpi); 9225 } catch (RemoteException e) { 9226 } 9227 } else { 9228 checkTime(startTime, "getContentProviderImpl: before start process"); 9229 proc = startProcessLocked(cpi.processName, 9230 cpr.appInfo, false, 0, "content provider", 9231 new ComponentName(cpi.applicationInfo.packageName, 9232 cpi.name), false, false, false); 9233 checkTime(startTime, "getContentProviderImpl: after start process"); 9234 if (proc == null) { 9235 Slog.w(TAG, "Unable to launch app " 9236 + cpi.applicationInfo.packageName + "/" 9237 + cpi.applicationInfo.uid + " for provider " 9238 + name + ": process is bad"); 9239 return null; 9240 } 9241 } 9242 cpr.launchingApp = proc; 9243 mLaunchingProviders.add(cpr); 9244 } finally { 9245 Binder.restoreCallingIdentity(origId); 9246 } 9247 } 9248 9249 checkTime(startTime, "getContentProviderImpl: updating data structures"); 9250 9251 // Make sure the provider is published (the same provider class 9252 // may be published under multiple names). 9253 if (firstClass) { 9254 mProviderMap.putProviderByClass(comp, cpr); 9255 } 9256 9257 mProviderMap.putProviderByName(name, cpr); 9258 conn = incProviderCountLocked(r, cpr, token, stable); 9259 if (conn != null) { 9260 conn.waiting = true; 9261 } 9262 } 9263 checkTime(startTime, "getContentProviderImpl: done!"); 9264 } 9265 9266 // Wait for the provider to be published... 9267 synchronized (cpr) { 9268 while (cpr.provider == null) { 9269 if (cpr.launchingApp == null) { 9270 Slog.w(TAG, "Unable to launch app " 9271 + cpi.applicationInfo.packageName + "/" 9272 + cpi.applicationInfo.uid + " for provider " 9273 + name + ": launching app became null"); 9274 EventLog.writeEvent(EventLogTags.AM_PROVIDER_LOST_PROCESS, 9275 UserHandle.getUserId(cpi.applicationInfo.uid), 9276 cpi.applicationInfo.packageName, 9277 cpi.applicationInfo.uid, name); 9278 return null; 9279 } 9280 try { 9281 if (DEBUG_MU) { 9282 Slog.v(TAG_MU, "Waiting to start provider " + cpr + " launchingApp=" 9283 + cpr.launchingApp); 9284 } 9285 if (conn != null) { 9286 conn.waiting = true; 9287 } 9288 cpr.wait(); 9289 } catch (InterruptedException ex) { 9290 } finally { 9291 if (conn != null) { 9292 conn.waiting = false; 9293 } 9294 } 9295 } 9296 } 9297 return cpr != null ? cpr.newHolder(conn) : null; 9298 } 9299 9300 @Override 9301 public final ContentProviderHolder getContentProvider( 9302 IApplicationThread caller, String name, int userId, boolean stable) { 9303 enforceNotIsolatedCaller("getContentProvider"); 9304 if (caller == null) { 9305 String msg = "null IApplicationThread when getting content provider " 9306 + name; 9307 Slog.w(TAG, msg); 9308 throw new SecurityException(msg); 9309 } 9310 // The incoming user check is now handled in checkContentProviderPermissionLocked() to deal 9311 // with cross-user grant. 9312 return getContentProviderImpl(caller, name, null, stable, userId); 9313 } 9314 9315 public ContentProviderHolder getContentProviderExternal( 9316 String name, int userId, IBinder token) { 9317 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 9318 "Do not have permission in call getContentProviderExternal()"); 9319 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 9320 false, ALLOW_FULL_ONLY, "getContentProvider", null); 9321 return getContentProviderExternalUnchecked(name, token, userId); 9322 } 9323 9324 private ContentProviderHolder getContentProviderExternalUnchecked(String name, 9325 IBinder token, int userId) { 9326 return getContentProviderImpl(null, name, token, true, userId); 9327 } 9328 9329 /** 9330 * Drop a content provider from a ProcessRecord's bookkeeping 9331 */ 9332 public void removeContentProvider(IBinder connection, boolean stable) { 9333 enforceNotIsolatedCaller("removeContentProvider"); 9334 long ident = Binder.clearCallingIdentity(); 9335 try { 9336 synchronized (this) { 9337 ContentProviderConnection conn; 9338 try { 9339 conn = (ContentProviderConnection)connection; 9340 } catch (ClassCastException e) { 9341 String msg ="removeContentProvider: " + connection 9342 + " not a ContentProviderConnection"; 9343 Slog.w(TAG, msg); 9344 throw new IllegalArgumentException(msg); 9345 } 9346 if (conn == null) { 9347 throw new NullPointerException("connection is null"); 9348 } 9349 if (decProviderCountLocked(conn, null, null, stable)) { 9350 updateOomAdjLocked(); 9351 } 9352 } 9353 } finally { 9354 Binder.restoreCallingIdentity(ident); 9355 } 9356 } 9357 9358 public void removeContentProviderExternal(String name, IBinder token) { 9359 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 9360 "Do not have permission in call removeContentProviderExternal()"); 9361 removeContentProviderExternalUnchecked(name, token, UserHandle.getCallingUserId()); 9362 } 9363 9364 private void removeContentProviderExternalUnchecked(String name, IBinder token, int userId) { 9365 synchronized (this) { 9366 ContentProviderRecord cpr = mProviderMap.getProviderByName(name, userId); 9367 if(cpr == null) { 9368 //remove from mProvidersByClass 9369 if(localLOGV) Slog.v(TAG, name+" content provider not found in providers list"); 9370 return; 9371 } 9372 9373 //update content provider record entry info 9374 ComponentName comp = new ComponentName(cpr.info.packageName, cpr.info.name); 9375 ContentProviderRecord localCpr = mProviderMap.getProviderByClass(comp, userId); 9376 if (localCpr.hasExternalProcessHandles()) { 9377 if (localCpr.removeExternalProcessHandleLocked(token)) { 9378 updateOomAdjLocked(); 9379 } else { 9380 Slog.e(TAG, "Attmpt to remove content provider " + localCpr 9381 + " with no external reference for token: " 9382 + token + "."); 9383 } 9384 } else { 9385 Slog.e(TAG, "Attmpt to remove content provider: " + localCpr 9386 + " with no external references."); 9387 } 9388 } 9389 } 9390 9391 public final void publishContentProviders(IApplicationThread caller, 9392 List<ContentProviderHolder> providers) { 9393 if (providers == null) { 9394 return; 9395 } 9396 9397 enforceNotIsolatedCaller("publishContentProviders"); 9398 synchronized (this) { 9399 final ProcessRecord r = getRecordForAppLocked(caller); 9400 if (DEBUG_MU) 9401 Slog.v(TAG_MU, "ProcessRecord uid = " + r.uid); 9402 if (r == null) { 9403 throw new SecurityException( 9404 "Unable to find app for caller " + caller 9405 + " (pid=" + Binder.getCallingPid() 9406 + ") when publishing content providers"); 9407 } 9408 9409 final long origId = Binder.clearCallingIdentity(); 9410 9411 final int N = providers.size(); 9412 for (int i=0; i<N; i++) { 9413 ContentProviderHolder src = providers.get(i); 9414 if (src == null || src.info == null || src.provider == null) { 9415 continue; 9416 } 9417 ContentProviderRecord dst = r.pubProviders.get(src.info.name); 9418 if (DEBUG_MU) 9419 Slog.v(TAG_MU, "ContentProviderRecord uid = " + dst.uid); 9420 if (dst != null) { 9421 ComponentName comp = new ComponentName(dst.info.packageName, dst.info.name); 9422 mProviderMap.putProviderByClass(comp, dst); 9423 String names[] = dst.info.authority.split(";"); 9424 for (int j = 0; j < names.length; j++) { 9425 mProviderMap.putProviderByName(names[j], dst); 9426 } 9427 9428 int NL = mLaunchingProviders.size(); 9429 int j; 9430 for (j=0; j<NL; j++) { 9431 if (mLaunchingProviders.get(j) == dst) { 9432 mLaunchingProviders.remove(j); 9433 j--; 9434 NL--; 9435 } 9436 } 9437 synchronized (dst) { 9438 dst.provider = src.provider; 9439 dst.proc = r; 9440 dst.notifyAll(); 9441 } 9442 updateOomAdjLocked(r); 9443 } 9444 } 9445 9446 Binder.restoreCallingIdentity(origId); 9447 } 9448 } 9449 9450 public boolean refContentProvider(IBinder connection, int stable, int unstable) { 9451 ContentProviderConnection conn; 9452 try { 9453 conn = (ContentProviderConnection)connection; 9454 } catch (ClassCastException e) { 9455 String msg ="refContentProvider: " + connection 9456 + " not a ContentProviderConnection"; 9457 Slog.w(TAG, msg); 9458 throw new IllegalArgumentException(msg); 9459 } 9460 if (conn == null) { 9461 throw new NullPointerException("connection is null"); 9462 } 9463 9464 synchronized (this) { 9465 if (stable > 0) { 9466 conn.numStableIncs += stable; 9467 } 9468 stable = conn.stableCount + stable; 9469 if (stable < 0) { 9470 throw new IllegalStateException("stableCount < 0: " + stable); 9471 } 9472 9473 if (unstable > 0) { 9474 conn.numUnstableIncs += unstable; 9475 } 9476 unstable = conn.unstableCount + unstable; 9477 if (unstable < 0) { 9478 throw new IllegalStateException("unstableCount < 0: " + unstable); 9479 } 9480 9481 if ((stable+unstable) <= 0) { 9482 throw new IllegalStateException("ref counts can't go to zero here: stable=" 9483 + stable + " unstable=" + unstable); 9484 } 9485 conn.stableCount = stable; 9486 conn.unstableCount = unstable; 9487 return !conn.dead; 9488 } 9489 } 9490 9491 public void unstableProviderDied(IBinder connection) { 9492 ContentProviderConnection conn; 9493 try { 9494 conn = (ContentProviderConnection)connection; 9495 } catch (ClassCastException e) { 9496 String msg ="refContentProvider: " + connection 9497 + " not a ContentProviderConnection"; 9498 Slog.w(TAG, msg); 9499 throw new IllegalArgumentException(msg); 9500 } 9501 if (conn == null) { 9502 throw new NullPointerException("connection is null"); 9503 } 9504 9505 // Safely retrieve the content provider associated with the connection. 9506 IContentProvider provider; 9507 synchronized (this) { 9508 provider = conn.provider.provider; 9509 } 9510 9511 if (provider == null) { 9512 // Um, yeah, we're way ahead of you. 9513 return; 9514 } 9515 9516 // Make sure the caller is being honest with us. 9517 if (provider.asBinder().pingBinder()) { 9518 // Er, no, still looks good to us. 9519 synchronized (this) { 9520 Slog.w(TAG, "unstableProviderDied: caller " + Binder.getCallingUid() 9521 + " says " + conn + " died, but we don't agree"); 9522 return; 9523 } 9524 } 9525 9526 // Well look at that! It's dead! 9527 synchronized (this) { 9528 if (conn.provider.provider != provider) { 9529 // But something changed... good enough. 9530 return; 9531 } 9532 9533 ProcessRecord proc = conn.provider.proc; 9534 if (proc == null || proc.thread == null) { 9535 // Seems like the process is already cleaned up. 9536 return; 9537 } 9538 9539 // As far as we're concerned, this is just like receiving a 9540 // death notification... just a bit prematurely. 9541 Slog.i(TAG, "Process " + proc.processName + " (pid " + proc.pid 9542 + ") early provider death"); 9543 final long ident = Binder.clearCallingIdentity(); 9544 try { 9545 appDiedLocked(proc); 9546 } finally { 9547 Binder.restoreCallingIdentity(ident); 9548 } 9549 } 9550 } 9551 9552 @Override 9553 public void appNotRespondingViaProvider(IBinder connection) { 9554 enforceCallingPermission( 9555 android.Manifest.permission.REMOVE_TASKS, "appNotRespondingViaProvider()"); 9556 9557 final ContentProviderConnection conn = (ContentProviderConnection) connection; 9558 if (conn == null) { 9559 Slog.w(TAG, "ContentProviderConnection is null"); 9560 return; 9561 } 9562 9563 final ProcessRecord host = conn.provider.proc; 9564 if (host == null) { 9565 Slog.w(TAG, "Failed to find hosting ProcessRecord"); 9566 return; 9567 } 9568 9569 final long token = Binder.clearCallingIdentity(); 9570 try { 9571 appNotResponding(host, null, null, false, "ContentProvider not responding"); 9572 } finally { 9573 Binder.restoreCallingIdentity(token); 9574 } 9575 } 9576 9577 public final void installSystemProviders() { 9578 List<ProviderInfo> providers; 9579 synchronized (this) { 9580 ProcessRecord app = mProcessNames.get("system", Process.SYSTEM_UID); 9581 providers = generateApplicationProvidersLocked(app); 9582 if (providers != null) { 9583 for (int i=providers.size()-1; i>=0; i--) { 9584 ProviderInfo pi = (ProviderInfo)providers.get(i); 9585 if ((pi.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) == 0) { 9586 Slog.w(TAG, "Not installing system proc provider " + pi.name 9587 + ": not system .apk"); 9588 providers.remove(i); 9589 } 9590 } 9591 } 9592 } 9593 if (providers != null) { 9594 mSystemThread.installSystemProviders(providers); 9595 } 9596 9597 mCoreSettingsObserver = new CoreSettingsObserver(this); 9598 9599 //mUsageStatsService.monitorPackages(); 9600 } 9601 9602 /** 9603 * Allows apps to retrieve the MIME type of a URI. 9604 * If an app is in the same user as the ContentProvider, or if it is allowed to interact across 9605 * users, then it does not need permission to access the ContentProvider. 9606 * Either, it needs cross-user uri grants. 9607 * 9608 * CTS tests for this functionality can be run with "runtest cts-appsecurity". 9609 * 9610 * Test cases are at cts/tests/appsecurity-tests/test-apps/UsePermissionDiffCert/ 9611 * src/com/android/cts/usespermissiondiffcertapp/AccessPermissionWithDiffSigTest.java 9612 */ 9613 public String getProviderMimeType(Uri uri, int userId) { 9614 enforceNotIsolatedCaller("getProviderMimeType"); 9615 final String name = uri.getAuthority(); 9616 int callingUid = Binder.getCallingUid(); 9617 int callingPid = Binder.getCallingPid(); 9618 long ident = 0; 9619 boolean clearedIdentity = false; 9620 userId = unsafeConvertIncomingUser(userId); 9621 if (UserHandle.getUserId(callingUid) != userId) { 9622 if (checkComponentPermission(INTERACT_ACROSS_USERS, callingPid, 9623 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED 9624 || checkComponentPermission(INTERACT_ACROSS_USERS_FULL, callingPid, 9625 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED) { 9626 clearedIdentity = true; 9627 ident = Binder.clearCallingIdentity(); 9628 } 9629 } 9630 ContentProviderHolder holder = null; 9631 try { 9632 holder = getContentProviderExternalUnchecked(name, null, userId); 9633 if (holder != null) { 9634 return holder.provider.getType(uri); 9635 } 9636 } catch (RemoteException e) { 9637 Log.w(TAG, "Content provider dead retrieving " + uri, e); 9638 return null; 9639 } finally { 9640 // We need to clear the identity to call removeContentProviderExternalUnchecked 9641 if (!clearedIdentity) { 9642 ident = Binder.clearCallingIdentity(); 9643 } 9644 try { 9645 if (holder != null) { 9646 removeContentProviderExternalUnchecked(name, null, userId); 9647 } 9648 } finally { 9649 Binder.restoreCallingIdentity(ident); 9650 } 9651 } 9652 9653 return null; 9654 } 9655 9656 // ========================================================= 9657 // GLOBAL MANAGEMENT 9658 // ========================================================= 9659 9660 final ProcessRecord newProcessRecordLocked(ApplicationInfo info, String customProcess, 9661 boolean isolated, int isolatedUid) { 9662 String proc = customProcess != null ? customProcess : info.processName; 9663 BatteryStatsImpl.Uid.Proc ps = null; 9664 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 9665 int uid = info.uid; 9666 if (isolated) { 9667 if (isolatedUid == 0) { 9668 int userId = UserHandle.getUserId(uid); 9669 int stepsLeft = Process.LAST_ISOLATED_UID - Process.FIRST_ISOLATED_UID + 1; 9670 while (true) { 9671 if (mNextIsolatedProcessUid < Process.FIRST_ISOLATED_UID 9672 || mNextIsolatedProcessUid > Process.LAST_ISOLATED_UID) { 9673 mNextIsolatedProcessUid = Process.FIRST_ISOLATED_UID; 9674 } 9675 uid = UserHandle.getUid(userId, mNextIsolatedProcessUid); 9676 mNextIsolatedProcessUid++; 9677 if (mIsolatedProcesses.indexOfKey(uid) < 0) { 9678 // No process for this uid, use it. 9679 break; 9680 } 9681 stepsLeft--; 9682 if (stepsLeft <= 0) { 9683 return null; 9684 } 9685 } 9686 } else { 9687 // Special case for startIsolatedProcess (internal only), where 9688 // the uid of the isolated process is specified by the caller. 9689 uid = isolatedUid; 9690 } 9691 } 9692 return new ProcessRecord(stats, info, proc, uid); 9693 } 9694 9695 final ProcessRecord addAppLocked(ApplicationInfo info, boolean isolated, 9696 String abiOverride) { 9697 ProcessRecord app; 9698 if (!isolated) { 9699 app = getProcessRecordLocked(info.processName, info.uid, true); 9700 } else { 9701 app = null; 9702 } 9703 9704 if (app == null) { 9705 app = newProcessRecordLocked(info, null, isolated, 0); 9706 mProcessNames.put(info.processName, app.uid, app); 9707 if (isolated) { 9708 mIsolatedProcesses.put(app.uid, app); 9709 } 9710 updateLruProcessLocked(app, false, null); 9711 updateOomAdjLocked(); 9712 } 9713 9714 // This package really, really can not be stopped. 9715 try { 9716 AppGlobals.getPackageManager().setPackageStoppedState( 9717 info.packageName, false, UserHandle.getUserId(app.uid)); 9718 } catch (RemoteException e) { 9719 } catch (IllegalArgumentException e) { 9720 Slog.w(TAG, "Failed trying to unstop package " 9721 + info.packageName + ": " + e); 9722 } 9723 9724 if ((info.flags&(ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) 9725 == (ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) { 9726 app.persistent = true; 9727 app.maxAdj = ProcessList.PERSISTENT_PROC_ADJ; 9728 } 9729 if (app.thread == null && mPersistentStartingProcesses.indexOf(app) < 0) { 9730 mPersistentStartingProcesses.add(app); 9731 startProcessLocked(app, "added application", app.processName, abiOverride, 9732 null /* entryPoint */, null /* entryPointArgs */); 9733 } 9734 9735 return app; 9736 } 9737 9738 public void unhandledBack() { 9739 enforceCallingPermission(android.Manifest.permission.FORCE_BACK, 9740 "unhandledBack()"); 9741 9742 synchronized(this) { 9743 final long origId = Binder.clearCallingIdentity(); 9744 try { 9745 getFocusedStack().unhandledBackLocked(); 9746 } finally { 9747 Binder.restoreCallingIdentity(origId); 9748 } 9749 } 9750 } 9751 9752 public ParcelFileDescriptor openContentUri(Uri uri) throws RemoteException { 9753 enforceNotIsolatedCaller("openContentUri"); 9754 final int userId = UserHandle.getCallingUserId(); 9755 String name = uri.getAuthority(); 9756 ContentProviderHolder cph = getContentProviderExternalUnchecked(name, null, userId); 9757 ParcelFileDescriptor pfd = null; 9758 if (cph != null) { 9759 // We record the binder invoker's uid in thread-local storage before 9760 // going to the content provider to open the file. Later, in the code 9761 // that handles all permissions checks, we look for this uid and use 9762 // that rather than the Activity Manager's own uid. The effect is that 9763 // we do the check against the caller's permissions even though it looks 9764 // to the content provider like the Activity Manager itself is making 9765 // the request. 9766 sCallerIdentity.set(new Identity( 9767 Binder.getCallingPid(), Binder.getCallingUid())); 9768 try { 9769 pfd = cph.provider.openFile(null, uri, "r", null); 9770 } catch (FileNotFoundException e) { 9771 // do nothing; pfd will be returned null 9772 } finally { 9773 // Ensure that whatever happens, we clean up the identity state 9774 sCallerIdentity.remove(); 9775 } 9776 9777 // We've got the fd now, so we're done with the provider. 9778 removeContentProviderExternalUnchecked(name, null, userId); 9779 } else { 9780 Slog.d(TAG, "Failed to get provider for authority '" + name + "'"); 9781 } 9782 return pfd; 9783 } 9784 9785 // Actually is sleeping or shutting down or whatever else in the future 9786 // is an inactive state. 9787 public boolean isSleepingOrShuttingDown() { 9788 return mSleeping || mShuttingDown; 9789 } 9790 9791 public boolean isSleeping() { 9792 return mSleeping; 9793 } 9794 9795 void goingToSleep() { 9796 synchronized(this) { 9797 mWentToSleep = true; 9798 updateEventDispatchingLocked(); 9799 goToSleepIfNeededLocked(); 9800 } 9801 } 9802 9803 void finishRunningVoiceLocked() { 9804 if (mRunningVoice) { 9805 mRunningVoice = false; 9806 goToSleepIfNeededLocked(); 9807 } 9808 } 9809 9810 void goToSleepIfNeededLocked() { 9811 if (mWentToSleep && !mRunningVoice) { 9812 if (!mSleeping) { 9813 mSleeping = true; 9814 mStackSupervisor.goingToSleepLocked(); 9815 9816 // Initialize the wake times of all processes. 9817 checkExcessivePowerUsageLocked(false); 9818 mHandler.removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 9819 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 9820 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 9821 } 9822 } 9823 } 9824 9825 void notifyTaskPersisterLocked(TaskRecord task, boolean flush) { 9826 if (task != null && task.stack != null && task.stack.isHomeStack()) { 9827 // Never persist the home stack. 9828 return; 9829 } 9830 mTaskPersister.wakeup(task, flush); 9831 } 9832 9833 @Override 9834 public boolean shutdown(int timeout) { 9835 if (checkCallingPermission(android.Manifest.permission.SHUTDOWN) 9836 != PackageManager.PERMISSION_GRANTED) { 9837 throw new SecurityException("Requires permission " 9838 + android.Manifest.permission.SHUTDOWN); 9839 } 9840 9841 boolean timedout = false; 9842 9843 synchronized(this) { 9844 mShuttingDown = true; 9845 updateEventDispatchingLocked(); 9846 timedout = mStackSupervisor.shutdownLocked(timeout); 9847 } 9848 9849 mAppOpsService.shutdown(); 9850 if (mUsageStatsService != null) { 9851 mUsageStatsService.prepareShutdown(); 9852 } 9853 mBatteryStatsService.shutdown(); 9854 synchronized (this) { 9855 mProcessStats.shutdownLocked(); 9856 } 9857 notifyTaskPersisterLocked(null, true); 9858 9859 return timedout; 9860 } 9861 9862 public final void activitySlept(IBinder token) { 9863 if (localLOGV) Slog.v(TAG, "Activity slept: token=" + token); 9864 9865 final long origId = Binder.clearCallingIdentity(); 9866 9867 synchronized (this) { 9868 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9869 if (r != null) { 9870 mStackSupervisor.activitySleptLocked(r); 9871 } 9872 } 9873 9874 Binder.restoreCallingIdentity(origId); 9875 } 9876 9877 void logLockScreen(String msg) { 9878 if (DEBUG_LOCKSCREEN) Slog.d(TAG, Debug.getCallers(2) + ":" + msg + 9879 " mLockScreenShown=" + mLockScreenShown + " mWentToSleep=" + 9880 mWentToSleep + " mSleeping=" + mSleeping); 9881 } 9882 9883 private void comeOutOfSleepIfNeededLocked() { 9884 if ((!mWentToSleep && !mLockScreenShown) || mRunningVoice) { 9885 if (mSleeping) { 9886 mSleeping = false; 9887 mStackSupervisor.comeOutOfSleepIfNeededLocked(); 9888 } 9889 } 9890 } 9891 9892 void wakingUp() { 9893 synchronized(this) { 9894 mWentToSleep = false; 9895 updateEventDispatchingLocked(); 9896 comeOutOfSleepIfNeededLocked(); 9897 } 9898 } 9899 9900 void startRunningVoiceLocked() { 9901 if (!mRunningVoice) { 9902 mRunningVoice = true; 9903 comeOutOfSleepIfNeededLocked(); 9904 } 9905 } 9906 9907 private void updateEventDispatchingLocked() { 9908 mWindowManager.setEventDispatching(mBooted && !mWentToSleep && !mShuttingDown); 9909 } 9910 9911 public void setLockScreenShown(boolean shown) { 9912 if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER) 9913 != PackageManager.PERMISSION_GRANTED) { 9914 throw new SecurityException("Requires permission " 9915 + android.Manifest.permission.DEVICE_POWER); 9916 } 9917 9918 synchronized(this) { 9919 long ident = Binder.clearCallingIdentity(); 9920 try { 9921 if (DEBUG_LOCKSCREEN) logLockScreen(" shown=" + shown); 9922 mLockScreenShown = shown; 9923 comeOutOfSleepIfNeededLocked(); 9924 } finally { 9925 Binder.restoreCallingIdentity(ident); 9926 } 9927 } 9928 } 9929 9930 @Override 9931 public void stopAppSwitches() { 9932 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 9933 != PackageManager.PERMISSION_GRANTED) { 9934 throw new SecurityException("Requires permission " 9935 + android.Manifest.permission.STOP_APP_SWITCHES); 9936 } 9937 9938 synchronized(this) { 9939 mAppSwitchesAllowedTime = SystemClock.uptimeMillis() 9940 + APP_SWITCH_DELAY_TIME; 9941 mDidAppSwitch = false; 9942 mHandler.removeMessages(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 9943 Message msg = mHandler.obtainMessage(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 9944 mHandler.sendMessageDelayed(msg, APP_SWITCH_DELAY_TIME); 9945 } 9946 } 9947 9948 public void resumeAppSwitches() { 9949 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 9950 != PackageManager.PERMISSION_GRANTED) { 9951 throw new SecurityException("Requires permission " 9952 + android.Manifest.permission.STOP_APP_SWITCHES); 9953 } 9954 9955 synchronized(this) { 9956 // Note that we don't execute any pending app switches... we will 9957 // let those wait until either the timeout, or the next start 9958 // activity request. 9959 mAppSwitchesAllowedTime = 0; 9960 } 9961 } 9962 9963 boolean checkAppSwitchAllowedLocked(int callingPid, int callingUid, 9964 String name) { 9965 if (mAppSwitchesAllowedTime < SystemClock.uptimeMillis()) { 9966 return true; 9967 } 9968 9969 final int perm = checkComponentPermission( 9970 android.Manifest.permission.STOP_APP_SWITCHES, callingPid, 9971 callingUid, -1, true); 9972 if (perm == PackageManager.PERMISSION_GRANTED) { 9973 return true; 9974 } 9975 9976 Slog.w(TAG, name + " request from " + callingUid + " stopped"); 9977 return false; 9978 } 9979 9980 public void setDebugApp(String packageName, boolean waitForDebugger, 9981 boolean persistent) { 9982 enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP, 9983 "setDebugApp()"); 9984 9985 long ident = Binder.clearCallingIdentity(); 9986 try { 9987 // Note that this is not really thread safe if there are multiple 9988 // callers into it at the same time, but that's not a situation we 9989 // care about. 9990 if (persistent) { 9991 final ContentResolver resolver = mContext.getContentResolver(); 9992 Settings.Global.putString( 9993 resolver, Settings.Global.DEBUG_APP, 9994 packageName); 9995 Settings.Global.putInt( 9996 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 9997 waitForDebugger ? 1 : 0); 9998 } 9999 10000 synchronized (this) { 10001 if (!persistent) { 10002 mOrigDebugApp = mDebugApp; 10003 mOrigWaitForDebugger = mWaitForDebugger; 10004 } 10005 mDebugApp = packageName; 10006 mWaitForDebugger = waitForDebugger; 10007 mDebugTransient = !persistent; 10008 if (packageName != null) { 10009 forceStopPackageLocked(packageName, -1, false, false, true, true, 10010 false, UserHandle.USER_ALL, "set debug app"); 10011 } 10012 } 10013 } finally { 10014 Binder.restoreCallingIdentity(ident); 10015 } 10016 } 10017 10018 void setOpenGlTraceApp(ApplicationInfo app, String processName) { 10019 synchronized (this) { 10020 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 10021 if (!isDebuggable) { 10022 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 10023 throw new SecurityException("Process not debuggable: " + app.packageName); 10024 } 10025 } 10026 10027 mOpenGlTraceApp = processName; 10028 } 10029 } 10030 10031 void setProfileApp(ApplicationInfo app, String processName, ProfilerInfo profilerInfo) { 10032 synchronized (this) { 10033 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 10034 if (!isDebuggable) { 10035 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 10036 throw new SecurityException("Process not debuggable: " + app.packageName); 10037 } 10038 } 10039 mProfileApp = processName; 10040 mProfileFile = profilerInfo.profileFile; 10041 if (mProfileFd != null) { 10042 try { 10043 mProfileFd.close(); 10044 } catch (IOException e) { 10045 } 10046 mProfileFd = null; 10047 } 10048 mProfileFd = profilerInfo.profileFd; 10049 mSamplingInterval = profilerInfo.samplingInterval; 10050 mAutoStopProfiler = profilerInfo.autoStopProfiler; 10051 mProfileType = 0; 10052 } 10053 } 10054 10055 @Override 10056 public void setAlwaysFinish(boolean enabled) { 10057 enforceCallingPermission(android.Manifest.permission.SET_ALWAYS_FINISH, 10058 "setAlwaysFinish()"); 10059 10060 Settings.Global.putInt( 10061 mContext.getContentResolver(), 10062 Settings.Global.ALWAYS_FINISH_ACTIVITIES, enabled ? 1 : 0); 10063 10064 synchronized (this) { 10065 mAlwaysFinishActivities = enabled; 10066 } 10067 } 10068 10069 @Override 10070 public void setActivityController(IActivityController controller) { 10071 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 10072 "setActivityController()"); 10073 synchronized (this) { 10074 mController = controller; 10075 Watchdog.getInstance().setActivityController(controller); 10076 } 10077 } 10078 10079 @Override 10080 public void setUserIsMonkey(boolean userIsMonkey) { 10081 synchronized (this) { 10082 synchronized (mPidsSelfLocked) { 10083 final int callingPid = Binder.getCallingPid(); 10084 ProcessRecord precessRecord = mPidsSelfLocked.get(callingPid); 10085 if (precessRecord == null) { 10086 throw new SecurityException("Unknown process: " + callingPid); 10087 } 10088 if (precessRecord.instrumentationUiAutomationConnection == null) { 10089 throw new SecurityException("Only an instrumentation process " 10090 + "with a UiAutomation can call setUserIsMonkey"); 10091 } 10092 } 10093 mUserIsMonkey = userIsMonkey; 10094 } 10095 } 10096 10097 @Override 10098 public boolean isUserAMonkey() { 10099 synchronized (this) { 10100 // If there is a controller also implies the user is a monkey. 10101 return (mUserIsMonkey || mController != null); 10102 } 10103 } 10104 10105 public void requestBugReport() { 10106 enforceCallingPermission(android.Manifest.permission.DUMP, "requestBugReport"); 10107 SystemProperties.set("ctl.start", "bugreport"); 10108 } 10109 10110 public static long getInputDispatchingTimeoutLocked(ActivityRecord r) { 10111 return r != null ? getInputDispatchingTimeoutLocked(r.app) : KEY_DISPATCHING_TIMEOUT; 10112 } 10113 10114 public static long getInputDispatchingTimeoutLocked(ProcessRecord r) { 10115 if (r != null && (r.instrumentationClass != null || r.usingWrapper)) { 10116 return INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT; 10117 } 10118 return KEY_DISPATCHING_TIMEOUT; 10119 } 10120 10121 @Override 10122 public long inputDispatchingTimedOut(int pid, final boolean aboveSystem, String reason) { 10123 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 10124 != PackageManager.PERMISSION_GRANTED) { 10125 throw new SecurityException("Requires permission " 10126 + android.Manifest.permission.FILTER_EVENTS); 10127 } 10128 ProcessRecord proc; 10129 long timeout; 10130 synchronized (this) { 10131 synchronized (mPidsSelfLocked) { 10132 proc = mPidsSelfLocked.get(pid); 10133 } 10134 timeout = getInputDispatchingTimeoutLocked(proc); 10135 } 10136 10137 if (!inputDispatchingTimedOut(proc, null, null, aboveSystem, reason)) { 10138 return -1; 10139 } 10140 10141 return timeout; 10142 } 10143 10144 /** 10145 * Handle input dispatching timeouts. 10146 * Returns whether input dispatching should be aborted or not. 10147 */ 10148 public boolean inputDispatchingTimedOut(final ProcessRecord proc, 10149 final ActivityRecord activity, final ActivityRecord parent, 10150 final boolean aboveSystem, String reason) { 10151 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 10152 != PackageManager.PERMISSION_GRANTED) { 10153 throw new SecurityException("Requires permission " 10154 + android.Manifest.permission.FILTER_EVENTS); 10155 } 10156 10157 final String annotation; 10158 if (reason == null) { 10159 annotation = "Input dispatching timed out"; 10160 } else { 10161 annotation = "Input dispatching timed out (" + reason + ")"; 10162 } 10163 10164 if (proc != null) { 10165 synchronized (this) { 10166 if (proc.debugging) { 10167 return false; 10168 } 10169 10170 if (mDidDexOpt) { 10171 // Give more time since we were dexopting. 10172 mDidDexOpt = false; 10173 return false; 10174 } 10175 10176 if (proc.instrumentationClass != null) { 10177 Bundle info = new Bundle(); 10178 info.putString("shortMsg", "keyDispatchingTimedOut"); 10179 info.putString("longMsg", annotation); 10180 finishInstrumentationLocked(proc, Activity.RESULT_CANCELED, info); 10181 return true; 10182 } 10183 } 10184 mHandler.post(new Runnable() { 10185 @Override 10186 public void run() { 10187 appNotResponding(proc, activity, parent, aboveSystem, annotation); 10188 } 10189 }); 10190 } 10191 10192 return true; 10193 } 10194 10195 public Bundle getAssistContextExtras(int requestType) { 10196 enforceCallingPermission(android.Manifest.permission.GET_TOP_ACTIVITY_INFO, 10197 "getAssistContextExtras()"); 10198 PendingAssistExtras pae; 10199 Bundle extras = new Bundle(); 10200 synchronized (this) { 10201 ActivityRecord activity = getFocusedStack().mResumedActivity; 10202 if (activity == null) { 10203 Slog.w(TAG, "getAssistContextExtras failed: no resumed activity"); 10204 return null; 10205 } 10206 extras.putString(Intent.EXTRA_ASSIST_PACKAGE, activity.packageName); 10207 if (activity.app == null || activity.app.thread == null) { 10208 Slog.w(TAG, "getAssistContextExtras failed: no process for " + activity); 10209 return extras; 10210 } 10211 if (activity.app.pid == Binder.getCallingPid()) { 10212 Slog.w(TAG, "getAssistContextExtras failed: request process same as " + activity); 10213 return extras; 10214 } 10215 pae = new PendingAssistExtras(activity); 10216 try { 10217 activity.app.thread.requestAssistContextExtras(activity.appToken, pae, 10218 requestType); 10219 mPendingAssistExtras.add(pae); 10220 mHandler.postDelayed(pae, PENDING_ASSIST_EXTRAS_TIMEOUT); 10221 } catch (RemoteException e) { 10222 Slog.w(TAG, "getAssistContextExtras failed: crash calling " + activity); 10223 return extras; 10224 } 10225 } 10226 synchronized (pae) { 10227 while (!pae.haveResult) { 10228 try { 10229 pae.wait(); 10230 } catch (InterruptedException e) { 10231 } 10232 } 10233 if (pae.result != null) { 10234 extras.putBundle(Intent.EXTRA_ASSIST_CONTEXT, pae.result); 10235 } 10236 } 10237 synchronized (this) { 10238 mPendingAssistExtras.remove(pae); 10239 mHandler.removeCallbacks(pae); 10240 } 10241 return extras; 10242 } 10243 10244 public void reportAssistContextExtras(IBinder token, Bundle extras) { 10245 PendingAssistExtras pae = (PendingAssistExtras)token; 10246 synchronized (pae) { 10247 pae.result = extras; 10248 pae.haveResult = true; 10249 pae.notifyAll(); 10250 } 10251 } 10252 10253 public void registerProcessObserver(IProcessObserver observer) { 10254 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 10255 "registerProcessObserver()"); 10256 synchronized (this) { 10257 mProcessObservers.register(observer); 10258 } 10259 } 10260 10261 @Override 10262 public void unregisterProcessObserver(IProcessObserver observer) { 10263 synchronized (this) { 10264 mProcessObservers.unregister(observer); 10265 } 10266 } 10267 10268 @Override 10269 public boolean convertFromTranslucent(IBinder token) { 10270 final long origId = Binder.clearCallingIdentity(); 10271 try { 10272 synchronized (this) { 10273 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10274 if (r == null) { 10275 return false; 10276 } 10277 if (r.changeWindowTranslucency(true)) { 10278 mWindowManager.setAppFullscreen(token, true); 10279 r.task.stack.releaseBackgroundResources(); 10280 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 10281 return true; 10282 } 10283 return false; 10284 } 10285 } finally { 10286 Binder.restoreCallingIdentity(origId); 10287 } 10288 } 10289 10290 @Override 10291 public boolean convertToTranslucent(IBinder token, ActivityOptions options) { 10292 final long origId = Binder.clearCallingIdentity(); 10293 try { 10294 synchronized (this) { 10295 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10296 if (r == null) { 10297 return false; 10298 } 10299 int index = r.task.mActivities.lastIndexOf(r); 10300 if (index > 0) { 10301 ActivityRecord under = r.task.mActivities.get(index - 1); 10302 under.returningOptions = options; 10303 } 10304 if (r.changeWindowTranslucency(false)) { 10305 r.task.stack.convertToTranslucent(r); 10306 mWindowManager.setAppFullscreen(token, false); 10307 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 10308 return true; 10309 } else { 10310 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 10311 return false; 10312 } 10313 } 10314 } finally { 10315 Binder.restoreCallingIdentity(origId); 10316 } 10317 } 10318 10319 @Override 10320 public boolean requestVisibleBehind(IBinder token, boolean visible) { 10321 final long origId = Binder.clearCallingIdentity(); 10322 try { 10323 synchronized (this) { 10324 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10325 if (r != null) { 10326 return mStackSupervisor.requestVisibleBehindLocked(r, visible); 10327 } 10328 } 10329 return false; 10330 } finally { 10331 Binder.restoreCallingIdentity(origId); 10332 } 10333 } 10334 10335 @Override 10336 public boolean isBackgroundVisibleBehind(IBinder token) { 10337 final long origId = Binder.clearCallingIdentity(); 10338 try { 10339 synchronized (this) { 10340 final ActivityStack stack = ActivityRecord.getStackLocked(token); 10341 final boolean visible = stack == null ? false : stack.hasVisibleBehindActivity(); 10342 if (ActivityStackSupervisor.DEBUG_VISIBLE_BEHIND) Slog.d(TAG, 10343 "isBackgroundVisibleBehind: stack=" + stack + " visible=" + visible); 10344 return visible; 10345 } 10346 } finally { 10347 Binder.restoreCallingIdentity(origId); 10348 } 10349 } 10350 10351 @Override 10352 public ActivityOptions getActivityOptions(IBinder token) { 10353 final long origId = Binder.clearCallingIdentity(); 10354 try { 10355 synchronized (this) { 10356 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10357 if (r != null) { 10358 final ActivityOptions activityOptions = r.pendingOptions; 10359 r.pendingOptions = null; 10360 return activityOptions; 10361 } 10362 return null; 10363 } 10364 } finally { 10365 Binder.restoreCallingIdentity(origId); 10366 } 10367 } 10368 10369 @Override 10370 public void setImmersive(IBinder token, boolean immersive) { 10371 synchronized(this) { 10372 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10373 if (r == null) { 10374 throw new IllegalArgumentException(); 10375 } 10376 r.immersive = immersive; 10377 10378 // update associated state if we're frontmost 10379 if (r == mFocusedActivity) { 10380 if (DEBUG_IMMERSIVE) { 10381 Slog.d(TAG, "Frontmost changed immersion: "+ r); 10382 } 10383 applyUpdateLockStateLocked(r); 10384 } 10385 } 10386 } 10387 10388 @Override 10389 public boolean isImmersive(IBinder token) { 10390 synchronized (this) { 10391 ActivityRecord r = ActivityRecord.isInStackLocked(token); 10392 if (r == null) { 10393 throw new IllegalArgumentException(); 10394 } 10395 return r.immersive; 10396 } 10397 } 10398 10399 public boolean isTopActivityImmersive() { 10400 enforceNotIsolatedCaller("startActivity"); 10401 synchronized (this) { 10402 ActivityRecord r = getFocusedStack().topRunningActivityLocked(null); 10403 return (r != null) ? r.immersive : false; 10404 } 10405 } 10406 10407 @Override 10408 public boolean isTopOfTask(IBinder token) { 10409 synchronized (this) { 10410 ActivityRecord r = ActivityRecord.isInStackLocked(token); 10411 if (r == null) { 10412 throw new IllegalArgumentException(); 10413 } 10414 return r.task.getTopActivity() == r; 10415 } 10416 } 10417 10418 public final void enterSafeMode() { 10419 synchronized(this) { 10420 // It only makes sense to do this before the system is ready 10421 // and started launching other packages. 10422 if (!mSystemReady) { 10423 try { 10424 AppGlobals.getPackageManager().enterSafeMode(); 10425 } catch (RemoteException e) { 10426 } 10427 } 10428 10429 mSafeMode = true; 10430 } 10431 } 10432 10433 public final void showSafeModeOverlay() { 10434 View v = LayoutInflater.from(mContext).inflate( 10435 com.android.internal.R.layout.safe_mode, null); 10436 WindowManager.LayoutParams lp = new WindowManager.LayoutParams(); 10437 lp.type = WindowManager.LayoutParams.TYPE_SECURE_SYSTEM_OVERLAY; 10438 lp.width = WindowManager.LayoutParams.WRAP_CONTENT; 10439 lp.height = WindowManager.LayoutParams.WRAP_CONTENT; 10440 lp.gravity = Gravity.BOTTOM | Gravity.START; 10441 lp.format = v.getBackground().getOpacity(); 10442 lp.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE 10443 | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE; 10444 lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; 10445 ((WindowManager)mContext.getSystemService( 10446 Context.WINDOW_SERVICE)).addView(v, lp); 10447 } 10448 10449 public void noteWakeupAlarm(IIntentSender sender, int sourceUid, String sourcePkg) { 10450 if (!(sender instanceof PendingIntentRecord)) { 10451 return; 10452 } 10453 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 10454 synchronized (stats) { 10455 if (mBatteryStatsService.isOnBattery()) { 10456 mBatteryStatsService.enforceCallingPermission(); 10457 PendingIntentRecord rec = (PendingIntentRecord)sender; 10458 int MY_UID = Binder.getCallingUid(); 10459 int uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid; 10460 BatteryStatsImpl.Uid.Pkg pkg = 10461 stats.getPackageStatsLocked(sourceUid >= 0 ? sourceUid : uid, 10462 sourcePkg != null ? sourcePkg : rec.key.packageName); 10463 pkg.incWakeupsLocked(); 10464 } 10465 } 10466 } 10467 10468 public boolean killPids(int[] pids, String pReason, boolean secure) { 10469 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10470 throw new SecurityException("killPids only available to the system"); 10471 } 10472 String reason = (pReason == null) ? "Unknown" : pReason; 10473 // XXX Note: don't acquire main activity lock here, because the window 10474 // manager calls in with its locks held. 10475 10476 boolean killed = false; 10477 synchronized (mPidsSelfLocked) { 10478 int[] types = new int[pids.length]; 10479 int worstType = 0; 10480 for (int i=0; i<pids.length; i++) { 10481 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 10482 if (proc != null) { 10483 int type = proc.setAdj; 10484 types[i] = type; 10485 if (type > worstType) { 10486 worstType = type; 10487 } 10488 } 10489 } 10490 10491 // If the worst oom_adj is somewhere in the cached proc LRU range, 10492 // then constrain it so we will kill all cached procs. 10493 if (worstType < ProcessList.CACHED_APP_MAX_ADJ 10494 && worstType > ProcessList.CACHED_APP_MIN_ADJ) { 10495 worstType = ProcessList.CACHED_APP_MIN_ADJ; 10496 } 10497 10498 // If this is not a secure call, don't let it kill processes that 10499 // are important. 10500 if (!secure && worstType < ProcessList.SERVICE_ADJ) { 10501 worstType = ProcessList.SERVICE_ADJ; 10502 } 10503 10504 Slog.w(TAG, "Killing processes " + reason + " at adjustment " + worstType); 10505 for (int i=0; i<pids.length; i++) { 10506 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 10507 if (proc == null) { 10508 continue; 10509 } 10510 int adj = proc.setAdj; 10511 if (adj >= worstType && !proc.killedByAm) { 10512 proc.kill(reason, true); 10513 killed = true; 10514 } 10515 } 10516 } 10517 return killed; 10518 } 10519 10520 @Override 10521 public void killUid(int uid, String reason) { 10522 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10523 throw new SecurityException("killUid only available to the system"); 10524 } 10525 synchronized (this) { 10526 killPackageProcessesLocked(null, UserHandle.getAppId(uid), UserHandle.getUserId(uid), 10527 ProcessList.FOREGROUND_APP_ADJ-1, false, true, true, false, 10528 reason != null ? reason : "kill uid"); 10529 } 10530 } 10531 10532 @Override 10533 public boolean killProcessesBelowForeground(String reason) { 10534 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10535 throw new SecurityException("killProcessesBelowForeground() only available to system"); 10536 } 10537 10538 return killProcessesBelowAdj(ProcessList.FOREGROUND_APP_ADJ, reason); 10539 } 10540 10541 private boolean killProcessesBelowAdj(int belowAdj, String reason) { 10542 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10543 throw new SecurityException("killProcessesBelowAdj() only available to system"); 10544 } 10545 10546 boolean killed = false; 10547 synchronized (mPidsSelfLocked) { 10548 final int size = mPidsSelfLocked.size(); 10549 for (int i = 0; i < size; i++) { 10550 final int pid = mPidsSelfLocked.keyAt(i); 10551 final ProcessRecord proc = mPidsSelfLocked.valueAt(i); 10552 if (proc == null) continue; 10553 10554 final int adj = proc.setAdj; 10555 if (adj > belowAdj && !proc.killedByAm) { 10556 proc.kill(reason, true); 10557 killed = true; 10558 } 10559 } 10560 } 10561 return killed; 10562 } 10563 10564 @Override 10565 public void hang(final IBinder who, boolean allowRestart) { 10566 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 10567 != PackageManager.PERMISSION_GRANTED) { 10568 throw new SecurityException("Requires permission " 10569 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 10570 } 10571 10572 final IBinder.DeathRecipient death = new DeathRecipient() { 10573 @Override 10574 public void binderDied() { 10575 synchronized (this) { 10576 notifyAll(); 10577 } 10578 } 10579 }; 10580 10581 try { 10582 who.linkToDeath(death, 0); 10583 } catch (RemoteException e) { 10584 Slog.w(TAG, "hang: given caller IBinder is already dead."); 10585 return; 10586 } 10587 10588 synchronized (this) { 10589 Watchdog.getInstance().setAllowRestart(allowRestart); 10590 Slog.i(TAG, "Hanging system process at request of pid " + Binder.getCallingPid()); 10591 synchronized (death) { 10592 while (who.isBinderAlive()) { 10593 try { 10594 death.wait(); 10595 } catch (InterruptedException e) { 10596 } 10597 } 10598 } 10599 Watchdog.getInstance().setAllowRestart(true); 10600 } 10601 } 10602 10603 @Override 10604 public void restart() { 10605 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 10606 != PackageManager.PERMISSION_GRANTED) { 10607 throw new SecurityException("Requires permission " 10608 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 10609 } 10610 10611 Log.i(TAG, "Sending shutdown broadcast..."); 10612 10613 BroadcastReceiver br = new BroadcastReceiver() { 10614 @Override public void onReceive(Context context, Intent intent) { 10615 // Now the broadcast is done, finish up the low-level shutdown. 10616 Log.i(TAG, "Shutting down activity manager..."); 10617 shutdown(10000); 10618 Log.i(TAG, "Shutdown complete, restarting!"); 10619 Process.killProcess(Process.myPid()); 10620 System.exit(10); 10621 } 10622 }; 10623 10624 // First send the high-level shut down broadcast. 10625 Intent intent = new Intent(Intent.ACTION_SHUTDOWN); 10626 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 10627 intent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 10628 /* For now we are not doing a clean shutdown, because things seem to get unhappy. 10629 mContext.sendOrderedBroadcastAsUser(intent, 10630 UserHandle.ALL, null, br, mHandler, 0, null, null); 10631 */ 10632 br.onReceive(mContext, intent); 10633 } 10634 10635 private long getLowRamTimeSinceIdle(long now) { 10636 return mLowRamTimeSinceLastIdle + (mLowRamStartTime > 0 ? (now-mLowRamStartTime) : 0); 10637 } 10638 10639 @Override 10640 public void performIdleMaintenance() { 10641 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 10642 != PackageManager.PERMISSION_GRANTED) { 10643 throw new SecurityException("Requires permission " 10644 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 10645 } 10646 10647 synchronized (this) { 10648 final long now = SystemClock.uptimeMillis(); 10649 final long timeSinceLastIdle = now - mLastIdleTime; 10650 final long lowRamSinceLastIdle = getLowRamTimeSinceIdle(now); 10651 mLastIdleTime = now; 10652 mLowRamTimeSinceLastIdle = 0; 10653 if (mLowRamStartTime != 0) { 10654 mLowRamStartTime = now; 10655 } 10656 10657 StringBuilder sb = new StringBuilder(128); 10658 sb.append("Idle maintenance over "); 10659 TimeUtils.formatDuration(timeSinceLastIdle, sb); 10660 sb.append(" low RAM for "); 10661 TimeUtils.formatDuration(lowRamSinceLastIdle, sb); 10662 Slog.i(TAG, sb.toString()); 10663 10664 // If at least 1/3 of our time since the last idle period has been spent 10665 // with RAM low, then we want to kill processes. 10666 boolean doKilling = lowRamSinceLastIdle > (timeSinceLastIdle/3); 10667 10668 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 10669 ProcessRecord proc = mLruProcesses.get(i); 10670 if (proc.notCachedSinceIdle) { 10671 if (proc.setProcState > ActivityManager.PROCESS_STATE_TOP 10672 && proc.setProcState <= ActivityManager.PROCESS_STATE_SERVICE) { 10673 if (doKilling && proc.initialIdlePss != 0 10674 && proc.lastPss > ((proc.initialIdlePss*3)/2)) { 10675 proc.kill("idle maint (pss " + proc.lastPss 10676 + " from " + proc.initialIdlePss + ")", true); 10677 } 10678 } 10679 } else if (proc.setProcState < ActivityManager.PROCESS_STATE_HOME) { 10680 proc.notCachedSinceIdle = true; 10681 proc.initialIdlePss = 0; 10682 proc.nextPssTime = ProcessList.computeNextPssTime(proc.curProcState, true, 10683 isSleeping(), now); 10684 } 10685 } 10686 10687 mHandler.removeMessages(REQUEST_ALL_PSS_MSG); 10688 mHandler.sendEmptyMessageDelayed(REQUEST_ALL_PSS_MSG, 2*60*1000); 10689 } 10690 } 10691 10692 private void retrieveSettings() { 10693 final ContentResolver resolver = mContext.getContentResolver(); 10694 String debugApp = Settings.Global.getString( 10695 resolver, Settings.Global.DEBUG_APP); 10696 boolean waitForDebugger = Settings.Global.getInt( 10697 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 0) != 0; 10698 boolean alwaysFinishActivities = Settings.Global.getInt( 10699 resolver, Settings.Global.ALWAYS_FINISH_ACTIVITIES, 0) != 0; 10700 boolean forceRtl = Settings.Global.getInt( 10701 resolver, Settings.Global.DEVELOPMENT_FORCE_RTL, 0) != 0; 10702 // Transfer any global setting for forcing RTL layout, into a System Property 10703 SystemProperties.set(Settings.Global.DEVELOPMENT_FORCE_RTL, forceRtl ? "1":"0"); 10704 10705 Configuration configuration = new Configuration(); 10706 Settings.System.getConfiguration(resolver, configuration); 10707 if (forceRtl) { 10708 // This will take care of setting the correct layout direction flags 10709 configuration.setLayoutDirection(configuration.locale); 10710 } 10711 10712 synchronized (this) { 10713 mDebugApp = mOrigDebugApp = debugApp; 10714 mWaitForDebugger = mOrigWaitForDebugger = waitForDebugger; 10715 mAlwaysFinishActivities = alwaysFinishActivities; 10716 // This happens before any activities are started, so we can 10717 // change mConfiguration in-place. 10718 updateConfigurationLocked(configuration, null, false, true); 10719 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Initial config: " + mConfiguration); 10720 } 10721 } 10722 10723 /** Loads resources after the current configuration has been set. */ 10724 private void loadResourcesOnSystemReady() { 10725 final Resources res = mContext.getResources(); 10726 mHasRecents = res.getBoolean(com.android.internal.R.bool.config_hasRecents); 10727 mThumbnailWidth = res.getDimensionPixelSize(com.android.internal.R.dimen.thumbnail_width); 10728 mThumbnailHeight = res.getDimensionPixelSize(com.android.internal.R.dimen.thumbnail_height); 10729 } 10730 10731 public boolean testIsSystemReady() { 10732 // no need to synchronize(this) just to read & return the value 10733 return mSystemReady; 10734 } 10735 10736 private static File getCalledPreBootReceiversFile() { 10737 File dataDir = Environment.getDataDirectory(); 10738 File systemDir = new File(dataDir, "system"); 10739 File fname = new File(systemDir, CALLED_PRE_BOOTS_FILENAME); 10740 return fname; 10741 } 10742 10743 private static ArrayList<ComponentName> readLastDonePreBootReceivers() { 10744 ArrayList<ComponentName> lastDoneReceivers = new ArrayList<ComponentName>(); 10745 File file = getCalledPreBootReceiversFile(); 10746 FileInputStream fis = null; 10747 try { 10748 fis = new FileInputStream(file); 10749 DataInputStream dis = new DataInputStream(new BufferedInputStream(fis, 2048)); 10750 int fvers = dis.readInt(); 10751 if (fvers == LAST_PREBOOT_DELIVERED_FILE_VERSION) { 10752 String vers = dis.readUTF(); 10753 String codename = dis.readUTF(); 10754 String build = dis.readUTF(); 10755 if (android.os.Build.VERSION.RELEASE.equals(vers) 10756 && android.os.Build.VERSION.CODENAME.equals(codename) 10757 && android.os.Build.VERSION.INCREMENTAL.equals(build)) { 10758 int num = dis.readInt(); 10759 while (num > 0) { 10760 num--; 10761 String pkg = dis.readUTF(); 10762 String cls = dis.readUTF(); 10763 lastDoneReceivers.add(new ComponentName(pkg, cls)); 10764 } 10765 } 10766 } 10767 } catch (FileNotFoundException e) { 10768 } catch (IOException e) { 10769 Slog.w(TAG, "Failure reading last done pre-boot receivers", e); 10770 } finally { 10771 if (fis != null) { 10772 try { 10773 fis.close(); 10774 } catch (IOException e) { 10775 } 10776 } 10777 } 10778 return lastDoneReceivers; 10779 } 10780 10781 private static void writeLastDonePreBootReceivers(ArrayList<ComponentName> list) { 10782 File file = getCalledPreBootReceiversFile(); 10783 FileOutputStream fos = null; 10784 DataOutputStream dos = null; 10785 try { 10786 fos = new FileOutputStream(file); 10787 dos = new DataOutputStream(new BufferedOutputStream(fos, 2048)); 10788 dos.writeInt(LAST_PREBOOT_DELIVERED_FILE_VERSION); 10789 dos.writeUTF(android.os.Build.VERSION.RELEASE); 10790 dos.writeUTF(android.os.Build.VERSION.CODENAME); 10791 dos.writeUTF(android.os.Build.VERSION.INCREMENTAL); 10792 dos.writeInt(list.size()); 10793 for (int i=0; i<list.size(); i++) { 10794 dos.writeUTF(list.get(i).getPackageName()); 10795 dos.writeUTF(list.get(i).getClassName()); 10796 } 10797 } catch (IOException e) { 10798 Slog.w(TAG, "Failure writing last done pre-boot receivers", e); 10799 file.delete(); 10800 } finally { 10801 FileUtils.sync(fos); 10802 if (dos != null) { 10803 try { 10804 dos.close(); 10805 } catch (IOException e) { 10806 // TODO Auto-generated catch block 10807 e.printStackTrace(); 10808 } 10809 } 10810 } 10811 } 10812 10813 private boolean deliverPreBootCompleted(final Runnable onFinishCallback, 10814 ArrayList<ComponentName> doneReceivers, int userId) { 10815 boolean waitingUpdate = false; 10816 Intent intent = new Intent(Intent.ACTION_PRE_BOOT_COMPLETED); 10817 List<ResolveInfo> ris = null; 10818 try { 10819 ris = AppGlobals.getPackageManager().queryIntentReceivers( 10820 intent, null, 0, userId); 10821 } catch (RemoteException e) { 10822 } 10823 if (ris != null) { 10824 for (int i=ris.size()-1; i>=0; i--) { 10825 if ((ris.get(i).activityInfo.applicationInfo.flags 10826 &ApplicationInfo.FLAG_SYSTEM) == 0) { 10827 ris.remove(i); 10828 } 10829 } 10830 intent.addFlags(Intent.FLAG_RECEIVER_BOOT_UPGRADE); 10831 10832 // For User 0, load the version number. When delivering to a new user, deliver 10833 // to all receivers. 10834 if (userId == UserHandle.USER_OWNER) { 10835 ArrayList<ComponentName> lastDoneReceivers = readLastDonePreBootReceivers(); 10836 for (int i=0; i<ris.size(); i++) { 10837 ActivityInfo ai = ris.get(i).activityInfo; 10838 ComponentName comp = new ComponentName(ai.packageName, ai.name); 10839 if (lastDoneReceivers.contains(comp)) { 10840 // We already did the pre boot receiver for this app with the current 10841 // platform version, so don't do it again... 10842 ris.remove(i); 10843 i--; 10844 // ...however, do keep it as one that has been done, so we don't 10845 // forget about it when rewriting the file of last done receivers. 10846 doneReceivers.add(comp); 10847 } 10848 } 10849 } 10850 10851 // If primary user, send broadcast to all available users, else just to userId 10852 final int[] users = userId == UserHandle.USER_OWNER ? getUsersLocked() 10853 : new int[] { userId }; 10854 for (int i = 0; i < ris.size(); i++) { 10855 ActivityInfo ai = ris.get(i).activityInfo; 10856 ComponentName comp = new ComponentName(ai.packageName, ai.name); 10857 doneReceivers.add(comp); 10858 intent.setComponent(comp); 10859 for (int j=0; j<users.length; j++) { 10860 IIntentReceiver finisher = null; 10861 // On last receiver and user, set up a completion callback 10862 if (i == ris.size() - 1 && j == users.length - 1 && onFinishCallback != null) { 10863 finisher = new IIntentReceiver.Stub() { 10864 public void performReceive(Intent intent, int resultCode, 10865 String data, Bundle extras, boolean ordered, 10866 boolean sticky, int sendingUser) { 10867 // The raw IIntentReceiver interface is called 10868 // with the AM lock held, so redispatch to 10869 // execute our code without the lock. 10870 mHandler.post(onFinishCallback); 10871 } 10872 }; 10873 } 10874 Slog.i(TAG, "Sending system update to " + intent.getComponent() 10875 + " for user " + users[j]); 10876 broadcastIntentLocked(null, null, intent, null, finisher, 10877 0, null, null, null, AppOpsManager.OP_NONE, 10878 true, false, MY_PID, Process.SYSTEM_UID, 10879 users[j]); 10880 if (finisher != null) { 10881 waitingUpdate = true; 10882 } 10883 } 10884 } 10885 } 10886 10887 return waitingUpdate; 10888 } 10889 10890 public void systemReady(final Runnable goingCallback) { 10891 synchronized(this) { 10892 if (mSystemReady) { 10893 // If we're done calling all the receivers, run the next "boot phase" passed in 10894 // by the SystemServer 10895 if (goingCallback != null) { 10896 goingCallback.run(); 10897 } 10898 return; 10899 } 10900 10901 // Make sure we have the current profile info, since it is needed for 10902 // security checks. 10903 updateCurrentProfileIdsLocked(); 10904 10905 if (mRecentTasks == null) { 10906 mRecentTasks = mTaskPersister.restoreTasksLocked(); 10907 if (!mRecentTasks.isEmpty()) { 10908 mStackSupervisor.createStackForRestoredTaskHistory(mRecentTasks); 10909 } 10910 cleanupRecentTasksLocked(UserHandle.USER_ALL); 10911 mTaskPersister.startPersisting(); 10912 } 10913 10914 // Check to see if there are any update receivers to run. 10915 if (!mDidUpdate) { 10916 if (mWaitingUpdate) { 10917 return; 10918 } 10919 final ArrayList<ComponentName> doneReceivers = new ArrayList<ComponentName>(); 10920 mWaitingUpdate = deliverPreBootCompleted(new Runnable() { 10921 public void run() { 10922 synchronized (ActivityManagerService.this) { 10923 mDidUpdate = true; 10924 } 10925 writeLastDonePreBootReceivers(doneReceivers); 10926 showBootMessage(mContext.getText( 10927 R.string.android_upgrading_complete), 10928 false); 10929 systemReady(goingCallback); 10930 } 10931 }, doneReceivers, UserHandle.USER_OWNER); 10932 10933 if (mWaitingUpdate) { 10934 return; 10935 } 10936 mDidUpdate = true; 10937 } 10938 10939 mAppOpsService.systemReady(); 10940 mSystemReady = true; 10941 } 10942 10943 ArrayList<ProcessRecord> procsToKill = null; 10944 synchronized(mPidsSelfLocked) { 10945 for (int i=mPidsSelfLocked.size()-1; i>=0; i--) { 10946 ProcessRecord proc = mPidsSelfLocked.valueAt(i); 10947 if (!isAllowedWhileBooting(proc.info)){ 10948 if (procsToKill == null) { 10949 procsToKill = new ArrayList<ProcessRecord>(); 10950 } 10951 procsToKill.add(proc); 10952 } 10953 } 10954 } 10955 10956 synchronized(this) { 10957 if (procsToKill != null) { 10958 for (int i=procsToKill.size()-1; i>=0; i--) { 10959 ProcessRecord proc = procsToKill.get(i); 10960 Slog.i(TAG, "Removing system update proc: " + proc); 10961 removeProcessLocked(proc, true, false, "system update done"); 10962 } 10963 } 10964 10965 // Now that we have cleaned up any update processes, we 10966 // are ready to start launching real processes and know that 10967 // we won't trample on them any more. 10968 mProcessesReady = true; 10969 } 10970 10971 Slog.i(TAG, "System now ready"); 10972 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_AMS_READY, 10973 SystemClock.uptimeMillis()); 10974 10975 synchronized(this) { 10976 // Make sure we have no pre-ready processes sitting around. 10977 10978 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) { 10979 ResolveInfo ri = mContext.getPackageManager() 10980 .resolveActivity(new Intent(Intent.ACTION_FACTORY_TEST), 10981 STOCK_PM_FLAGS); 10982 CharSequence errorMsg = null; 10983 if (ri != null) { 10984 ActivityInfo ai = ri.activityInfo; 10985 ApplicationInfo app = ai.applicationInfo; 10986 if ((app.flags&ApplicationInfo.FLAG_SYSTEM) != 0) { 10987 mTopAction = Intent.ACTION_FACTORY_TEST; 10988 mTopData = null; 10989 mTopComponent = new ComponentName(app.packageName, 10990 ai.name); 10991 } else { 10992 errorMsg = mContext.getResources().getText( 10993 com.android.internal.R.string.factorytest_not_system); 10994 } 10995 } else { 10996 errorMsg = mContext.getResources().getText( 10997 com.android.internal.R.string.factorytest_no_action); 10998 } 10999 if (errorMsg != null) { 11000 mTopAction = null; 11001 mTopData = null; 11002 mTopComponent = null; 11003 Message msg = Message.obtain(); 11004 msg.what = SHOW_FACTORY_ERROR_MSG; 11005 msg.getData().putCharSequence("msg", errorMsg); 11006 mHandler.sendMessage(msg); 11007 } 11008 } 11009 } 11010 11011 retrieveSettings(); 11012 loadResourcesOnSystemReady(); 11013 11014 synchronized (this) { 11015 readGrantedUriPermissionsLocked(); 11016 } 11017 11018 if (goingCallback != null) goingCallback.run(); 11019 11020 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 11021 Integer.toString(mCurrentUserId), mCurrentUserId); 11022 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 11023 Integer.toString(mCurrentUserId), mCurrentUserId); 11024 mSystemServiceManager.startUser(mCurrentUserId); 11025 11026 synchronized (this) { 11027 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 11028 try { 11029 List apps = AppGlobals.getPackageManager(). 11030 getPersistentApplications(STOCK_PM_FLAGS); 11031 if (apps != null) { 11032 int N = apps.size(); 11033 int i; 11034 for (i=0; i<N; i++) { 11035 ApplicationInfo info 11036 = (ApplicationInfo)apps.get(i); 11037 if (info != null && 11038 !info.packageName.equals("android")) { 11039 addAppLocked(info, false, null /* ABI override */); 11040 } 11041 } 11042 } 11043 } catch (RemoteException ex) { 11044 // pm is in same process, this will never happen. 11045 } 11046 } 11047 11048 // Start up initial activity. 11049 mBooting = true; 11050 11051 try { 11052 if (AppGlobals.getPackageManager().hasSystemUidErrors()) { 11053 Message msg = Message.obtain(); 11054 msg.what = SHOW_UID_ERROR_MSG; 11055 mHandler.sendMessage(msg); 11056 } 11057 } catch (RemoteException e) { 11058 } 11059 11060 long ident = Binder.clearCallingIdentity(); 11061 try { 11062 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 11063 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 11064 | Intent.FLAG_RECEIVER_FOREGROUND); 11065 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 11066 broadcastIntentLocked(null, null, intent, 11067 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 11068 false, false, MY_PID, Process.SYSTEM_UID, mCurrentUserId); 11069 intent = new Intent(Intent.ACTION_USER_STARTING); 11070 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 11071 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 11072 broadcastIntentLocked(null, null, intent, 11073 null, new IIntentReceiver.Stub() { 11074 @Override 11075 public void performReceive(Intent intent, int resultCode, String data, 11076 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 11077 throws RemoteException { 11078 } 11079 }, 0, null, null, 11080 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 11081 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 11082 } catch (Throwable t) { 11083 Slog.wtf(TAG, "Failed sending first user broadcasts", t); 11084 } finally { 11085 Binder.restoreCallingIdentity(ident); 11086 } 11087 mStackSupervisor.resumeTopActivitiesLocked(); 11088 sendUserSwitchBroadcastsLocked(-1, mCurrentUserId); 11089 } 11090 } 11091 11092 private boolean makeAppCrashingLocked(ProcessRecord app, 11093 String shortMsg, String longMsg, String stackTrace) { 11094 app.crashing = true; 11095 app.crashingReport = generateProcessError(app, 11096 ActivityManager.ProcessErrorStateInfo.CRASHED, null, shortMsg, longMsg, stackTrace); 11097 startAppProblemLocked(app); 11098 app.stopFreezingAllLocked(); 11099 return handleAppCrashLocked(app, shortMsg, longMsg, stackTrace); 11100 } 11101 11102 private void makeAppNotRespondingLocked(ProcessRecord app, 11103 String activity, String shortMsg, String longMsg) { 11104 app.notResponding = true; 11105 app.notRespondingReport = generateProcessError(app, 11106 ActivityManager.ProcessErrorStateInfo.NOT_RESPONDING, 11107 activity, shortMsg, longMsg, null); 11108 startAppProblemLocked(app); 11109 app.stopFreezingAllLocked(); 11110 } 11111 11112 /** 11113 * Generate a process error record, suitable for attachment to a ProcessRecord. 11114 * 11115 * @param app The ProcessRecord in which the error occurred. 11116 * @param condition Crashing, Application Not Responding, etc. Values are defined in 11117 * ActivityManager.AppErrorStateInfo 11118 * @param activity The activity associated with the crash, if known. 11119 * @param shortMsg Short message describing the crash. 11120 * @param longMsg Long message describing the crash. 11121 * @param stackTrace Full crash stack trace, may be null. 11122 * 11123 * @return Returns a fully-formed AppErrorStateInfo record. 11124 */ 11125 private ActivityManager.ProcessErrorStateInfo generateProcessError(ProcessRecord app, 11126 int condition, String activity, String shortMsg, String longMsg, String stackTrace) { 11127 ActivityManager.ProcessErrorStateInfo report = new ActivityManager.ProcessErrorStateInfo(); 11128 11129 report.condition = condition; 11130 report.processName = app.processName; 11131 report.pid = app.pid; 11132 report.uid = app.info.uid; 11133 report.tag = activity; 11134 report.shortMsg = shortMsg; 11135 report.longMsg = longMsg; 11136 report.stackTrace = stackTrace; 11137 11138 return report; 11139 } 11140 11141 void killAppAtUsersRequest(ProcessRecord app, Dialog fromDialog) { 11142 synchronized (this) { 11143 app.crashing = false; 11144 app.crashingReport = null; 11145 app.notResponding = false; 11146 app.notRespondingReport = null; 11147 if (app.anrDialog == fromDialog) { 11148 app.anrDialog = null; 11149 } 11150 if (app.waitDialog == fromDialog) { 11151 app.waitDialog = null; 11152 } 11153 if (app.pid > 0 && app.pid != MY_PID) { 11154 handleAppCrashLocked(app, null, null, null); 11155 app.kill("user request after error", true); 11156 } 11157 } 11158 } 11159 11160 private boolean handleAppCrashLocked(ProcessRecord app, String shortMsg, String longMsg, 11161 String stackTrace) { 11162 long now = SystemClock.uptimeMillis(); 11163 11164 Long crashTime; 11165 if (!app.isolated) { 11166 crashTime = mProcessCrashTimes.get(app.info.processName, app.uid); 11167 } else { 11168 crashTime = null; 11169 } 11170 if (crashTime != null && now < crashTime+ProcessList.MIN_CRASH_INTERVAL) { 11171 // This process loses! 11172 Slog.w(TAG, "Process " + app.info.processName 11173 + " has crashed too many times: killing!"); 11174 EventLog.writeEvent(EventLogTags.AM_PROCESS_CRASHED_TOO_MUCH, 11175 app.userId, app.info.processName, app.uid); 11176 mStackSupervisor.handleAppCrashLocked(app); 11177 if (!app.persistent) { 11178 // We don't want to start this process again until the user 11179 // explicitly does so... but for persistent process, we really 11180 // need to keep it running. If a persistent process is actually 11181 // repeatedly crashing, then badness for everyone. 11182 EventLog.writeEvent(EventLogTags.AM_PROC_BAD, app.userId, app.uid, 11183 app.info.processName); 11184 if (!app.isolated) { 11185 // XXX We don't have a way to mark isolated processes 11186 // as bad, since they don't have a peristent identity. 11187 mBadProcesses.put(app.info.processName, app.uid, 11188 new BadProcessInfo(now, shortMsg, longMsg, stackTrace)); 11189 mProcessCrashTimes.remove(app.info.processName, app.uid); 11190 } 11191 app.bad = true; 11192 app.removed = true; 11193 // Don't let services in this process be restarted and potentially 11194 // annoy the user repeatedly. Unless it is persistent, since those 11195 // processes run critical code. 11196 removeProcessLocked(app, false, false, "crash"); 11197 mStackSupervisor.resumeTopActivitiesLocked(); 11198 return false; 11199 } 11200 mStackSupervisor.resumeTopActivitiesLocked(); 11201 } else { 11202 mStackSupervisor.finishTopRunningActivityLocked(app); 11203 } 11204 11205 // Bump up the crash count of any services currently running in the proc. 11206 for (int i=app.services.size()-1; i>=0; i--) { 11207 // Any services running in the application need to be placed 11208 // back in the pending list. 11209 ServiceRecord sr = app.services.valueAt(i); 11210 sr.crashCount++; 11211 } 11212 11213 // If the crashing process is what we consider to be the "home process" and it has been 11214 // replaced by a third-party app, clear the package preferred activities from packages 11215 // with a home activity running in the process to prevent a repeatedly crashing app 11216 // from blocking the user to manually clear the list. 11217 final ArrayList<ActivityRecord> activities = app.activities; 11218 if (app == mHomeProcess && activities.size() > 0 11219 && (mHomeProcess.info.flags & ApplicationInfo.FLAG_SYSTEM) == 0) { 11220 for (int activityNdx = activities.size() - 1; activityNdx >= 0; --activityNdx) { 11221 final ActivityRecord r = activities.get(activityNdx); 11222 if (r.isHomeActivity()) { 11223 Log.i(TAG, "Clearing package preferred activities from " + r.packageName); 11224 try { 11225 ActivityThread.getPackageManager() 11226 .clearPackagePreferredActivities(r.packageName); 11227 } catch (RemoteException c) { 11228 // pm is in same process, this will never happen. 11229 } 11230 } 11231 } 11232 } 11233 11234 if (!app.isolated) { 11235 // XXX Can't keep track of crash times for isolated processes, 11236 // because they don't have a perisistent identity. 11237 mProcessCrashTimes.put(app.info.processName, app.uid, now); 11238 } 11239 11240 if (app.crashHandler != null) mHandler.post(app.crashHandler); 11241 return true; 11242 } 11243 11244 void startAppProblemLocked(ProcessRecord app) { 11245 // If this app is not running under the current user, then we 11246 // can't give it a report button because that would require 11247 // launching the report UI under a different user. 11248 app.errorReportReceiver = null; 11249 11250 for (int userId : mCurrentProfileIds) { 11251 if (app.userId == userId) { 11252 app.errorReportReceiver = ApplicationErrorReport.getErrorReportReceiver( 11253 mContext, app.info.packageName, app.info.flags); 11254 } 11255 } 11256 skipCurrentReceiverLocked(app); 11257 } 11258 11259 void skipCurrentReceiverLocked(ProcessRecord app) { 11260 for (BroadcastQueue queue : mBroadcastQueues) { 11261 queue.skipCurrentReceiverLocked(app); 11262 } 11263 } 11264 11265 /** 11266 * Used by {@link com.android.internal.os.RuntimeInit} to report when an application crashes. 11267 * The application process will exit immediately after this call returns. 11268 * @param app object of the crashing app, null for the system server 11269 * @param crashInfo describing the exception 11270 */ 11271 public void handleApplicationCrash(IBinder app, ApplicationErrorReport.CrashInfo crashInfo) { 11272 ProcessRecord r = findAppProcess(app, "Crash"); 11273 final String processName = app == null ? "system_server" 11274 : (r == null ? "unknown" : r.processName); 11275 11276 handleApplicationCrashInner("crash", r, processName, crashInfo); 11277 } 11278 11279 /* Native crash reporting uses this inner version because it needs to be somewhat 11280 * decoupled from the AM-managed cleanup lifecycle 11281 */ 11282 void handleApplicationCrashInner(String eventType, ProcessRecord r, String processName, 11283 ApplicationErrorReport.CrashInfo crashInfo) { 11284 EventLog.writeEvent(EventLogTags.AM_CRASH, Binder.getCallingPid(), 11285 UserHandle.getUserId(Binder.getCallingUid()), processName, 11286 r == null ? -1 : r.info.flags, 11287 crashInfo.exceptionClassName, 11288 crashInfo.exceptionMessage, 11289 crashInfo.throwFileName, 11290 crashInfo.throwLineNumber); 11291 11292 addErrorToDropBox(eventType, r, processName, null, null, null, null, null, crashInfo); 11293 11294 crashApplication(r, crashInfo); 11295 } 11296 11297 public void handleApplicationStrictModeViolation( 11298 IBinder app, 11299 int violationMask, 11300 StrictMode.ViolationInfo info) { 11301 ProcessRecord r = findAppProcess(app, "StrictMode"); 11302 if (r == null) { 11303 return; 11304 } 11305 11306 if ((violationMask & StrictMode.PENALTY_DROPBOX) != 0) { 11307 Integer stackFingerprint = info.hashCode(); 11308 boolean logIt = true; 11309 synchronized (mAlreadyLoggedViolatedStacks) { 11310 if (mAlreadyLoggedViolatedStacks.contains(stackFingerprint)) { 11311 logIt = false; 11312 // TODO: sub-sample into EventLog for these, with 11313 // the info.durationMillis? Then we'd get 11314 // the relative pain numbers, without logging all 11315 // the stack traces repeatedly. We'd want to do 11316 // likewise in the client code, which also does 11317 // dup suppression, before the Binder call. 11318 } else { 11319 if (mAlreadyLoggedViolatedStacks.size() >= MAX_DUP_SUPPRESSED_STACKS) { 11320 mAlreadyLoggedViolatedStacks.clear(); 11321 } 11322 mAlreadyLoggedViolatedStacks.add(stackFingerprint); 11323 } 11324 } 11325 if (logIt) { 11326 logStrictModeViolationToDropBox(r, info); 11327 } 11328 } 11329 11330 if ((violationMask & StrictMode.PENALTY_DIALOG) != 0) { 11331 AppErrorResult result = new AppErrorResult(); 11332 synchronized (this) { 11333 final long origId = Binder.clearCallingIdentity(); 11334 11335 Message msg = Message.obtain(); 11336 msg.what = SHOW_STRICT_MODE_VIOLATION_MSG; 11337 HashMap<String, Object> data = new HashMap<String, Object>(); 11338 data.put("result", result); 11339 data.put("app", r); 11340 data.put("violationMask", violationMask); 11341 data.put("info", info); 11342 msg.obj = data; 11343 mHandler.sendMessage(msg); 11344 11345 Binder.restoreCallingIdentity(origId); 11346 } 11347 int res = result.get(); 11348 Slog.w(TAG, "handleApplicationStrictModeViolation; res=" + res); 11349 } 11350 } 11351 11352 // Depending on the policy in effect, there could be a bunch of 11353 // these in quick succession so we try to batch these together to 11354 // minimize disk writes, number of dropbox entries, and maximize 11355 // compression, by having more fewer, larger records. 11356 private void logStrictModeViolationToDropBox( 11357 ProcessRecord process, 11358 StrictMode.ViolationInfo info) { 11359 if (info == null) { 11360 return; 11361 } 11362 final boolean isSystemApp = process == null || 11363 (process.info.flags & (ApplicationInfo.FLAG_SYSTEM | 11364 ApplicationInfo.FLAG_UPDATED_SYSTEM_APP)) != 0; 11365 final String processName = process == null ? "unknown" : process.processName; 11366 final String dropboxTag = isSystemApp ? "system_app_strictmode" : "data_app_strictmode"; 11367 final DropBoxManager dbox = (DropBoxManager) 11368 mContext.getSystemService(Context.DROPBOX_SERVICE); 11369 11370 // Exit early if the dropbox isn't configured to accept this report type. 11371 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 11372 11373 boolean bufferWasEmpty; 11374 boolean needsFlush; 11375 final StringBuilder sb = isSystemApp ? mStrictModeBuffer : new StringBuilder(1024); 11376 synchronized (sb) { 11377 bufferWasEmpty = sb.length() == 0; 11378 appendDropBoxProcessHeaders(process, processName, sb); 11379 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 11380 sb.append("System-App: ").append(isSystemApp).append("\n"); 11381 sb.append("Uptime-Millis: ").append(info.violationUptimeMillis).append("\n"); 11382 if (info.violationNumThisLoop != 0) { 11383 sb.append("Loop-Violation-Number: ").append(info.violationNumThisLoop).append("\n"); 11384 } 11385 if (info.numAnimationsRunning != 0) { 11386 sb.append("Animations-Running: ").append(info.numAnimationsRunning).append("\n"); 11387 } 11388 if (info.broadcastIntentAction != null) { 11389 sb.append("Broadcast-Intent-Action: ").append(info.broadcastIntentAction).append("\n"); 11390 } 11391 if (info.durationMillis != -1) { 11392 sb.append("Duration-Millis: ").append(info.durationMillis).append("\n"); 11393 } 11394 if (info.numInstances != -1) { 11395 sb.append("Instance-Count: ").append(info.numInstances).append("\n"); 11396 } 11397 if (info.tags != null) { 11398 for (String tag : info.tags) { 11399 sb.append("Span-Tag: ").append(tag).append("\n"); 11400 } 11401 } 11402 sb.append("\n"); 11403 if (info.crashInfo != null && info.crashInfo.stackTrace != null) { 11404 sb.append(info.crashInfo.stackTrace); 11405 } 11406 sb.append("\n"); 11407 11408 // Only buffer up to ~64k. Various logging bits truncate 11409 // things at 128k. 11410 needsFlush = (sb.length() > 64 * 1024); 11411 } 11412 11413 // Flush immediately if the buffer's grown too large, or this 11414 // is a non-system app. Non-system apps are isolated with a 11415 // different tag & policy and not batched. 11416 // 11417 // Batching is useful during internal testing with 11418 // StrictMode settings turned up high. Without batching, 11419 // thousands of separate files could be created on boot. 11420 if (!isSystemApp || needsFlush) { 11421 new Thread("Error dump: " + dropboxTag) { 11422 @Override 11423 public void run() { 11424 String report; 11425 synchronized (sb) { 11426 report = sb.toString(); 11427 sb.delete(0, sb.length()); 11428 sb.trimToSize(); 11429 } 11430 if (report.length() != 0) { 11431 dbox.addText(dropboxTag, report); 11432 } 11433 } 11434 }.start(); 11435 return; 11436 } 11437 11438 // System app batching: 11439 if (!bufferWasEmpty) { 11440 // An existing dropbox-writing thread is outstanding, so 11441 // we don't need to start it up. The existing thread will 11442 // catch the buffer appends we just did. 11443 return; 11444 } 11445 11446 // Worker thread to both batch writes and to avoid blocking the caller on I/O. 11447 // (After this point, we shouldn't access AMS internal data structures.) 11448 new Thread("Error dump: " + dropboxTag) { 11449 @Override 11450 public void run() { 11451 // 5 second sleep to let stacks arrive and be batched together 11452 try { 11453 Thread.sleep(5000); // 5 seconds 11454 } catch (InterruptedException e) {} 11455 11456 String errorReport; 11457 synchronized (mStrictModeBuffer) { 11458 errorReport = mStrictModeBuffer.toString(); 11459 if (errorReport.length() == 0) { 11460 return; 11461 } 11462 mStrictModeBuffer.delete(0, mStrictModeBuffer.length()); 11463 mStrictModeBuffer.trimToSize(); 11464 } 11465 dbox.addText(dropboxTag, errorReport); 11466 } 11467 }.start(); 11468 } 11469 11470 /** 11471 * Used by {@link Log} via {@link com.android.internal.os.RuntimeInit} to report serious errors. 11472 * @param app object of the crashing app, null for the system server 11473 * @param tag reported by the caller 11474 * @param system whether this wtf is coming from the system 11475 * @param crashInfo describing the context of the error 11476 * @return true if the process should exit immediately (WTF is fatal) 11477 */ 11478 public boolean handleApplicationWtf(IBinder app, final String tag, boolean system, 11479 final ApplicationErrorReport.CrashInfo crashInfo) { 11480 final ProcessRecord r = findAppProcess(app, "WTF"); 11481 final String processName = app == null ? "system_server" 11482 : (r == null ? "unknown" : r.processName); 11483 11484 EventLog.writeEvent(EventLogTags.AM_WTF, 11485 UserHandle.getUserId(Binder.getCallingUid()), Binder.getCallingPid(), 11486 processName, 11487 r == null ? -1 : r.info.flags, 11488 tag, crashInfo.exceptionMessage); 11489 11490 if (system) { 11491 // If this is coming from the system, we could very well have low-level 11492 // system locks held, so we want to do this all asynchronously. And we 11493 // never want this to become fatal, so there is that too. 11494 mHandler.post(new Runnable() { 11495 @Override public void run() { 11496 addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, 11497 crashInfo); 11498 } 11499 }); 11500 return false; 11501 } 11502 11503 addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, crashInfo); 11504 11505 if (r != null && r.pid != Process.myPid() && 11506 Settings.Global.getInt(mContext.getContentResolver(), 11507 Settings.Global.WTF_IS_FATAL, 0) != 0) { 11508 crashApplication(r, crashInfo); 11509 return true; 11510 } else { 11511 return false; 11512 } 11513 } 11514 11515 /** 11516 * @param app object of some object (as stored in {@link com.android.internal.os.RuntimeInit}) 11517 * @return the corresponding {@link ProcessRecord} object, or null if none could be found 11518 */ 11519 private ProcessRecord findAppProcess(IBinder app, String reason) { 11520 if (app == null) { 11521 return null; 11522 } 11523 11524 synchronized (this) { 11525 final int NP = mProcessNames.getMap().size(); 11526 for (int ip=0; ip<NP; ip++) { 11527 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 11528 final int NA = apps.size(); 11529 for (int ia=0; ia<NA; ia++) { 11530 ProcessRecord p = apps.valueAt(ia); 11531 if (p.thread != null && p.thread.asBinder() == app) { 11532 return p; 11533 } 11534 } 11535 } 11536 11537 Slog.w(TAG, "Can't find mystery application for " + reason 11538 + " from pid=" + Binder.getCallingPid() 11539 + " uid=" + Binder.getCallingUid() + ": " + app); 11540 return null; 11541 } 11542 } 11543 11544 /** 11545 * Utility function for addErrorToDropBox and handleStrictModeViolation's logging 11546 * to append various headers to the dropbox log text. 11547 */ 11548 private void appendDropBoxProcessHeaders(ProcessRecord process, String processName, 11549 StringBuilder sb) { 11550 // Watchdog thread ends up invoking this function (with 11551 // a null ProcessRecord) to add the stack file to dropbox. 11552 // Do not acquire a lock on this (am) in such cases, as it 11553 // could cause a potential deadlock, if and when watchdog 11554 // is invoked due to unavailability of lock on am and it 11555 // would prevent watchdog from killing system_server. 11556 if (process == null) { 11557 sb.append("Process: ").append(processName).append("\n"); 11558 return; 11559 } 11560 // Note: ProcessRecord 'process' is guarded by the service 11561 // instance. (notably process.pkgList, which could otherwise change 11562 // concurrently during execution of this method) 11563 synchronized (this) { 11564 sb.append("Process: ").append(processName).append("\n"); 11565 int flags = process.info.flags; 11566 IPackageManager pm = AppGlobals.getPackageManager(); 11567 sb.append("Flags: 0x").append(Integer.toString(flags, 16)).append("\n"); 11568 for (int ip=0; ip<process.pkgList.size(); ip++) { 11569 String pkg = process.pkgList.keyAt(ip); 11570 sb.append("Package: ").append(pkg); 11571 try { 11572 PackageInfo pi = pm.getPackageInfo(pkg, 0, UserHandle.getCallingUserId()); 11573 if (pi != null) { 11574 sb.append(" v").append(pi.versionCode); 11575 if (pi.versionName != null) { 11576 sb.append(" (").append(pi.versionName).append(")"); 11577 } 11578 } 11579 } catch (RemoteException e) { 11580 Slog.e(TAG, "Error getting package info: " + pkg, e); 11581 } 11582 sb.append("\n"); 11583 } 11584 } 11585 } 11586 11587 private static String processClass(ProcessRecord process) { 11588 if (process == null || process.pid == MY_PID) { 11589 return "system_server"; 11590 } else if ((process.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 11591 return "system_app"; 11592 } else { 11593 return "data_app"; 11594 } 11595 } 11596 11597 /** 11598 * Write a description of an error (crash, WTF, ANR) to the drop box. 11599 * @param eventType to include in the drop box tag ("crash", "wtf", etc.) 11600 * @param process which caused the error, null means the system server 11601 * @param activity which triggered the error, null if unknown 11602 * @param parent activity related to the error, null if unknown 11603 * @param subject line related to the error, null if absent 11604 * @param report in long form describing the error, null if absent 11605 * @param logFile to include in the report, null if none 11606 * @param crashInfo giving an application stack trace, null if absent 11607 */ 11608 public void addErrorToDropBox(String eventType, 11609 ProcessRecord process, String processName, ActivityRecord activity, 11610 ActivityRecord parent, String subject, 11611 final String report, final File logFile, 11612 final ApplicationErrorReport.CrashInfo crashInfo) { 11613 // NOTE -- this must never acquire the ActivityManagerService lock, 11614 // otherwise the watchdog may be prevented from resetting the system. 11615 11616 final String dropboxTag = processClass(process) + "_" + eventType; 11617 final DropBoxManager dbox = (DropBoxManager) 11618 mContext.getSystemService(Context.DROPBOX_SERVICE); 11619 11620 // Exit early if the dropbox isn't configured to accept this report type. 11621 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 11622 11623 final StringBuilder sb = new StringBuilder(1024); 11624 appendDropBoxProcessHeaders(process, processName, sb); 11625 if (activity != null) { 11626 sb.append("Activity: ").append(activity.shortComponentName).append("\n"); 11627 } 11628 if (parent != null && parent.app != null && parent.app.pid != process.pid) { 11629 sb.append("Parent-Process: ").append(parent.app.processName).append("\n"); 11630 } 11631 if (parent != null && parent != activity) { 11632 sb.append("Parent-Activity: ").append(parent.shortComponentName).append("\n"); 11633 } 11634 if (subject != null) { 11635 sb.append("Subject: ").append(subject).append("\n"); 11636 } 11637 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 11638 if (Debug.isDebuggerConnected()) { 11639 sb.append("Debugger: Connected\n"); 11640 } 11641 sb.append("\n"); 11642 11643 // Do the rest in a worker thread to avoid blocking the caller on I/O 11644 // (After this point, we shouldn't access AMS internal data structures.) 11645 Thread worker = new Thread("Error dump: " + dropboxTag) { 11646 @Override 11647 public void run() { 11648 if (report != null) { 11649 sb.append(report); 11650 } 11651 if (logFile != null) { 11652 try { 11653 sb.append(FileUtils.readTextFile(logFile, DROPBOX_MAX_SIZE, 11654 "\n\n[[TRUNCATED]]")); 11655 } catch (IOException e) { 11656 Slog.e(TAG, "Error reading " + logFile, e); 11657 } 11658 } 11659 if (crashInfo != null && crashInfo.stackTrace != null) { 11660 sb.append(crashInfo.stackTrace); 11661 } 11662 11663 String setting = Settings.Global.ERROR_LOGCAT_PREFIX + dropboxTag; 11664 int lines = Settings.Global.getInt(mContext.getContentResolver(), setting, 0); 11665 if (lines > 0) { 11666 sb.append("\n"); 11667 11668 // Merge several logcat streams, and take the last N lines 11669 InputStreamReader input = null; 11670 try { 11671 java.lang.Process logcat = new ProcessBuilder("/system/bin/logcat", 11672 "-v", "time", "-b", "events", "-b", "system", "-b", "main", 11673 "-b", "crash", 11674 "-t", String.valueOf(lines)).redirectErrorStream(true).start(); 11675 11676 try { logcat.getOutputStream().close(); } catch (IOException e) {} 11677 try { logcat.getErrorStream().close(); } catch (IOException e) {} 11678 input = new InputStreamReader(logcat.getInputStream()); 11679 11680 int num; 11681 char[] buf = new char[8192]; 11682 while ((num = input.read(buf)) > 0) sb.append(buf, 0, num); 11683 } catch (IOException e) { 11684 Slog.e(TAG, "Error running logcat", e); 11685 } finally { 11686 if (input != null) try { input.close(); } catch (IOException e) {} 11687 } 11688 } 11689 11690 dbox.addText(dropboxTag, sb.toString()); 11691 } 11692 }; 11693 11694 if (process == null) { 11695 // If process is null, we are being called from some internal code 11696 // and may be about to die -- run this synchronously. 11697 worker.run(); 11698 } else { 11699 worker.start(); 11700 } 11701 } 11702 11703 /** 11704 * Bring up the "unexpected error" dialog box for a crashing app. 11705 * Deal with edge cases (intercepts from instrumented applications, 11706 * ActivityController, error intent receivers, that sort of thing). 11707 * @param r the application crashing 11708 * @param crashInfo describing the failure 11709 */ 11710 private void crashApplication(ProcessRecord r, ApplicationErrorReport.CrashInfo crashInfo) { 11711 long timeMillis = System.currentTimeMillis(); 11712 String shortMsg = crashInfo.exceptionClassName; 11713 String longMsg = crashInfo.exceptionMessage; 11714 String stackTrace = crashInfo.stackTrace; 11715 if (shortMsg != null && longMsg != null) { 11716 longMsg = shortMsg + ": " + longMsg; 11717 } else if (shortMsg != null) { 11718 longMsg = shortMsg; 11719 } 11720 11721 AppErrorResult result = new AppErrorResult(); 11722 synchronized (this) { 11723 if (mController != null) { 11724 try { 11725 String name = r != null ? r.processName : null; 11726 int pid = r != null ? r.pid : Binder.getCallingPid(); 11727 int uid = r != null ? r.info.uid : Binder.getCallingUid(); 11728 if (!mController.appCrashed(name, pid, 11729 shortMsg, longMsg, timeMillis, crashInfo.stackTrace)) { 11730 if ("1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")) 11731 && "Native crash".equals(crashInfo.exceptionClassName)) { 11732 Slog.w(TAG, "Skip killing native crashed app " + name 11733 + "(" + pid + ") during testing"); 11734 } else { 11735 Slog.w(TAG, "Force-killing crashed app " + name 11736 + " at watcher's request"); 11737 if (r != null) { 11738 r.kill("crash", true); 11739 } else { 11740 // Huh. 11741 Process.killProcess(pid); 11742 Process.killProcessGroup(uid, pid); 11743 } 11744 } 11745 return; 11746 } 11747 } catch (RemoteException e) { 11748 mController = null; 11749 Watchdog.getInstance().setActivityController(null); 11750 } 11751 } 11752 11753 final long origId = Binder.clearCallingIdentity(); 11754 11755 // If this process is running instrumentation, finish it. 11756 if (r != null && r.instrumentationClass != null) { 11757 Slog.w(TAG, "Error in app " + r.processName 11758 + " running instrumentation " + r.instrumentationClass + ":"); 11759 if (shortMsg != null) Slog.w(TAG, " " + shortMsg); 11760 if (longMsg != null) Slog.w(TAG, " " + longMsg); 11761 Bundle info = new Bundle(); 11762 info.putString("shortMsg", shortMsg); 11763 info.putString("longMsg", longMsg); 11764 finishInstrumentationLocked(r, Activity.RESULT_CANCELED, info); 11765 Binder.restoreCallingIdentity(origId); 11766 return; 11767 } 11768 11769 // If we can't identify the process or it's already exceeded its crash quota, 11770 // quit right away without showing a crash dialog. 11771 if (r == null || !makeAppCrashingLocked(r, shortMsg, longMsg, stackTrace)) { 11772 Binder.restoreCallingIdentity(origId); 11773 return; 11774 } 11775 11776 Message msg = Message.obtain(); 11777 msg.what = SHOW_ERROR_MSG; 11778 HashMap data = new HashMap(); 11779 data.put("result", result); 11780 data.put("app", r); 11781 msg.obj = data; 11782 mHandler.sendMessage(msg); 11783 11784 Binder.restoreCallingIdentity(origId); 11785 } 11786 11787 int res = result.get(); 11788 11789 Intent appErrorIntent = null; 11790 synchronized (this) { 11791 if (r != null && !r.isolated) { 11792 // XXX Can't keep track of crash time for isolated processes, 11793 // since they don't have a persistent identity. 11794 mProcessCrashTimes.put(r.info.processName, r.uid, 11795 SystemClock.uptimeMillis()); 11796 } 11797 if (res == AppErrorDialog.FORCE_QUIT_AND_REPORT) { 11798 appErrorIntent = createAppErrorIntentLocked(r, timeMillis, crashInfo); 11799 } 11800 } 11801 11802 if (appErrorIntent != null) { 11803 try { 11804 mContext.startActivityAsUser(appErrorIntent, new UserHandle(r.userId)); 11805 } catch (ActivityNotFoundException e) { 11806 Slog.w(TAG, "bug report receiver dissappeared", e); 11807 } 11808 } 11809 } 11810 11811 Intent createAppErrorIntentLocked(ProcessRecord r, 11812 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 11813 ApplicationErrorReport report = createAppErrorReportLocked(r, timeMillis, crashInfo); 11814 if (report == null) { 11815 return null; 11816 } 11817 Intent result = new Intent(Intent.ACTION_APP_ERROR); 11818 result.setComponent(r.errorReportReceiver); 11819 result.putExtra(Intent.EXTRA_BUG_REPORT, report); 11820 result.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 11821 return result; 11822 } 11823 11824 private ApplicationErrorReport createAppErrorReportLocked(ProcessRecord r, 11825 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 11826 if (r.errorReportReceiver == null) { 11827 return null; 11828 } 11829 11830 if (!r.crashing && !r.notResponding && !r.forceCrashReport) { 11831 return null; 11832 } 11833 11834 ApplicationErrorReport report = new ApplicationErrorReport(); 11835 report.packageName = r.info.packageName; 11836 report.installerPackageName = r.errorReportReceiver.getPackageName(); 11837 report.processName = r.processName; 11838 report.time = timeMillis; 11839 report.systemApp = (r.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0; 11840 11841 if (r.crashing || r.forceCrashReport) { 11842 report.type = ApplicationErrorReport.TYPE_CRASH; 11843 report.crashInfo = crashInfo; 11844 } else if (r.notResponding) { 11845 report.type = ApplicationErrorReport.TYPE_ANR; 11846 report.anrInfo = new ApplicationErrorReport.AnrInfo(); 11847 11848 report.anrInfo.activity = r.notRespondingReport.tag; 11849 report.anrInfo.cause = r.notRespondingReport.shortMsg; 11850 report.anrInfo.info = r.notRespondingReport.longMsg; 11851 } 11852 11853 return report; 11854 } 11855 11856 public List<ActivityManager.ProcessErrorStateInfo> getProcessesInErrorState() { 11857 enforceNotIsolatedCaller("getProcessesInErrorState"); 11858 // assume our apps are happy - lazy create the list 11859 List<ActivityManager.ProcessErrorStateInfo> errList = null; 11860 11861 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 11862 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 11863 int userId = UserHandle.getUserId(Binder.getCallingUid()); 11864 11865 synchronized (this) { 11866 11867 // iterate across all processes 11868 for (int i=mLruProcesses.size()-1; i>=0; i--) { 11869 ProcessRecord app = mLruProcesses.get(i); 11870 if (!allUsers && app.userId != userId) { 11871 continue; 11872 } 11873 if ((app.thread != null) && (app.crashing || app.notResponding)) { 11874 // This one's in trouble, so we'll generate a report for it 11875 // crashes are higher priority (in case there's a crash *and* an anr) 11876 ActivityManager.ProcessErrorStateInfo report = null; 11877 if (app.crashing) { 11878 report = app.crashingReport; 11879 } else if (app.notResponding) { 11880 report = app.notRespondingReport; 11881 } 11882 11883 if (report != null) { 11884 if (errList == null) { 11885 errList = new ArrayList<ActivityManager.ProcessErrorStateInfo>(1); 11886 } 11887 errList.add(report); 11888 } else { 11889 Slog.w(TAG, "Missing app error report, app = " + app.processName + 11890 " crashing = " + app.crashing + 11891 " notResponding = " + app.notResponding); 11892 } 11893 } 11894 } 11895 } 11896 11897 return errList; 11898 } 11899 11900 static int procStateToImportance(int procState, int memAdj, 11901 ActivityManager.RunningAppProcessInfo currApp) { 11902 int imp = ActivityManager.RunningAppProcessInfo.procStateToImportance(procState); 11903 if (imp == ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND) { 11904 currApp.lru = memAdj; 11905 } else { 11906 currApp.lru = 0; 11907 } 11908 return imp; 11909 } 11910 11911 private void fillInProcMemInfo(ProcessRecord app, 11912 ActivityManager.RunningAppProcessInfo outInfo) { 11913 outInfo.pid = app.pid; 11914 outInfo.uid = app.info.uid; 11915 if (mHeavyWeightProcess == app) { 11916 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_CANT_SAVE_STATE; 11917 } 11918 if (app.persistent) { 11919 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_PERSISTENT; 11920 } 11921 if (app.activities.size() > 0) { 11922 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_HAS_ACTIVITIES; 11923 } 11924 outInfo.lastTrimLevel = app.trimMemoryLevel; 11925 int adj = app.curAdj; 11926 int procState = app.curProcState; 11927 outInfo.importance = procStateToImportance(procState, adj, outInfo); 11928 outInfo.importanceReasonCode = app.adjTypeCode; 11929 outInfo.processState = app.curProcState; 11930 } 11931 11932 public List<ActivityManager.RunningAppProcessInfo> getRunningAppProcesses() { 11933 enforceNotIsolatedCaller("getRunningAppProcesses"); 11934 // Lazy instantiation of list 11935 List<ActivityManager.RunningAppProcessInfo> runList = null; 11936 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 11937 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 11938 int userId = UserHandle.getUserId(Binder.getCallingUid()); 11939 synchronized (this) { 11940 // Iterate across all processes 11941 for (int i=mLruProcesses.size()-1; i>=0; i--) { 11942 ProcessRecord app = mLruProcesses.get(i); 11943 if (!allUsers && app.userId != userId) { 11944 continue; 11945 } 11946 if ((app.thread != null) && (!app.crashing && !app.notResponding)) { 11947 // Generate process state info for running application 11948 ActivityManager.RunningAppProcessInfo currApp = 11949 new ActivityManager.RunningAppProcessInfo(app.processName, 11950 app.pid, app.getPackageList()); 11951 fillInProcMemInfo(app, currApp); 11952 if (app.adjSource instanceof ProcessRecord) { 11953 currApp.importanceReasonPid = ((ProcessRecord)app.adjSource).pid; 11954 currApp.importanceReasonImportance = 11955 ActivityManager.RunningAppProcessInfo.procStateToImportance( 11956 app.adjSourceProcState); 11957 } else if (app.adjSource instanceof ActivityRecord) { 11958 ActivityRecord r = (ActivityRecord)app.adjSource; 11959 if (r.app != null) currApp.importanceReasonPid = r.app.pid; 11960 } 11961 if (app.adjTarget instanceof ComponentName) { 11962 currApp.importanceReasonComponent = (ComponentName)app.adjTarget; 11963 } 11964 //Slog.v(TAG, "Proc " + app.processName + ": imp=" + currApp.importance 11965 // + " lru=" + currApp.lru); 11966 if (runList == null) { 11967 runList = new ArrayList<ActivityManager.RunningAppProcessInfo>(); 11968 } 11969 runList.add(currApp); 11970 } 11971 } 11972 } 11973 return runList; 11974 } 11975 11976 public List<ApplicationInfo> getRunningExternalApplications() { 11977 enforceNotIsolatedCaller("getRunningExternalApplications"); 11978 List<ActivityManager.RunningAppProcessInfo> runningApps = getRunningAppProcesses(); 11979 List<ApplicationInfo> retList = new ArrayList<ApplicationInfo>(); 11980 if (runningApps != null && runningApps.size() > 0) { 11981 Set<String> extList = new HashSet<String>(); 11982 for (ActivityManager.RunningAppProcessInfo app : runningApps) { 11983 if (app.pkgList != null) { 11984 for (String pkg : app.pkgList) { 11985 extList.add(pkg); 11986 } 11987 } 11988 } 11989 IPackageManager pm = AppGlobals.getPackageManager(); 11990 for (String pkg : extList) { 11991 try { 11992 ApplicationInfo info = pm.getApplicationInfo(pkg, 0, UserHandle.getCallingUserId()); 11993 if ((info.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0) { 11994 retList.add(info); 11995 } 11996 } catch (RemoteException e) { 11997 } 11998 } 11999 } 12000 return retList; 12001 } 12002 12003 @Override 12004 public void getMyMemoryState(ActivityManager.RunningAppProcessInfo outInfo) { 12005 enforceNotIsolatedCaller("getMyMemoryState"); 12006 synchronized (this) { 12007 ProcessRecord proc; 12008 synchronized (mPidsSelfLocked) { 12009 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 12010 } 12011 fillInProcMemInfo(proc, outInfo); 12012 } 12013 } 12014 12015 @Override 12016 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 12017 if (checkCallingPermission(android.Manifest.permission.DUMP) 12018 != PackageManager.PERMISSION_GRANTED) { 12019 pw.println("Permission Denial: can't dump ActivityManager from from pid=" 12020 + Binder.getCallingPid() 12021 + ", uid=" + Binder.getCallingUid() 12022 + " without permission " 12023 + android.Manifest.permission.DUMP); 12024 return; 12025 } 12026 12027 boolean dumpAll = false; 12028 boolean dumpClient = false; 12029 String dumpPackage = null; 12030 12031 int opti = 0; 12032 while (opti < args.length) { 12033 String opt = args[opti]; 12034 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 12035 break; 12036 } 12037 opti++; 12038 if ("-a".equals(opt)) { 12039 dumpAll = true; 12040 } else if ("-c".equals(opt)) { 12041 dumpClient = true; 12042 } else if ("-h".equals(opt)) { 12043 pw.println("Activity manager dump options:"); 12044 pw.println(" [-a] [-c] [-h] [cmd] ..."); 12045 pw.println(" cmd may be one of:"); 12046 pw.println(" a[ctivities]: activity stack state"); 12047 pw.println(" r[recents]: recent activities state"); 12048 pw.println(" b[roadcasts] [PACKAGE_NAME] [history [-s]]: broadcast state"); 12049 pw.println(" i[ntents] [PACKAGE_NAME]: pending intent state"); 12050 pw.println(" p[rocesses] [PACKAGE_NAME]: process state"); 12051 pw.println(" o[om]: out of memory management"); 12052 pw.println(" prov[iders] [COMP_SPEC ...]: content provider state"); 12053 pw.println(" provider [COMP_SPEC]: provider client-side state"); 12054 pw.println(" s[ervices] [COMP_SPEC ...]: service state"); 12055 pw.println(" service [COMP_SPEC]: service client-side state"); 12056 pw.println(" package [PACKAGE_NAME]: all state related to given package"); 12057 pw.println(" all: dump all activities"); 12058 pw.println(" top: dump the top activity"); 12059 pw.println(" cmd may also be a COMP_SPEC to dump activities."); 12060 pw.println(" COMP_SPEC may be a component name (com.foo/.myApp),"); 12061 pw.println(" a partial substring in a component name, a"); 12062 pw.println(" hex object identifier."); 12063 pw.println(" -a: include all available server state."); 12064 pw.println(" -c: include client state."); 12065 return; 12066 } else { 12067 pw.println("Unknown argument: " + opt + "; use -h for help"); 12068 } 12069 } 12070 12071 long origId = Binder.clearCallingIdentity(); 12072 boolean more = false; 12073 // Is the caller requesting to dump a particular piece of data? 12074 if (opti < args.length) { 12075 String cmd = args[opti]; 12076 opti++; 12077 if ("activities".equals(cmd) || "a".equals(cmd)) { 12078 synchronized (this) { 12079 dumpActivitiesLocked(fd, pw, args, opti, true, dumpClient, null); 12080 } 12081 } else if ("recents".equals(cmd) || "r".equals(cmd)) { 12082 synchronized (this) { 12083 dumpRecentsLocked(fd, pw, args, opti, true, null); 12084 } 12085 } else if ("broadcasts".equals(cmd) || "b".equals(cmd)) { 12086 String[] newArgs; 12087 String name; 12088 if (opti >= args.length) { 12089 name = null; 12090 newArgs = EMPTY_STRING_ARRAY; 12091 } else { 12092 name = args[opti]; 12093 opti++; 12094 newArgs = new String[args.length - opti]; 12095 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12096 args.length - opti); 12097 } 12098 synchronized (this) { 12099 dumpBroadcastsLocked(fd, pw, args, opti, true, name); 12100 } 12101 } else if ("intents".equals(cmd) || "i".equals(cmd)) { 12102 String[] newArgs; 12103 String name; 12104 if (opti >= args.length) { 12105 name = null; 12106 newArgs = EMPTY_STRING_ARRAY; 12107 } else { 12108 name = args[opti]; 12109 opti++; 12110 newArgs = new String[args.length - opti]; 12111 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12112 args.length - opti); 12113 } 12114 synchronized (this) { 12115 dumpPendingIntentsLocked(fd, pw, args, opti, true, name); 12116 } 12117 } else if ("processes".equals(cmd) || "p".equals(cmd)) { 12118 String[] newArgs; 12119 String name; 12120 if (opti >= args.length) { 12121 name = null; 12122 newArgs = EMPTY_STRING_ARRAY; 12123 } else { 12124 name = args[opti]; 12125 opti++; 12126 newArgs = new String[args.length - opti]; 12127 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12128 args.length - opti); 12129 } 12130 synchronized (this) { 12131 dumpProcessesLocked(fd, pw, args, opti, true, name); 12132 } 12133 } else if ("oom".equals(cmd) || "o".equals(cmd)) { 12134 synchronized (this) { 12135 dumpOomLocked(fd, pw, args, opti, true); 12136 } 12137 } else if ("provider".equals(cmd)) { 12138 String[] newArgs; 12139 String name; 12140 if (opti >= args.length) { 12141 name = null; 12142 newArgs = EMPTY_STRING_ARRAY; 12143 } else { 12144 name = args[opti]; 12145 opti++; 12146 newArgs = new String[args.length - opti]; 12147 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, args.length - opti); 12148 } 12149 if (!dumpProvider(fd, pw, name, newArgs, 0, dumpAll)) { 12150 pw.println("No providers match: " + name); 12151 pw.println("Use -h for help."); 12152 } 12153 } else if ("providers".equals(cmd) || "prov".equals(cmd)) { 12154 synchronized (this) { 12155 dumpProvidersLocked(fd, pw, args, opti, true, null); 12156 } 12157 } else if ("service".equals(cmd)) { 12158 String[] newArgs; 12159 String name; 12160 if (opti >= args.length) { 12161 name = null; 12162 newArgs = EMPTY_STRING_ARRAY; 12163 } else { 12164 name = args[opti]; 12165 opti++; 12166 newArgs = new String[args.length - opti]; 12167 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12168 args.length - opti); 12169 } 12170 if (!mServices.dumpService(fd, pw, name, newArgs, 0, dumpAll)) { 12171 pw.println("No services match: " + name); 12172 pw.println("Use -h for help."); 12173 } 12174 } else if ("package".equals(cmd)) { 12175 String[] newArgs; 12176 if (opti >= args.length) { 12177 pw.println("package: no package name specified"); 12178 pw.println("Use -h for help."); 12179 } else { 12180 dumpPackage = args[opti]; 12181 opti++; 12182 newArgs = new String[args.length - opti]; 12183 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12184 args.length - opti); 12185 args = newArgs; 12186 opti = 0; 12187 more = true; 12188 } 12189 } else if ("services".equals(cmd) || "s".equals(cmd)) { 12190 synchronized (this) { 12191 mServices.dumpServicesLocked(fd, pw, args, opti, true, dumpClient, null); 12192 } 12193 } else { 12194 // Dumping a single activity? 12195 if (!dumpActivity(fd, pw, cmd, args, opti, dumpAll)) { 12196 pw.println("Bad activity command, or no activities match: " + cmd); 12197 pw.println("Use -h for help."); 12198 } 12199 } 12200 if (!more) { 12201 Binder.restoreCallingIdentity(origId); 12202 return; 12203 } 12204 } 12205 12206 // No piece of data specified, dump everything. 12207 synchronized (this) { 12208 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12209 pw.println(); 12210 if (dumpAll) { 12211 pw.println("-------------------------------------------------------------------------------"); 12212 } 12213 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12214 pw.println(); 12215 if (dumpAll) { 12216 pw.println("-------------------------------------------------------------------------------"); 12217 } 12218 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12219 pw.println(); 12220 if (dumpAll) { 12221 pw.println("-------------------------------------------------------------------------------"); 12222 } 12223 mServices.dumpServicesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 12224 pw.println(); 12225 if (dumpAll) { 12226 pw.println("-------------------------------------------------------------------------------"); 12227 } 12228 dumpRecentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12229 pw.println(); 12230 if (dumpAll) { 12231 pw.println("-------------------------------------------------------------------------------"); 12232 } 12233 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 12234 pw.println(); 12235 if (dumpAll) { 12236 pw.println("-------------------------------------------------------------------------------"); 12237 } 12238 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12239 } 12240 Binder.restoreCallingIdentity(origId); 12241 } 12242 12243 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12244 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) { 12245 pw.println("ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)"); 12246 12247 boolean printedAnything = mStackSupervisor.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient, 12248 dumpPackage); 12249 boolean needSep = printedAnything; 12250 12251 boolean printed = ActivityStackSupervisor.printThisActivity(pw, mFocusedActivity, 12252 dumpPackage, needSep, " mFocusedActivity: "); 12253 if (printed) { 12254 printedAnything = true; 12255 needSep = false; 12256 } 12257 12258 if (dumpPackage == null) { 12259 if (needSep) { 12260 pw.println(); 12261 } 12262 needSep = true; 12263 printedAnything = true; 12264 mStackSupervisor.dump(pw, " "); 12265 } 12266 12267 if (!printedAnything) { 12268 pw.println(" (nothing)"); 12269 } 12270 } 12271 12272 void dumpRecentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12273 int opti, boolean dumpAll, String dumpPackage) { 12274 pw.println("ACTIVITY MANAGER RECENT ACTIVITIES (dumpsys activity recents)"); 12275 12276 boolean printedAnything = false; 12277 12278 if (mRecentTasks.size() > 0) { 12279 boolean printedHeader = false; 12280 12281 final int N = mRecentTasks.size(); 12282 for (int i=0; i<N; i++) { 12283 TaskRecord tr = mRecentTasks.get(i); 12284 if (dumpPackage != null) { 12285 if (tr.realActivity == null || 12286 !dumpPackage.equals(tr.realActivity)) { 12287 continue; 12288 } 12289 } 12290 if (!printedHeader) { 12291 pw.println(" Recent tasks:"); 12292 printedHeader = true; 12293 printedAnything = true; 12294 } 12295 pw.print(" * Recent #"); pw.print(i); pw.print(": "); 12296 pw.println(tr); 12297 if (dumpAll) { 12298 mRecentTasks.get(i).dump(pw, " "); 12299 } 12300 } 12301 } 12302 12303 if (!printedAnything) { 12304 pw.println(" (nothing)"); 12305 } 12306 } 12307 12308 void dumpProcessesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12309 int opti, boolean dumpAll, String dumpPackage) { 12310 boolean needSep = false; 12311 boolean printedAnything = false; 12312 int numPers = 0; 12313 12314 pw.println("ACTIVITY MANAGER RUNNING PROCESSES (dumpsys activity processes)"); 12315 12316 if (dumpAll) { 12317 final int NP = mProcessNames.getMap().size(); 12318 for (int ip=0; ip<NP; ip++) { 12319 SparseArray<ProcessRecord> procs = mProcessNames.getMap().valueAt(ip); 12320 final int NA = procs.size(); 12321 for (int ia=0; ia<NA; ia++) { 12322 ProcessRecord r = procs.valueAt(ia); 12323 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 12324 continue; 12325 } 12326 if (!needSep) { 12327 pw.println(" All known processes:"); 12328 needSep = true; 12329 printedAnything = true; 12330 } 12331 pw.print(r.persistent ? " *PERS*" : " *APP*"); 12332 pw.print(" UID "); pw.print(procs.keyAt(ia)); 12333 pw.print(" "); pw.println(r); 12334 r.dump(pw, " "); 12335 if (r.persistent) { 12336 numPers++; 12337 } 12338 } 12339 } 12340 } 12341 12342 if (mIsolatedProcesses.size() > 0) { 12343 boolean printed = false; 12344 for (int i=0; i<mIsolatedProcesses.size(); i++) { 12345 ProcessRecord r = mIsolatedProcesses.valueAt(i); 12346 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 12347 continue; 12348 } 12349 if (!printed) { 12350 if (needSep) { 12351 pw.println(); 12352 } 12353 pw.println(" Isolated process list (sorted by uid):"); 12354 printedAnything = true; 12355 printed = true; 12356 needSep = true; 12357 } 12358 pw.println(String.format("%sIsolated #%2d: %s", 12359 " ", i, r.toString())); 12360 } 12361 } 12362 12363 if (mLruProcesses.size() > 0) { 12364 if (needSep) { 12365 pw.println(); 12366 } 12367 pw.print(" Process LRU list (sorted by oom_adj, "); pw.print(mLruProcesses.size()); 12368 pw.print(" total, non-act at "); 12369 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 12370 pw.print(", non-svc at "); 12371 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 12372 pw.println("):"); 12373 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", false, dumpPackage); 12374 needSep = true; 12375 printedAnything = true; 12376 } 12377 12378 if (dumpAll || dumpPackage != null) { 12379 synchronized (mPidsSelfLocked) { 12380 boolean printed = false; 12381 for (int i=0; i<mPidsSelfLocked.size(); i++) { 12382 ProcessRecord r = mPidsSelfLocked.valueAt(i); 12383 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 12384 continue; 12385 } 12386 if (!printed) { 12387 if (needSep) pw.println(); 12388 needSep = true; 12389 pw.println(" PID mappings:"); 12390 printed = true; 12391 printedAnything = true; 12392 } 12393 pw.print(" PID #"); pw.print(mPidsSelfLocked.keyAt(i)); 12394 pw.print(": "); pw.println(mPidsSelfLocked.valueAt(i)); 12395 } 12396 } 12397 } 12398 12399 if (mForegroundProcesses.size() > 0) { 12400 synchronized (mPidsSelfLocked) { 12401 boolean printed = false; 12402 for (int i=0; i<mForegroundProcesses.size(); i++) { 12403 ProcessRecord r = mPidsSelfLocked.get( 12404 mForegroundProcesses.valueAt(i).pid); 12405 if (dumpPackage != null && (r == null 12406 || !r.pkgList.containsKey(dumpPackage))) { 12407 continue; 12408 } 12409 if (!printed) { 12410 if (needSep) pw.println(); 12411 needSep = true; 12412 pw.println(" Foreground Processes:"); 12413 printed = true; 12414 printedAnything = true; 12415 } 12416 pw.print(" PID #"); pw.print(mForegroundProcesses.keyAt(i)); 12417 pw.print(": "); pw.println(mForegroundProcesses.valueAt(i)); 12418 } 12419 } 12420 } 12421 12422 if (mPersistentStartingProcesses.size() > 0) { 12423 if (needSep) pw.println(); 12424 needSep = true; 12425 printedAnything = true; 12426 pw.println(" Persisent processes that are starting:"); 12427 dumpProcessList(pw, this, mPersistentStartingProcesses, " ", 12428 "Starting Norm", "Restarting PERS", dumpPackage); 12429 } 12430 12431 if (mRemovedProcesses.size() > 0) { 12432 if (needSep) pw.println(); 12433 needSep = true; 12434 printedAnything = true; 12435 pw.println(" Processes that are being removed:"); 12436 dumpProcessList(pw, this, mRemovedProcesses, " ", 12437 "Removed Norm", "Removed PERS", dumpPackage); 12438 } 12439 12440 if (mProcessesOnHold.size() > 0) { 12441 if (needSep) pw.println(); 12442 needSep = true; 12443 printedAnything = true; 12444 pw.println(" Processes that are on old until the system is ready:"); 12445 dumpProcessList(pw, this, mProcessesOnHold, " ", 12446 "OnHold Norm", "OnHold PERS", dumpPackage); 12447 } 12448 12449 needSep = dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, dumpPackage); 12450 12451 if (mProcessCrashTimes.getMap().size() > 0) { 12452 boolean printed = false; 12453 long now = SystemClock.uptimeMillis(); 12454 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 12455 final int NP = pmap.size(); 12456 for (int ip=0; ip<NP; ip++) { 12457 String pname = pmap.keyAt(ip); 12458 SparseArray<Long> uids = pmap.valueAt(ip); 12459 final int N = uids.size(); 12460 for (int i=0; i<N; i++) { 12461 int puid = uids.keyAt(i); 12462 ProcessRecord r = mProcessNames.get(pname, puid); 12463 if (dumpPackage != null && (r == null 12464 || !r.pkgList.containsKey(dumpPackage))) { 12465 continue; 12466 } 12467 if (!printed) { 12468 if (needSep) pw.println(); 12469 needSep = true; 12470 pw.println(" Time since processes crashed:"); 12471 printed = true; 12472 printedAnything = true; 12473 } 12474 pw.print(" Process "); pw.print(pname); 12475 pw.print(" uid "); pw.print(puid); 12476 pw.print(": last crashed "); 12477 TimeUtils.formatDuration(now-uids.valueAt(i), pw); 12478 pw.println(" ago"); 12479 } 12480 } 12481 } 12482 12483 if (mBadProcesses.getMap().size() > 0) { 12484 boolean printed = false; 12485 final ArrayMap<String, SparseArray<BadProcessInfo>> pmap = mBadProcesses.getMap(); 12486 final int NP = pmap.size(); 12487 for (int ip=0; ip<NP; ip++) { 12488 String pname = pmap.keyAt(ip); 12489 SparseArray<BadProcessInfo> uids = pmap.valueAt(ip); 12490 final int N = uids.size(); 12491 for (int i=0; i<N; i++) { 12492 int puid = uids.keyAt(i); 12493 ProcessRecord r = mProcessNames.get(pname, puid); 12494 if (dumpPackage != null && (r == null 12495 || !r.pkgList.containsKey(dumpPackage))) { 12496 continue; 12497 } 12498 if (!printed) { 12499 if (needSep) pw.println(); 12500 needSep = true; 12501 pw.println(" Bad processes:"); 12502 printedAnything = true; 12503 } 12504 BadProcessInfo info = uids.valueAt(i); 12505 pw.print(" Bad process "); pw.print(pname); 12506 pw.print(" uid "); pw.print(puid); 12507 pw.print(": crashed at time "); pw.println(info.time); 12508 if (info.shortMsg != null) { 12509 pw.print(" Short msg: "); pw.println(info.shortMsg); 12510 } 12511 if (info.longMsg != null) { 12512 pw.print(" Long msg: "); pw.println(info.longMsg); 12513 } 12514 if (info.stack != null) { 12515 pw.println(" Stack:"); 12516 int lastPos = 0; 12517 for (int pos=0; pos<info.stack.length(); pos++) { 12518 if (info.stack.charAt(pos) == '\n') { 12519 pw.print(" "); 12520 pw.write(info.stack, lastPos, pos-lastPos); 12521 pw.println(); 12522 lastPos = pos+1; 12523 } 12524 } 12525 if (lastPos < info.stack.length()) { 12526 pw.print(" "); 12527 pw.write(info.stack, lastPos, info.stack.length()-lastPos); 12528 pw.println(); 12529 } 12530 } 12531 } 12532 } 12533 } 12534 12535 if (dumpPackage == null) { 12536 pw.println(); 12537 needSep = false; 12538 pw.println(" mStartedUsers:"); 12539 for (int i=0; i<mStartedUsers.size(); i++) { 12540 UserStartedState uss = mStartedUsers.valueAt(i); 12541 pw.print(" User #"); pw.print(uss.mHandle.getIdentifier()); 12542 pw.print(": "); uss.dump("", pw); 12543 } 12544 pw.print(" mStartedUserArray: ["); 12545 for (int i=0; i<mStartedUserArray.length; i++) { 12546 if (i > 0) pw.print(", "); 12547 pw.print(mStartedUserArray[i]); 12548 } 12549 pw.println("]"); 12550 pw.print(" mUserLru: ["); 12551 for (int i=0; i<mUserLru.size(); i++) { 12552 if (i > 0) pw.print(", "); 12553 pw.print(mUserLru.get(i)); 12554 } 12555 pw.println("]"); 12556 if (dumpAll) { 12557 pw.print(" mStartedUserArray: "); pw.println(Arrays.toString(mStartedUserArray)); 12558 } 12559 synchronized (mUserProfileGroupIdsSelfLocked) { 12560 if (mUserProfileGroupIdsSelfLocked.size() > 0) { 12561 pw.println(" mUserProfileGroupIds:"); 12562 for (int i=0; i<mUserProfileGroupIdsSelfLocked.size(); i++) { 12563 pw.print(" User #"); 12564 pw.print(mUserProfileGroupIdsSelfLocked.keyAt(i)); 12565 pw.print(" -> profile #"); 12566 pw.println(mUserProfileGroupIdsSelfLocked.valueAt(i)); 12567 } 12568 } 12569 } 12570 } 12571 if (mHomeProcess != null && (dumpPackage == null 12572 || mHomeProcess.pkgList.containsKey(dumpPackage))) { 12573 if (needSep) { 12574 pw.println(); 12575 needSep = false; 12576 } 12577 pw.println(" mHomeProcess: " + mHomeProcess); 12578 } 12579 if (mPreviousProcess != null && (dumpPackage == null 12580 || mPreviousProcess.pkgList.containsKey(dumpPackage))) { 12581 if (needSep) { 12582 pw.println(); 12583 needSep = false; 12584 } 12585 pw.println(" mPreviousProcess: " + mPreviousProcess); 12586 } 12587 if (dumpAll) { 12588 StringBuilder sb = new StringBuilder(128); 12589 sb.append(" mPreviousProcessVisibleTime: "); 12590 TimeUtils.formatDuration(mPreviousProcessVisibleTime, sb); 12591 pw.println(sb); 12592 } 12593 if (mHeavyWeightProcess != null && (dumpPackage == null 12594 || mHeavyWeightProcess.pkgList.containsKey(dumpPackage))) { 12595 if (needSep) { 12596 pw.println(); 12597 needSep = false; 12598 } 12599 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 12600 } 12601 if (dumpPackage == null) { 12602 pw.println(" mConfiguration: " + mConfiguration); 12603 } 12604 if (dumpAll) { 12605 pw.println(" mConfigWillChange: " + getFocusedStack().mConfigWillChange); 12606 if (mCompatModePackages.getPackages().size() > 0) { 12607 boolean printed = false; 12608 for (Map.Entry<String, Integer> entry 12609 : mCompatModePackages.getPackages().entrySet()) { 12610 String pkg = entry.getKey(); 12611 int mode = entry.getValue(); 12612 if (dumpPackage != null && !dumpPackage.equals(pkg)) { 12613 continue; 12614 } 12615 if (!printed) { 12616 pw.println(" mScreenCompatPackages:"); 12617 printed = true; 12618 } 12619 pw.print(" "); pw.print(pkg); pw.print(": "); 12620 pw.print(mode); pw.println(); 12621 } 12622 } 12623 } 12624 if (dumpPackage == null) { 12625 if (mSleeping || mWentToSleep || mLockScreenShown) { 12626 pw.println(" mSleeping=" + mSleeping + " mWentToSleep=" + mWentToSleep 12627 + " mLockScreenShown " + mLockScreenShown); 12628 } 12629 if (mShuttingDown || mRunningVoice) { 12630 pw.print(" mShuttingDown=" + mShuttingDown + " mRunningVoice=" + mRunningVoice); 12631 } 12632 } 12633 if (mDebugApp != null || mOrigDebugApp != null || mDebugTransient 12634 || mOrigWaitForDebugger) { 12635 if (dumpPackage == null || dumpPackage.equals(mDebugApp) 12636 || dumpPackage.equals(mOrigDebugApp)) { 12637 if (needSep) { 12638 pw.println(); 12639 needSep = false; 12640 } 12641 pw.println(" mDebugApp=" + mDebugApp + "/orig=" + mOrigDebugApp 12642 + " mDebugTransient=" + mDebugTransient 12643 + " mOrigWaitForDebugger=" + mOrigWaitForDebugger); 12644 } 12645 } 12646 if (mOpenGlTraceApp != null) { 12647 if (dumpPackage == null || dumpPackage.equals(mOpenGlTraceApp)) { 12648 if (needSep) { 12649 pw.println(); 12650 needSep = false; 12651 } 12652 pw.println(" mOpenGlTraceApp=" + mOpenGlTraceApp); 12653 } 12654 } 12655 if (mProfileApp != null || mProfileProc != null || mProfileFile != null 12656 || mProfileFd != null) { 12657 if (dumpPackage == null || dumpPackage.equals(mProfileApp)) { 12658 if (needSep) { 12659 pw.println(); 12660 needSep = false; 12661 } 12662 pw.println(" mProfileApp=" + mProfileApp + " mProfileProc=" + mProfileProc); 12663 pw.println(" mProfileFile=" + mProfileFile + " mProfileFd=" + mProfileFd); 12664 pw.println(" mSamplingInterval=" + mSamplingInterval + " mAutoStopProfiler=" 12665 + mAutoStopProfiler); 12666 pw.println(" mProfileType=" + mProfileType); 12667 } 12668 } 12669 if (dumpPackage == null) { 12670 if (mAlwaysFinishActivities || mController != null) { 12671 pw.println(" mAlwaysFinishActivities=" + mAlwaysFinishActivities 12672 + " mController=" + mController); 12673 } 12674 if (dumpAll) { 12675 pw.println(" Total persistent processes: " + numPers); 12676 pw.println(" mProcessesReady=" + mProcessesReady 12677 + " mSystemReady=" + mSystemReady); 12678 pw.println(" mBooting=" + mBooting 12679 + " mBooted=" + mBooted 12680 + " mFactoryTest=" + mFactoryTest); 12681 pw.print(" mLastPowerCheckRealtime="); 12682 TimeUtils.formatDuration(mLastPowerCheckRealtime, pw); 12683 pw.println(""); 12684 pw.print(" mLastPowerCheckUptime="); 12685 TimeUtils.formatDuration(mLastPowerCheckUptime, pw); 12686 pw.println(""); 12687 pw.println(" mGoingToSleep=" + mStackSupervisor.mGoingToSleep); 12688 pw.println(" mLaunchingActivity=" + mStackSupervisor.mLaunchingActivity); 12689 pw.println(" mAdjSeq=" + mAdjSeq + " mLruSeq=" + mLruSeq); 12690 pw.println(" mNumNonCachedProcs=" + mNumNonCachedProcs 12691 + " (" + mLruProcesses.size() + " total)" 12692 + " mNumCachedHiddenProcs=" + mNumCachedHiddenProcs 12693 + " mNumServiceProcs=" + mNumServiceProcs 12694 + " mNewNumServiceProcs=" + mNewNumServiceProcs); 12695 pw.println(" mAllowLowerMemLevel=" + mAllowLowerMemLevel 12696 + " mLastMemoryLevel" + mLastMemoryLevel 12697 + " mLastNumProcesses" + mLastNumProcesses); 12698 long now = SystemClock.uptimeMillis(); 12699 pw.print(" mLastIdleTime="); 12700 TimeUtils.formatDuration(now, mLastIdleTime, pw); 12701 pw.print(" mLowRamSinceLastIdle="); 12702 TimeUtils.formatDuration(getLowRamTimeSinceIdle(now), pw); 12703 pw.println(); 12704 } 12705 } 12706 12707 if (!printedAnything) { 12708 pw.println(" (nothing)"); 12709 } 12710 } 12711 12712 boolean dumpProcessesToGc(FileDescriptor fd, PrintWriter pw, String[] args, 12713 int opti, boolean needSep, boolean dumpAll, String dumpPackage) { 12714 if (mProcessesToGc.size() > 0) { 12715 boolean printed = false; 12716 long now = SystemClock.uptimeMillis(); 12717 for (int i=0; i<mProcessesToGc.size(); i++) { 12718 ProcessRecord proc = mProcessesToGc.get(i); 12719 if (dumpPackage != null && !dumpPackage.equals(proc.info.packageName)) { 12720 continue; 12721 } 12722 if (!printed) { 12723 if (needSep) pw.println(); 12724 needSep = true; 12725 pw.println(" Processes that are waiting to GC:"); 12726 printed = true; 12727 } 12728 pw.print(" Process "); pw.println(proc); 12729 pw.print(" lowMem="); pw.print(proc.reportLowMemory); 12730 pw.print(", last gced="); 12731 pw.print(now-proc.lastRequestedGc); 12732 pw.print(" ms ago, last lowMem="); 12733 pw.print(now-proc.lastLowMemory); 12734 pw.println(" ms ago"); 12735 12736 } 12737 } 12738 return needSep; 12739 } 12740 12741 void printOomLevel(PrintWriter pw, String name, int adj) { 12742 pw.print(" "); 12743 if (adj >= 0) { 12744 pw.print(' '); 12745 if (adj < 10) pw.print(' '); 12746 } else { 12747 if (adj > -10) pw.print(' '); 12748 } 12749 pw.print(adj); 12750 pw.print(": "); 12751 pw.print(name); 12752 pw.print(" ("); 12753 pw.print(mProcessList.getMemLevel(adj)/1024); 12754 pw.println(" kB)"); 12755 } 12756 12757 boolean dumpOomLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12758 int opti, boolean dumpAll) { 12759 boolean needSep = false; 12760 12761 if (mLruProcesses.size() > 0) { 12762 if (needSep) pw.println(); 12763 needSep = true; 12764 pw.println(" OOM levels:"); 12765 printOomLevel(pw, "SYSTEM_ADJ", ProcessList.SYSTEM_ADJ); 12766 printOomLevel(pw, "PERSISTENT_PROC_ADJ", ProcessList.PERSISTENT_PROC_ADJ); 12767 printOomLevel(pw, "FOREGROUND_APP_ADJ", ProcessList.FOREGROUND_APP_ADJ); 12768 printOomLevel(pw, "VISIBLE_APP_ADJ", ProcessList.VISIBLE_APP_ADJ); 12769 printOomLevel(pw, "PERCEPTIBLE_APP_ADJ", ProcessList.PERCEPTIBLE_APP_ADJ); 12770 printOomLevel(pw, "BACKUP_APP_ADJ", ProcessList.BACKUP_APP_ADJ); 12771 printOomLevel(pw, "HEAVY_WEIGHT_APP_ADJ", ProcessList.HEAVY_WEIGHT_APP_ADJ); 12772 printOomLevel(pw, "SERVICE_ADJ", ProcessList.SERVICE_ADJ); 12773 printOomLevel(pw, "HOME_APP_ADJ", ProcessList.HOME_APP_ADJ); 12774 printOomLevel(pw, "PREVIOUS_APP_ADJ", ProcessList.PREVIOUS_APP_ADJ); 12775 printOomLevel(pw, "SERVICE_B_ADJ", ProcessList.SERVICE_B_ADJ); 12776 printOomLevel(pw, "CACHED_APP_MIN_ADJ", ProcessList.CACHED_APP_MIN_ADJ); 12777 printOomLevel(pw, "CACHED_APP_MAX_ADJ", ProcessList.CACHED_APP_MAX_ADJ); 12778 12779 if (needSep) pw.println(); 12780 pw.print(" Process OOM control ("); pw.print(mLruProcesses.size()); 12781 pw.print(" total, non-act at "); 12782 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 12783 pw.print(", non-svc at "); 12784 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 12785 pw.println("):"); 12786 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", true, null); 12787 needSep = true; 12788 } 12789 12790 dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, null); 12791 12792 pw.println(); 12793 pw.println(" mHomeProcess: " + mHomeProcess); 12794 pw.println(" mPreviousProcess: " + mPreviousProcess); 12795 if (mHeavyWeightProcess != null) { 12796 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 12797 } 12798 12799 return true; 12800 } 12801 12802 /** 12803 * There are three ways to call this: 12804 * - no provider specified: dump all the providers 12805 * - a flattened component name that matched an existing provider was specified as the 12806 * first arg: dump that one provider 12807 * - the first arg isn't the flattened component name of an existing provider: 12808 * dump all providers whose component contains the first arg as a substring 12809 */ 12810 protected boolean dumpProvider(FileDescriptor fd, PrintWriter pw, String name, String[] args, 12811 int opti, boolean dumpAll) { 12812 return mProviderMap.dumpProvider(fd, pw, name, args, opti, dumpAll); 12813 } 12814 12815 static class ItemMatcher { 12816 ArrayList<ComponentName> components; 12817 ArrayList<String> strings; 12818 ArrayList<Integer> objects; 12819 boolean all; 12820 12821 ItemMatcher() { 12822 all = true; 12823 } 12824 12825 void build(String name) { 12826 ComponentName componentName = ComponentName.unflattenFromString(name); 12827 if (componentName != null) { 12828 if (components == null) { 12829 components = new ArrayList<ComponentName>(); 12830 } 12831 components.add(componentName); 12832 all = false; 12833 } else { 12834 int objectId = 0; 12835 // Not a '/' separated full component name; maybe an object ID? 12836 try { 12837 objectId = Integer.parseInt(name, 16); 12838 if (objects == null) { 12839 objects = new ArrayList<Integer>(); 12840 } 12841 objects.add(objectId); 12842 all = false; 12843 } catch (RuntimeException e) { 12844 // Not an integer; just do string match. 12845 if (strings == null) { 12846 strings = new ArrayList<String>(); 12847 } 12848 strings.add(name); 12849 all = false; 12850 } 12851 } 12852 } 12853 12854 int build(String[] args, int opti) { 12855 for (; opti<args.length; opti++) { 12856 String name = args[opti]; 12857 if ("--".equals(name)) { 12858 return opti+1; 12859 } 12860 build(name); 12861 } 12862 return opti; 12863 } 12864 12865 boolean match(Object object, ComponentName comp) { 12866 if (all) { 12867 return true; 12868 } 12869 if (components != null) { 12870 for (int i=0; i<components.size(); i++) { 12871 if (components.get(i).equals(comp)) { 12872 return true; 12873 } 12874 } 12875 } 12876 if (objects != null) { 12877 for (int i=0; i<objects.size(); i++) { 12878 if (System.identityHashCode(object) == objects.get(i)) { 12879 return true; 12880 } 12881 } 12882 } 12883 if (strings != null) { 12884 String flat = comp.flattenToString(); 12885 for (int i=0; i<strings.size(); i++) { 12886 if (flat.contains(strings.get(i))) { 12887 return true; 12888 } 12889 } 12890 } 12891 return false; 12892 } 12893 } 12894 12895 /** 12896 * There are three things that cmd can be: 12897 * - a flattened component name that matches an existing activity 12898 * - the cmd arg isn't the flattened component name of an existing activity: 12899 * dump all activity whose component contains the cmd as a substring 12900 * - A hex number of the ActivityRecord object instance. 12901 */ 12902 protected boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name, String[] args, 12903 int opti, boolean dumpAll) { 12904 ArrayList<ActivityRecord> activities; 12905 12906 synchronized (this) { 12907 activities = mStackSupervisor.getDumpActivitiesLocked(name); 12908 } 12909 12910 if (activities.size() <= 0) { 12911 return false; 12912 } 12913 12914 String[] newArgs = new String[args.length - opti]; 12915 System.arraycopy(args, opti, newArgs, 0, args.length - opti); 12916 12917 TaskRecord lastTask = null; 12918 boolean needSep = false; 12919 for (int i=activities.size()-1; i>=0; i--) { 12920 ActivityRecord r = activities.get(i); 12921 if (needSep) { 12922 pw.println(); 12923 } 12924 needSep = true; 12925 synchronized (this) { 12926 if (lastTask != r.task) { 12927 lastTask = r.task; 12928 pw.print("TASK "); pw.print(lastTask.affinity); 12929 pw.print(" id="); pw.println(lastTask.taskId); 12930 if (dumpAll) { 12931 lastTask.dump(pw, " "); 12932 } 12933 } 12934 } 12935 dumpActivity(" ", fd, pw, activities.get(i), newArgs, dumpAll); 12936 } 12937 return true; 12938 } 12939 12940 /** 12941 * Invokes IApplicationThread.dumpActivity() on the thread of the specified activity if 12942 * there is a thread associated with the activity. 12943 */ 12944 private void dumpActivity(String prefix, FileDescriptor fd, PrintWriter pw, 12945 final ActivityRecord r, String[] args, boolean dumpAll) { 12946 String innerPrefix = prefix + " "; 12947 synchronized (this) { 12948 pw.print(prefix); pw.print("ACTIVITY "); pw.print(r.shortComponentName); 12949 pw.print(" "); pw.print(Integer.toHexString(System.identityHashCode(r))); 12950 pw.print(" pid="); 12951 if (r.app != null) pw.println(r.app.pid); 12952 else pw.println("(not running)"); 12953 if (dumpAll) { 12954 r.dump(pw, innerPrefix); 12955 } 12956 } 12957 if (r.app != null && r.app.thread != null) { 12958 // flush anything that is already in the PrintWriter since the thread is going 12959 // to write to the file descriptor directly 12960 pw.flush(); 12961 try { 12962 TransferPipe tp = new TransferPipe(); 12963 try { 12964 r.app.thread.dumpActivity(tp.getWriteFd().getFileDescriptor(), 12965 r.appToken, innerPrefix, args); 12966 tp.go(fd); 12967 } finally { 12968 tp.kill(); 12969 } 12970 } catch (IOException e) { 12971 pw.println(innerPrefix + "Failure while dumping the activity: " + e); 12972 } catch (RemoteException e) { 12973 pw.println(innerPrefix + "Got a RemoteException while dumping the activity"); 12974 } 12975 } 12976 } 12977 12978 void dumpBroadcastsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12979 int opti, boolean dumpAll, String dumpPackage) { 12980 boolean needSep = false; 12981 boolean onlyHistory = false; 12982 boolean printedAnything = false; 12983 12984 if ("history".equals(dumpPackage)) { 12985 if (opti < args.length && "-s".equals(args[opti])) { 12986 dumpAll = false; 12987 } 12988 onlyHistory = true; 12989 dumpPackage = null; 12990 } 12991 12992 pw.println("ACTIVITY MANAGER BROADCAST STATE (dumpsys activity broadcasts)"); 12993 if (!onlyHistory && dumpAll) { 12994 if (mRegisteredReceivers.size() > 0) { 12995 boolean printed = false; 12996 Iterator it = mRegisteredReceivers.values().iterator(); 12997 while (it.hasNext()) { 12998 ReceiverList r = (ReceiverList)it.next(); 12999 if (dumpPackage != null && (r.app == null || 13000 !dumpPackage.equals(r.app.info.packageName))) { 13001 continue; 13002 } 13003 if (!printed) { 13004 pw.println(" Registered Receivers:"); 13005 needSep = true; 13006 printed = true; 13007 printedAnything = true; 13008 } 13009 pw.print(" * "); pw.println(r); 13010 r.dump(pw, " "); 13011 } 13012 } 13013 13014 if (mReceiverResolver.dump(pw, needSep ? 13015 "\n Receiver Resolver Table:" : " Receiver Resolver Table:", 13016 " ", dumpPackage, false)) { 13017 needSep = true; 13018 printedAnything = true; 13019 } 13020 } 13021 13022 for (BroadcastQueue q : mBroadcastQueues) { 13023 needSep = q.dumpLocked(fd, pw, args, opti, dumpAll, dumpPackage, needSep); 13024 printedAnything |= needSep; 13025 } 13026 13027 needSep = true; 13028 13029 if (!onlyHistory && mStickyBroadcasts != null && dumpPackage == null) { 13030 for (int user=0; user<mStickyBroadcasts.size(); user++) { 13031 if (needSep) { 13032 pw.println(); 13033 } 13034 needSep = true; 13035 printedAnything = true; 13036 pw.print(" Sticky broadcasts for user "); 13037 pw.print(mStickyBroadcasts.keyAt(user)); pw.println(":"); 13038 StringBuilder sb = new StringBuilder(128); 13039 for (Map.Entry<String, ArrayList<Intent>> ent 13040 : mStickyBroadcasts.valueAt(user).entrySet()) { 13041 pw.print(" * Sticky action "); pw.print(ent.getKey()); 13042 if (dumpAll) { 13043 pw.println(":"); 13044 ArrayList<Intent> intents = ent.getValue(); 13045 final int N = intents.size(); 13046 for (int i=0; i<N; i++) { 13047 sb.setLength(0); 13048 sb.append(" Intent: "); 13049 intents.get(i).toShortString(sb, false, true, false, false); 13050 pw.println(sb.toString()); 13051 Bundle bundle = intents.get(i).getExtras(); 13052 if (bundle != null) { 13053 pw.print(" "); 13054 pw.println(bundle.toString()); 13055 } 13056 } 13057 } else { 13058 pw.println(""); 13059 } 13060 } 13061 } 13062 } 13063 13064 if (!onlyHistory && dumpAll) { 13065 pw.println(); 13066 for (BroadcastQueue queue : mBroadcastQueues) { 13067 pw.println(" mBroadcastsScheduled [" + queue.mQueueName + "]=" 13068 + queue.mBroadcastsScheduled); 13069 } 13070 pw.println(" mHandler:"); 13071 mHandler.dump(new PrintWriterPrinter(pw), " "); 13072 needSep = true; 13073 printedAnything = true; 13074 } 13075 13076 if (!printedAnything) { 13077 pw.println(" (nothing)"); 13078 } 13079 } 13080 13081 void dumpProvidersLocked(FileDescriptor fd, PrintWriter pw, String[] args, 13082 int opti, boolean dumpAll, String dumpPackage) { 13083 boolean needSep; 13084 boolean printedAnything = false; 13085 13086 ItemMatcher matcher = new ItemMatcher(); 13087 matcher.build(args, opti); 13088 13089 pw.println("ACTIVITY MANAGER CONTENT PROVIDERS (dumpsys activity providers)"); 13090 13091 needSep = mProviderMap.dumpProvidersLocked(pw, dumpAll, dumpPackage); 13092 printedAnything |= needSep; 13093 13094 if (mLaunchingProviders.size() > 0) { 13095 boolean printed = false; 13096 for (int i=mLaunchingProviders.size()-1; i>=0; i--) { 13097 ContentProviderRecord r = mLaunchingProviders.get(i); 13098 if (dumpPackage != null && !dumpPackage.equals(r.name.getPackageName())) { 13099 continue; 13100 } 13101 if (!printed) { 13102 if (needSep) pw.println(); 13103 needSep = true; 13104 pw.println(" Launching content providers:"); 13105 printed = true; 13106 printedAnything = true; 13107 } 13108 pw.print(" Launching #"); pw.print(i); pw.print(": "); 13109 pw.println(r); 13110 } 13111 } 13112 13113 if (mGrantedUriPermissions.size() > 0) { 13114 boolean printed = false; 13115 int dumpUid = -2; 13116 if (dumpPackage != null) { 13117 try { 13118 dumpUid = mContext.getPackageManager().getPackageUid(dumpPackage, 0); 13119 } catch (NameNotFoundException e) { 13120 dumpUid = -1; 13121 } 13122 } 13123 for (int i=0; i<mGrantedUriPermissions.size(); i++) { 13124 int uid = mGrantedUriPermissions.keyAt(i); 13125 if (dumpUid >= -1 && UserHandle.getAppId(uid) != dumpUid) { 13126 continue; 13127 } 13128 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 13129 if (!printed) { 13130 if (needSep) pw.println(); 13131 needSep = true; 13132 pw.println(" Granted Uri Permissions:"); 13133 printed = true; 13134 printedAnything = true; 13135 } 13136 pw.print(" * UID "); pw.print(uid); pw.println(" holds:"); 13137 for (UriPermission perm : perms.values()) { 13138 pw.print(" "); pw.println(perm); 13139 if (dumpAll) { 13140 perm.dump(pw, " "); 13141 } 13142 } 13143 } 13144 } 13145 13146 if (!printedAnything) { 13147 pw.println(" (nothing)"); 13148 } 13149 } 13150 13151 void dumpPendingIntentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 13152 int opti, boolean dumpAll, String dumpPackage) { 13153 boolean printed = false; 13154 13155 pw.println("ACTIVITY MANAGER PENDING INTENTS (dumpsys activity intents)"); 13156 13157 if (mIntentSenderRecords.size() > 0) { 13158 Iterator<WeakReference<PendingIntentRecord>> it 13159 = mIntentSenderRecords.values().iterator(); 13160 while (it.hasNext()) { 13161 WeakReference<PendingIntentRecord> ref = it.next(); 13162 PendingIntentRecord rec = ref != null ? ref.get(): null; 13163 if (dumpPackage != null && (rec == null 13164 || !dumpPackage.equals(rec.key.packageName))) { 13165 continue; 13166 } 13167 printed = true; 13168 if (rec != null) { 13169 pw.print(" * "); pw.println(rec); 13170 if (dumpAll) { 13171 rec.dump(pw, " "); 13172 } 13173 } else { 13174 pw.print(" * "); pw.println(ref); 13175 } 13176 } 13177 } 13178 13179 if (!printed) { 13180 pw.println(" (nothing)"); 13181 } 13182 } 13183 13184 private static final int dumpProcessList(PrintWriter pw, 13185 ActivityManagerService service, List list, 13186 String prefix, String normalLabel, String persistentLabel, 13187 String dumpPackage) { 13188 int numPers = 0; 13189 final int N = list.size()-1; 13190 for (int i=N; i>=0; i--) { 13191 ProcessRecord r = (ProcessRecord)list.get(i); 13192 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 13193 continue; 13194 } 13195 pw.println(String.format("%s%s #%2d: %s", 13196 prefix, (r.persistent ? persistentLabel : normalLabel), 13197 i, r.toString())); 13198 if (r.persistent) { 13199 numPers++; 13200 } 13201 } 13202 return numPers; 13203 } 13204 13205 private static final boolean dumpProcessOomList(PrintWriter pw, 13206 ActivityManagerService service, List<ProcessRecord> origList, 13207 String prefix, String normalLabel, String persistentLabel, 13208 boolean inclDetails, String dumpPackage) { 13209 13210 ArrayList<Pair<ProcessRecord, Integer>> list 13211 = new ArrayList<Pair<ProcessRecord, Integer>>(origList.size()); 13212 for (int i=0; i<origList.size(); i++) { 13213 ProcessRecord r = origList.get(i); 13214 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 13215 continue; 13216 } 13217 list.add(new Pair<ProcessRecord, Integer>(origList.get(i), i)); 13218 } 13219 13220 if (list.size() <= 0) { 13221 return false; 13222 } 13223 13224 Comparator<Pair<ProcessRecord, Integer>> comparator 13225 = new Comparator<Pair<ProcessRecord, Integer>>() { 13226 @Override 13227 public int compare(Pair<ProcessRecord, Integer> object1, 13228 Pair<ProcessRecord, Integer> object2) { 13229 if (object1.first.setAdj != object2.first.setAdj) { 13230 return object1.first.setAdj > object2.first.setAdj ? -1 : 1; 13231 } 13232 if (object1.second.intValue() != object2.second.intValue()) { 13233 return object1.second.intValue() > object2.second.intValue() ? -1 : 1; 13234 } 13235 return 0; 13236 } 13237 }; 13238 13239 Collections.sort(list, comparator); 13240 13241 final long curRealtime = SystemClock.elapsedRealtime(); 13242 final long realtimeSince = curRealtime - service.mLastPowerCheckRealtime; 13243 final long curUptime = SystemClock.uptimeMillis(); 13244 final long uptimeSince = curUptime - service.mLastPowerCheckUptime; 13245 13246 for (int i=list.size()-1; i>=0; i--) { 13247 ProcessRecord r = list.get(i).first; 13248 String oomAdj = ProcessList.makeOomAdjString(r.setAdj); 13249 char schedGroup; 13250 switch (r.setSchedGroup) { 13251 case Process.THREAD_GROUP_BG_NONINTERACTIVE: 13252 schedGroup = 'B'; 13253 break; 13254 case Process.THREAD_GROUP_DEFAULT: 13255 schedGroup = 'F'; 13256 break; 13257 default: 13258 schedGroup = '?'; 13259 break; 13260 } 13261 char foreground; 13262 if (r.foregroundActivities) { 13263 foreground = 'A'; 13264 } else if (r.foregroundServices) { 13265 foreground = 'S'; 13266 } else { 13267 foreground = ' '; 13268 } 13269 String procState = ProcessList.makeProcStateString(r.curProcState); 13270 pw.print(prefix); 13271 pw.print(r.persistent ? persistentLabel : normalLabel); 13272 pw.print(" #"); 13273 int num = (origList.size()-1)-list.get(i).second; 13274 if (num < 10) pw.print(' '); 13275 pw.print(num); 13276 pw.print(": "); 13277 pw.print(oomAdj); 13278 pw.print(' '); 13279 pw.print(schedGroup); 13280 pw.print('/'); 13281 pw.print(foreground); 13282 pw.print('/'); 13283 pw.print(procState); 13284 pw.print(" trm:"); 13285 if (r.trimMemoryLevel < 10) pw.print(' '); 13286 pw.print(r.trimMemoryLevel); 13287 pw.print(' '); 13288 pw.print(r.toShortString()); 13289 pw.print(" ("); 13290 pw.print(r.adjType); 13291 pw.println(')'); 13292 if (r.adjSource != null || r.adjTarget != null) { 13293 pw.print(prefix); 13294 pw.print(" "); 13295 if (r.adjTarget instanceof ComponentName) { 13296 pw.print(((ComponentName)r.adjTarget).flattenToShortString()); 13297 } else if (r.adjTarget != null) { 13298 pw.print(r.adjTarget.toString()); 13299 } else { 13300 pw.print("{null}"); 13301 } 13302 pw.print("<="); 13303 if (r.adjSource instanceof ProcessRecord) { 13304 pw.print("Proc{"); 13305 pw.print(((ProcessRecord)r.adjSource).toShortString()); 13306 pw.println("}"); 13307 } else if (r.adjSource != null) { 13308 pw.println(r.adjSource.toString()); 13309 } else { 13310 pw.println("{null}"); 13311 } 13312 } 13313 if (inclDetails) { 13314 pw.print(prefix); 13315 pw.print(" "); 13316 pw.print("oom: max="); pw.print(r.maxAdj); 13317 pw.print(" curRaw="); pw.print(r.curRawAdj); 13318 pw.print(" setRaw="); pw.print(r.setRawAdj); 13319 pw.print(" cur="); pw.print(r.curAdj); 13320 pw.print(" set="); pw.println(r.setAdj); 13321 pw.print(prefix); 13322 pw.print(" "); 13323 pw.print("state: cur="); pw.print(ProcessList.makeProcStateString(r.curProcState)); 13324 pw.print(" set="); pw.print(ProcessList.makeProcStateString(r.setProcState)); 13325 pw.print(" lastPss="); pw.print(r.lastPss); 13326 pw.print(" lastCachedPss="); pw.println(r.lastCachedPss); 13327 pw.print(prefix); 13328 pw.print(" "); 13329 pw.print("cached="); pw.print(r.cached); 13330 pw.print(" empty="); pw.print(r.empty); 13331 pw.print(" hasAboveClient="); pw.println(r.hasAboveClient); 13332 13333 if (r.setProcState >= ActivityManager.PROCESS_STATE_SERVICE) { 13334 if (r.lastWakeTime != 0) { 13335 long wtime; 13336 BatteryStatsImpl stats = service.mBatteryStatsService.getActiveStatistics(); 13337 synchronized (stats) { 13338 wtime = stats.getProcessWakeTime(r.info.uid, 13339 r.pid, curRealtime); 13340 } 13341 long timeUsed = wtime - r.lastWakeTime; 13342 pw.print(prefix); 13343 pw.print(" "); 13344 pw.print("keep awake over "); 13345 TimeUtils.formatDuration(realtimeSince, pw); 13346 pw.print(" used "); 13347 TimeUtils.formatDuration(timeUsed, pw); 13348 pw.print(" ("); 13349 pw.print((timeUsed*100)/realtimeSince); 13350 pw.println("%)"); 13351 } 13352 if (r.lastCpuTime != 0) { 13353 long timeUsed = r.curCpuTime - r.lastCpuTime; 13354 pw.print(prefix); 13355 pw.print(" "); 13356 pw.print("run cpu over "); 13357 TimeUtils.formatDuration(uptimeSince, pw); 13358 pw.print(" used "); 13359 TimeUtils.formatDuration(timeUsed, pw); 13360 pw.print(" ("); 13361 pw.print((timeUsed*100)/uptimeSince); 13362 pw.println("%)"); 13363 } 13364 } 13365 } 13366 } 13367 return true; 13368 } 13369 13370 ArrayList<ProcessRecord> collectProcesses(PrintWriter pw, int start, String[] args) { 13371 ArrayList<ProcessRecord> procs; 13372 synchronized (this) { 13373 if (args != null && args.length > start 13374 && args[start].charAt(0) != '-') { 13375 procs = new ArrayList<ProcessRecord>(); 13376 int pid = -1; 13377 try { 13378 pid = Integer.parseInt(args[start]); 13379 } catch (NumberFormatException e) { 13380 } 13381 for (int i=mLruProcesses.size()-1; i>=0; i--) { 13382 ProcessRecord proc = mLruProcesses.get(i); 13383 if (proc.pid == pid) { 13384 procs.add(proc); 13385 } else if (proc.processName.equals(args[start])) { 13386 procs.add(proc); 13387 } 13388 } 13389 if (procs.size() <= 0) { 13390 return null; 13391 } 13392 } else { 13393 procs = new ArrayList<ProcessRecord>(mLruProcesses); 13394 } 13395 } 13396 return procs; 13397 } 13398 13399 final void dumpGraphicsHardwareUsage(FileDescriptor fd, 13400 PrintWriter pw, String[] args) { 13401 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 13402 if (procs == null) { 13403 pw.println("No process found for: " + args[0]); 13404 return; 13405 } 13406 13407 long uptime = SystemClock.uptimeMillis(); 13408 long realtime = SystemClock.elapsedRealtime(); 13409 pw.println("Applications Graphics Acceleration Info:"); 13410 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 13411 13412 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 13413 ProcessRecord r = procs.get(i); 13414 if (r.thread != null) { 13415 pw.println("\n** Graphics info for pid " + r.pid + " [" + r.processName + "] **"); 13416 pw.flush(); 13417 try { 13418 TransferPipe tp = new TransferPipe(); 13419 try { 13420 r.thread.dumpGfxInfo(tp.getWriteFd().getFileDescriptor(), args); 13421 tp.go(fd); 13422 } finally { 13423 tp.kill(); 13424 } 13425 } catch (IOException e) { 13426 pw.println("Failure while dumping the app: " + r); 13427 pw.flush(); 13428 } catch (RemoteException e) { 13429 pw.println("Got a RemoteException while dumping the app " + r); 13430 pw.flush(); 13431 } 13432 } 13433 } 13434 } 13435 13436 final void dumpDbInfo(FileDescriptor fd, PrintWriter pw, String[] args) { 13437 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 13438 if (procs == null) { 13439 pw.println("No process found for: " + args[0]); 13440 return; 13441 } 13442 13443 pw.println("Applications Database Info:"); 13444 13445 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 13446 ProcessRecord r = procs.get(i); 13447 if (r.thread != null) { 13448 pw.println("\n** Database info for pid " + r.pid + " [" + r.processName + "] **"); 13449 pw.flush(); 13450 try { 13451 TransferPipe tp = new TransferPipe(); 13452 try { 13453 r.thread.dumpDbInfo(tp.getWriteFd().getFileDescriptor(), args); 13454 tp.go(fd); 13455 } finally { 13456 tp.kill(); 13457 } 13458 } catch (IOException e) { 13459 pw.println("Failure while dumping the app: " + r); 13460 pw.flush(); 13461 } catch (RemoteException e) { 13462 pw.println("Got a RemoteException while dumping the app " + r); 13463 pw.flush(); 13464 } 13465 } 13466 } 13467 } 13468 13469 final static class MemItem { 13470 final boolean isProc; 13471 final String label; 13472 final String shortLabel; 13473 final long pss; 13474 final int id; 13475 final boolean hasActivities; 13476 ArrayList<MemItem> subitems; 13477 13478 public MemItem(String _label, String _shortLabel, long _pss, int _id, 13479 boolean _hasActivities) { 13480 isProc = true; 13481 label = _label; 13482 shortLabel = _shortLabel; 13483 pss = _pss; 13484 id = _id; 13485 hasActivities = _hasActivities; 13486 } 13487 13488 public MemItem(String _label, String _shortLabel, long _pss, int _id) { 13489 isProc = false; 13490 label = _label; 13491 shortLabel = _shortLabel; 13492 pss = _pss; 13493 id = _id; 13494 hasActivities = false; 13495 } 13496 } 13497 13498 static final void dumpMemItems(PrintWriter pw, String prefix, String tag, 13499 ArrayList<MemItem> items, boolean sort, boolean isCompact) { 13500 if (sort && !isCompact) { 13501 Collections.sort(items, new Comparator<MemItem>() { 13502 @Override 13503 public int compare(MemItem lhs, MemItem rhs) { 13504 if (lhs.pss < rhs.pss) { 13505 return 1; 13506 } else if (lhs.pss > rhs.pss) { 13507 return -1; 13508 } 13509 return 0; 13510 } 13511 }); 13512 } 13513 13514 for (int i=0; i<items.size(); i++) { 13515 MemItem mi = items.get(i); 13516 if (!isCompact) { 13517 pw.print(prefix); pw.printf("%7d kB: ", mi.pss); pw.println(mi.label); 13518 } else if (mi.isProc) { 13519 pw.print("proc,"); pw.print(tag); pw.print(","); pw.print(mi.shortLabel); 13520 pw.print(","); pw.print(mi.id); pw.print(","); pw.print(mi.pss); 13521 pw.println(mi.hasActivities ? ",a" : ",e"); 13522 } else { 13523 pw.print(tag); pw.print(","); pw.print(mi.shortLabel); pw.print(","); 13524 pw.println(mi.pss); 13525 } 13526 if (mi.subitems != null) { 13527 dumpMemItems(pw, prefix + " ", mi.shortLabel, mi.subitems, 13528 true, isCompact); 13529 } 13530 } 13531 } 13532 13533 // These are in KB. 13534 static final long[] DUMP_MEM_BUCKETS = new long[] { 13535 5*1024, 7*1024, 10*1024, 15*1024, 20*1024, 30*1024, 40*1024, 80*1024, 13536 120*1024, 160*1024, 200*1024, 13537 250*1024, 300*1024, 350*1024, 400*1024, 500*1024, 600*1024, 800*1024, 13538 1*1024*1024, 2*1024*1024, 5*1024*1024, 10*1024*1024, 20*1024*1024 13539 }; 13540 13541 static final void appendMemBucket(StringBuilder out, long memKB, String label, 13542 boolean stackLike) { 13543 int start = label.lastIndexOf('.'); 13544 if (start >= 0) start++; 13545 else start = 0; 13546 int end = label.length(); 13547 for (int i=0; i<DUMP_MEM_BUCKETS.length; i++) { 13548 if (DUMP_MEM_BUCKETS[i] >= memKB) { 13549 long bucket = DUMP_MEM_BUCKETS[i]/1024; 13550 out.append(bucket); 13551 out.append(stackLike ? "MB." : "MB "); 13552 out.append(label, start, end); 13553 return; 13554 } 13555 } 13556 out.append(memKB/1024); 13557 out.append(stackLike ? "MB." : "MB "); 13558 out.append(label, start, end); 13559 } 13560 13561 static final int[] DUMP_MEM_OOM_ADJ = new int[] { 13562 ProcessList.NATIVE_ADJ, 13563 ProcessList.SYSTEM_ADJ, ProcessList.PERSISTENT_PROC_ADJ, ProcessList.FOREGROUND_APP_ADJ, 13564 ProcessList.VISIBLE_APP_ADJ, ProcessList.PERCEPTIBLE_APP_ADJ, 13565 ProcessList.BACKUP_APP_ADJ, ProcessList.HEAVY_WEIGHT_APP_ADJ, 13566 ProcessList.SERVICE_ADJ, ProcessList.HOME_APP_ADJ, 13567 ProcessList.PREVIOUS_APP_ADJ, ProcessList.SERVICE_B_ADJ, ProcessList.CACHED_APP_MAX_ADJ 13568 }; 13569 static final String[] DUMP_MEM_OOM_LABEL = new String[] { 13570 "Native", 13571 "System", "Persistent", "Foreground", 13572 "Visible", "Perceptible", 13573 "Heavy Weight", "Backup", 13574 "A Services", "Home", 13575 "Previous", "B Services", "Cached" 13576 }; 13577 static final String[] DUMP_MEM_OOM_COMPACT_LABEL = new String[] { 13578 "native", 13579 "sys", "pers", "fore", 13580 "vis", "percept", 13581 "heavy", "backup", 13582 "servicea", "home", 13583 "prev", "serviceb", "cached" 13584 }; 13585 13586 private final void dumpApplicationMemoryUsageHeader(PrintWriter pw, long uptime, 13587 long realtime, boolean isCheckinRequest, boolean isCompact) { 13588 if (isCheckinRequest || isCompact) { 13589 // short checkin version 13590 pw.print("time,"); pw.print(uptime); pw.print(","); pw.println(realtime); 13591 } else { 13592 pw.println("Applications Memory Usage (kB):"); 13593 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 13594 } 13595 } 13596 13597 final void dumpApplicationMemoryUsage(FileDescriptor fd, 13598 PrintWriter pw, String prefix, String[] args, boolean brief, PrintWriter categoryPw) { 13599 boolean dumpDetails = false; 13600 boolean dumpFullDetails = false; 13601 boolean dumpDalvik = false; 13602 boolean oomOnly = false; 13603 boolean isCompact = false; 13604 boolean localOnly = false; 13605 13606 int opti = 0; 13607 while (opti < args.length) { 13608 String opt = args[opti]; 13609 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 13610 break; 13611 } 13612 opti++; 13613 if ("-a".equals(opt)) { 13614 dumpDetails = true; 13615 dumpFullDetails = true; 13616 dumpDalvik = true; 13617 } else if ("-d".equals(opt)) { 13618 dumpDalvik = true; 13619 } else if ("-c".equals(opt)) { 13620 isCompact = true; 13621 } else if ("--oom".equals(opt)) { 13622 oomOnly = true; 13623 } else if ("--local".equals(opt)) { 13624 localOnly = true; 13625 } else if ("-h".equals(opt)) { 13626 pw.println("meminfo dump options: [-a] [-d] [-c] [--oom] [process]"); 13627 pw.println(" -a: include all available information for each process."); 13628 pw.println(" -d: include dalvik details when dumping process details."); 13629 pw.println(" -c: dump in a compact machine-parseable representation."); 13630 pw.println(" --oom: only show processes organized by oom adj."); 13631 pw.println(" --local: only collect details locally, don't call process."); 13632 pw.println("If [process] is specified it can be the name or "); 13633 pw.println("pid of a specific process to dump."); 13634 return; 13635 } else { 13636 pw.println("Unknown argument: " + opt + "; use -h for help"); 13637 } 13638 } 13639 13640 final boolean isCheckinRequest = scanArgs(args, "--checkin"); 13641 long uptime = SystemClock.uptimeMillis(); 13642 long realtime = SystemClock.elapsedRealtime(); 13643 final long[] tmpLong = new long[1]; 13644 13645 ArrayList<ProcessRecord> procs = collectProcesses(pw, opti, args); 13646 if (procs == null) { 13647 // No Java processes. Maybe they want to print a native process. 13648 if (args != null && args.length > opti 13649 && args[opti].charAt(0) != '-') { 13650 ArrayList<ProcessCpuTracker.Stats> nativeProcs 13651 = new ArrayList<ProcessCpuTracker.Stats>(); 13652 updateCpuStatsNow(); 13653 int findPid = -1; 13654 try { 13655 findPid = Integer.parseInt(args[opti]); 13656 } catch (NumberFormatException e) { 13657 } 13658 synchronized (mProcessCpuThread) { 13659 final int N = mProcessCpuTracker.countStats(); 13660 for (int i=0; i<N; i++) { 13661 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 13662 if (st.pid == findPid || (st.baseName != null 13663 && st.baseName.equals(args[opti]))) { 13664 nativeProcs.add(st); 13665 } 13666 } 13667 } 13668 if (nativeProcs.size() > 0) { 13669 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, 13670 isCompact); 13671 Debug.MemoryInfo mi = null; 13672 for (int i = nativeProcs.size() - 1 ; i >= 0 ; i--) { 13673 final ProcessCpuTracker.Stats r = nativeProcs.get(i); 13674 final int pid = r.pid; 13675 if (!isCheckinRequest && dumpDetails) { 13676 pw.println("\n** MEMINFO in pid " + pid + " [" + r.baseName + "] **"); 13677 } 13678 if (mi == null) { 13679 mi = new Debug.MemoryInfo(); 13680 } 13681 if (dumpDetails || (!brief && !oomOnly)) { 13682 Debug.getMemoryInfo(pid, mi); 13683 } else { 13684 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 13685 mi.dalvikPrivateDirty = (int)tmpLong[0]; 13686 } 13687 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 13688 dumpDalvik, pid, r.baseName, 0, 0, 0, 0, 0, 0); 13689 if (isCheckinRequest) { 13690 pw.println(); 13691 } 13692 } 13693 return; 13694 } 13695 } 13696 pw.println("No process found for: " + args[opti]); 13697 return; 13698 } 13699 13700 if (!brief && !oomOnly && (procs.size() == 1 || isCheckinRequest)) { 13701 dumpDetails = true; 13702 } 13703 13704 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, isCompact); 13705 13706 String[] innerArgs = new String[args.length-opti]; 13707 System.arraycopy(args, opti, innerArgs, 0, args.length-opti); 13708 13709 ArrayList<MemItem> procMems = new ArrayList<MemItem>(); 13710 final SparseArray<MemItem> procMemsMap = new SparseArray<MemItem>(); 13711 long nativePss=0, dalvikPss=0, otherPss=0; 13712 long[] miscPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 13713 13714 long oomPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 13715 ArrayList<MemItem>[] oomProcs = (ArrayList<MemItem>[]) 13716 new ArrayList[DUMP_MEM_OOM_LABEL.length]; 13717 13718 long totalPss = 0; 13719 long cachedPss = 0; 13720 13721 Debug.MemoryInfo mi = null; 13722 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 13723 final ProcessRecord r = procs.get(i); 13724 final IApplicationThread thread; 13725 final int pid; 13726 final int oomAdj; 13727 final boolean hasActivities; 13728 synchronized (this) { 13729 thread = r.thread; 13730 pid = r.pid; 13731 oomAdj = r.getSetAdjWithServices(); 13732 hasActivities = r.activities.size() > 0; 13733 } 13734 if (thread != null) { 13735 if (!isCheckinRequest && dumpDetails) { 13736 pw.println("\n** MEMINFO in pid " + pid + " [" + r.processName + "] **"); 13737 } 13738 if (mi == null) { 13739 mi = new Debug.MemoryInfo(); 13740 } 13741 if (dumpDetails || (!brief && !oomOnly)) { 13742 Debug.getMemoryInfo(pid, mi); 13743 } else { 13744 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 13745 mi.dalvikPrivateDirty = (int)tmpLong[0]; 13746 } 13747 if (dumpDetails) { 13748 if (localOnly) { 13749 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 13750 dumpDalvik, pid, r.processName, 0, 0, 0, 0, 0, 0); 13751 if (isCheckinRequest) { 13752 pw.println(); 13753 } 13754 } else { 13755 try { 13756 pw.flush(); 13757 thread.dumpMemInfo(fd, mi, isCheckinRequest, dumpFullDetails, 13758 dumpDalvik, innerArgs); 13759 } catch (RemoteException e) { 13760 if (!isCheckinRequest) { 13761 pw.println("Got RemoteException!"); 13762 pw.flush(); 13763 } 13764 } 13765 } 13766 } 13767 13768 final long myTotalPss = mi.getTotalPss(); 13769 final long myTotalUss = mi.getTotalUss(); 13770 13771 synchronized (this) { 13772 if (r.thread != null && oomAdj == r.getSetAdjWithServices()) { 13773 // Record this for posterity if the process has been stable. 13774 r.baseProcessTracker.addPss(myTotalPss, myTotalUss, true, r.pkgList); 13775 } 13776 } 13777 13778 if (!isCheckinRequest && mi != null) { 13779 totalPss += myTotalPss; 13780 MemItem pssItem = new MemItem(r.processName + " (pid " + pid + 13781 (hasActivities ? " / activities)" : ")"), 13782 r.processName, myTotalPss, pid, hasActivities); 13783 procMems.add(pssItem); 13784 procMemsMap.put(pid, pssItem); 13785 13786 nativePss += mi.nativePss; 13787 dalvikPss += mi.dalvikPss; 13788 otherPss += mi.otherPss; 13789 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 13790 long mem = mi.getOtherPss(j); 13791 miscPss[j] += mem; 13792 otherPss -= mem; 13793 } 13794 13795 if (oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 13796 cachedPss += myTotalPss; 13797 } 13798 13799 for (int oomIndex=0; oomIndex<oomPss.length; oomIndex++) { 13800 if (oomAdj <= DUMP_MEM_OOM_ADJ[oomIndex] 13801 || oomIndex == (oomPss.length-1)) { 13802 oomPss[oomIndex] += myTotalPss; 13803 if (oomProcs[oomIndex] == null) { 13804 oomProcs[oomIndex] = new ArrayList<MemItem>(); 13805 } 13806 oomProcs[oomIndex].add(pssItem); 13807 break; 13808 } 13809 } 13810 } 13811 } 13812 } 13813 13814 long nativeProcTotalPss = 0; 13815 13816 if (!isCheckinRequest && procs.size() > 1) { 13817 // If we are showing aggregations, also look for native processes to 13818 // include so that our aggregations are more accurate. 13819 updateCpuStatsNow(); 13820 synchronized (mProcessCpuThread) { 13821 final int N = mProcessCpuTracker.countStats(); 13822 for (int i=0; i<N; i++) { 13823 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 13824 if (st.vsize > 0 && procMemsMap.indexOfKey(st.pid) < 0) { 13825 if (mi == null) { 13826 mi = new Debug.MemoryInfo(); 13827 } 13828 if (!brief && !oomOnly) { 13829 Debug.getMemoryInfo(st.pid, mi); 13830 } else { 13831 mi.nativePss = (int)Debug.getPss(st.pid, tmpLong); 13832 mi.nativePrivateDirty = (int)tmpLong[0]; 13833 } 13834 13835 final long myTotalPss = mi.getTotalPss(); 13836 totalPss += myTotalPss; 13837 nativeProcTotalPss += myTotalPss; 13838 13839 MemItem pssItem = new MemItem(st.name + " (pid " + st.pid + ")", 13840 st.name, myTotalPss, st.pid, false); 13841 procMems.add(pssItem); 13842 13843 nativePss += mi.nativePss; 13844 dalvikPss += mi.dalvikPss; 13845 otherPss += mi.otherPss; 13846 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 13847 long mem = mi.getOtherPss(j); 13848 miscPss[j] += mem; 13849 otherPss -= mem; 13850 } 13851 oomPss[0] += myTotalPss; 13852 if (oomProcs[0] == null) { 13853 oomProcs[0] = new ArrayList<MemItem>(); 13854 } 13855 oomProcs[0].add(pssItem); 13856 } 13857 } 13858 } 13859 13860 ArrayList<MemItem> catMems = new ArrayList<MemItem>(); 13861 13862 catMems.add(new MemItem("Native", "Native", nativePss, -1)); 13863 catMems.add(new MemItem("Dalvik", "Dalvik", dalvikPss, -2)); 13864 catMems.add(new MemItem("Unknown", "Unknown", otherPss, -3)); 13865 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 13866 String label = Debug.MemoryInfo.getOtherLabel(j); 13867 catMems.add(new MemItem(label, label, miscPss[j], j)); 13868 } 13869 13870 ArrayList<MemItem> oomMems = new ArrayList<MemItem>(); 13871 for (int j=0; j<oomPss.length; j++) { 13872 if (oomPss[j] != 0) { 13873 String label = isCompact ? DUMP_MEM_OOM_COMPACT_LABEL[j] 13874 : DUMP_MEM_OOM_LABEL[j]; 13875 MemItem item = new MemItem(label, label, oomPss[j], 13876 DUMP_MEM_OOM_ADJ[j]); 13877 item.subitems = oomProcs[j]; 13878 oomMems.add(item); 13879 } 13880 } 13881 13882 if (!brief && !oomOnly && !isCompact) { 13883 pw.println(); 13884 pw.println("Total PSS by process:"); 13885 dumpMemItems(pw, " ", "proc", procMems, true, isCompact); 13886 pw.println(); 13887 } 13888 if (!isCompact) { 13889 pw.println("Total PSS by OOM adjustment:"); 13890 } 13891 dumpMemItems(pw, " ", "oom", oomMems, false, isCompact); 13892 if (!brief && !oomOnly) { 13893 PrintWriter out = categoryPw != null ? categoryPw : pw; 13894 if (!isCompact) { 13895 out.println(); 13896 out.println("Total PSS by category:"); 13897 } 13898 dumpMemItems(out, " ", "cat", catMems, true, isCompact); 13899 } 13900 if (!isCompact) { 13901 pw.println(); 13902 } 13903 MemInfoReader memInfo = new MemInfoReader(); 13904 memInfo.readMemInfo(); 13905 if (nativeProcTotalPss > 0) { 13906 synchronized (this) { 13907 mProcessStats.addSysMemUsageLocked(memInfo.getCachedSizeKb(), 13908 memInfo.getFreeSizeKb(), memInfo.getZramTotalSizeKb(), 13909 memInfo.getBuffersSizeKb()+memInfo.getShmemSizeKb()+memInfo.getSlabSizeKb(), 13910 nativeProcTotalPss); 13911 } 13912 } 13913 if (!brief) { 13914 if (!isCompact) { 13915 pw.print("Total RAM: "); pw.print(memInfo.getTotalSizeKb()); 13916 pw.print(" kB (status "); 13917 switch (mLastMemoryLevel) { 13918 case ProcessStats.ADJ_MEM_FACTOR_NORMAL: 13919 pw.println("normal)"); 13920 break; 13921 case ProcessStats.ADJ_MEM_FACTOR_MODERATE: 13922 pw.println("moderate)"); 13923 break; 13924 case ProcessStats.ADJ_MEM_FACTOR_LOW: 13925 pw.println("low)"); 13926 break; 13927 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 13928 pw.println("critical)"); 13929 break; 13930 default: 13931 pw.print(mLastMemoryLevel); 13932 pw.println(")"); 13933 break; 13934 } 13935 pw.print(" Free RAM: "); pw.print(cachedPss + memInfo.getCachedSizeKb() 13936 + memInfo.getFreeSizeKb()); pw.print(" kB ("); 13937 pw.print(cachedPss); pw.print(" cached pss + "); 13938 pw.print(memInfo.getCachedSizeKb()); pw.print(" cached + "); 13939 pw.print(memInfo.getFreeSizeKb()); pw.println(" free)"); 13940 } else { 13941 pw.print("ram,"); pw.print(memInfo.getTotalSizeKb()); pw.print(","); 13942 pw.print(cachedPss + memInfo.getCachedSizeKb() 13943 + memInfo.getFreeSizeKb()); pw.print(","); 13944 pw.println(totalPss - cachedPss); 13945 } 13946 } 13947 if (!isCompact) { 13948 pw.print(" Used RAM: "); pw.print(totalPss - cachedPss 13949 + memInfo.getBuffersSizeKb() + memInfo.getShmemSizeKb() 13950 + memInfo.getSlabSizeKb()); pw.print(" kB ("); 13951 pw.print(totalPss - cachedPss); pw.print(" used pss + "); 13952 pw.print(memInfo.getBuffersSizeKb()); pw.print(" buffers + "); 13953 pw.print(memInfo.getShmemSizeKb()); pw.print(" shmem + "); 13954 pw.print(memInfo.getSlabSizeKb()); pw.println(" slab)"); 13955 pw.print(" Lost RAM: "); pw.print(memInfo.getTotalSizeKb() 13956 - totalPss - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 13957 - memInfo.getBuffersSizeKb() - memInfo.getShmemSizeKb() 13958 - memInfo.getSlabSizeKb()); pw.println(" kB"); 13959 } 13960 if (!brief) { 13961 if (memInfo.getZramTotalSizeKb() != 0) { 13962 if (!isCompact) { 13963 pw.print(" ZRAM: "); pw.print(memInfo.getZramTotalSizeKb()); 13964 pw.print(" kB physical used for "); 13965 pw.print(memInfo.getSwapTotalSizeKb() 13966 - memInfo.getSwapFreeSizeKb()); 13967 pw.print(" kB in swap ("); 13968 pw.print(memInfo.getSwapTotalSizeKb()); 13969 pw.println(" kB total swap)"); 13970 } else { 13971 pw.print("zram,"); pw.print(memInfo.getZramTotalSizeKb()); pw.print(","); 13972 pw.print(memInfo.getSwapTotalSizeKb()); pw.print(","); 13973 pw.println(memInfo.getSwapFreeSizeKb()); 13974 } 13975 } 13976 final int[] SINGLE_LONG_FORMAT = new int[] { 13977 Process.PROC_SPACE_TERM|Process.PROC_OUT_LONG 13978 }; 13979 long[] longOut = new long[1]; 13980 Process.readProcFile("/sys/kernel/mm/ksm/pages_shared", 13981 SINGLE_LONG_FORMAT, null, longOut, null); 13982 long shared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13983 longOut[0] = 0; 13984 Process.readProcFile("/sys/kernel/mm/ksm/pages_sharing", 13985 SINGLE_LONG_FORMAT, null, longOut, null); 13986 long sharing = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13987 longOut[0] = 0; 13988 Process.readProcFile("/sys/kernel/mm/ksm/pages_unshared", 13989 SINGLE_LONG_FORMAT, null, longOut, null); 13990 long unshared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13991 longOut[0] = 0; 13992 Process.readProcFile("/sys/kernel/mm/ksm/pages_volatile", 13993 SINGLE_LONG_FORMAT, null, longOut, null); 13994 long voltile = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13995 if (!isCompact) { 13996 if (sharing != 0 || shared != 0 || unshared != 0 || voltile != 0) { 13997 pw.print(" KSM: "); pw.print(sharing); 13998 pw.print(" kB saved from shared "); 13999 pw.print(shared); pw.println(" kB"); 14000 pw.print(" "); pw.print(unshared); pw.print(" kB unshared; "); 14001 pw.print(voltile); pw.println(" kB volatile"); 14002 } 14003 pw.print(" Tuning: "); 14004 pw.print(ActivityManager.staticGetMemoryClass()); 14005 pw.print(" (large "); 14006 pw.print(ActivityManager.staticGetLargeMemoryClass()); 14007 pw.print("), oom "); 14008 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 14009 pw.print(" kB"); 14010 pw.print(", restore limit "); 14011 pw.print(mProcessList.getCachedRestoreThresholdKb()); 14012 pw.print(" kB"); 14013 if (ActivityManager.isLowRamDeviceStatic()) { 14014 pw.print(" (low-ram)"); 14015 } 14016 if (ActivityManager.isHighEndGfx()) { 14017 pw.print(" (high-end-gfx)"); 14018 } 14019 pw.println(); 14020 } else { 14021 pw.print("ksm,"); pw.print(sharing); pw.print(","); 14022 pw.print(shared); pw.print(","); pw.print(unshared); pw.print(","); 14023 pw.println(voltile); 14024 pw.print("tuning,"); 14025 pw.print(ActivityManager.staticGetMemoryClass()); 14026 pw.print(','); 14027 pw.print(ActivityManager.staticGetLargeMemoryClass()); 14028 pw.print(','); 14029 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 14030 if (ActivityManager.isLowRamDeviceStatic()) { 14031 pw.print(",low-ram"); 14032 } 14033 if (ActivityManager.isHighEndGfx()) { 14034 pw.print(",high-end-gfx"); 14035 } 14036 pw.println(); 14037 } 14038 } 14039 } 14040 } 14041 14042 /** 14043 * Searches array of arguments for the specified string 14044 * @param args array of argument strings 14045 * @param value value to search for 14046 * @return true if the value is contained in the array 14047 */ 14048 private static boolean scanArgs(String[] args, String value) { 14049 if (args != null) { 14050 for (String arg : args) { 14051 if (value.equals(arg)) { 14052 return true; 14053 } 14054 } 14055 } 14056 return false; 14057 } 14058 14059 private final boolean removeDyingProviderLocked(ProcessRecord proc, 14060 ContentProviderRecord cpr, boolean always) { 14061 final boolean inLaunching = mLaunchingProviders.contains(cpr); 14062 14063 if (!inLaunching || always) { 14064 synchronized (cpr) { 14065 cpr.launchingApp = null; 14066 cpr.notifyAll(); 14067 } 14068 mProviderMap.removeProviderByClass(cpr.name, UserHandle.getUserId(cpr.uid)); 14069 String names[] = cpr.info.authority.split(";"); 14070 for (int j = 0; j < names.length; j++) { 14071 mProviderMap.removeProviderByName(names[j], UserHandle.getUserId(cpr.uid)); 14072 } 14073 } 14074 14075 for (int i=0; i<cpr.connections.size(); i++) { 14076 ContentProviderConnection conn = cpr.connections.get(i); 14077 if (conn.waiting) { 14078 // If this connection is waiting for the provider, then we don't 14079 // need to mess with its process unless we are always removing 14080 // or for some reason the provider is not currently launching. 14081 if (inLaunching && !always) { 14082 continue; 14083 } 14084 } 14085 ProcessRecord capp = conn.client; 14086 conn.dead = true; 14087 if (conn.stableCount > 0) { 14088 if (!capp.persistent && capp.thread != null 14089 && capp.pid != 0 14090 && capp.pid != MY_PID) { 14091 capp.kill("depends on provider " 14092 + cpr.name.flattenToShortString() 14093 + " in dying proc " + (proc != null ? proc.processName : "??"), true); 14094 } 14095 } else if (capp.thread != null && conn.provider.provider != null) { 14096 try { 14097 capp.thread.unstableProviderDied(conn.provider.provider.asBinder()); 14098 } catch (RemoteException e) { 14099 } 14100 // In the protocol here, we don't expect the client to correctly 14101 // clean up this connection, we'll just remove it. 14102 cpr.connections.remove(i); 14103 conn.client.conProviders.remove(conn); 14104 } 14105 } 14106 14107 if (inLaunching && always) { 14108 mLaunchingProviders.remove(cpr); 14109 } 14110 return inLaunching; 14111 } 14112 14113 /** 14114 * Main code for cleaning up a process when it has gone away. This is 14115 * called both as a result of the process dying, or directly when stopping 14116 * a process when running in single process mode. 14117 */ 14118 private final void cleanUpApplicationRecordLocked(ProcessRecord app, 14119 boolean restarting, boolean allowRestart, int index) { 14120 if (index >= 0) { 14121 removeLruProcessLocked(app); 14122 ProcessList.remove(app.pid); 14123 } 14124 14125 mProcessesToGc.remove(app); 14126 mPendingPssProcesses.remove(app); 14127 14128 // Dismiss any open dialogs. 14129 if (app.crashDialog != null && !app.forceCrashReport) { 14130 app.crashDialog.dismiss(); 14131 app.crashDialog = null; 14132 } 14133 if (app.anrDialog != null) { 14134 app.anrDialog.dismiss(); 14135 app.anrDialog = null; 14136 } 14137 if (app.waitDialog != null) { 14138 app.waitDialog.dismiss(); 14139 app.waitDialog = null; 14140 } 14141 14142 app.crashing = false; 14143 app.notResponding = false; 14144 14145 app.resetPackageList(mProcessStats); 14146 app.unlinkDeathRecipient(); 14147 app.makeInactive(mProcessStats); 14148 app.waitingToKill = null; 14149 app.forcingToForeground = null; 14150 updateProcessForegroundLocked(app, false, false); 14151 app.foregroundActivities = false; 14152 app.hasShownUi = false; 14153 app.treatLikeActivity = false; 14154 app.hasAboveClient = false; 14155 app.hasClientActivities = false; 14156 14157 mServices.killServicesLocked(app, allowRestart); 14158 14159 boolean restart = false; 14160 14161 // Remove published content providers. 14162 for (int i=app.pubProviders.size()-1; i>=0; i--) { 14163 ContentProviderRecord cpr = app.pubProviders.valueAt(i); 14164 final boolean always = app.bad || !allowRestart; 14165 if (removeDyingProviderLocked(app, cpr, always) || always) { 14166 // We left the provider in the launching list, need to 14167 // restart it. 14168 restart = true; 14169 } 14170 14171 cpr.provider = null; 14172 cpr.proc = null; 14173 } 14174 app.pubProviders.clear(); 14175 14176 // Take care of any launching providers waiting for this process. 14177 if (checkAppInLaunchingProvidersLocked(app, false)) { 14178 restart = true; 14179 } 14180 14181 // Unregister from connected content providers. 14182 if (!app.conProviders.isEmpty()) { 14183 for (int i=0; i<app.conProviders.size(); i++) { 14184 ContentProviderConnection conn = app.conProviders.get(i); 14185 conn.provider.connections.remove(conn); 14186 } 14187 app.conProviders.clear(); 14188 } 14189 14190 // At this point there may be remaining entries in mLaunchingProviders 14191 // where we were the only one waiting, so they are no longer of use. 14192 // Look for these and clean up if found. 14193 // XXX Commented out for now. Trying to figure out a way to reproduce 14194 // the actual situation to identify what is actually going on. 14195 if (false) { 14196 for (int i=0; i<mLaunchingProviders.size(); i++) { 14197 ContentProviderRecord cpr = (ContentProviderRecord) 14198 mLaunchingProviders.get(i); 14199 if (cpr.connections.size() <= 0 && !cpr.hasExternalProcessHandles()) { 14200 synchronized (cpr) { 14201 cpr.launchingApp = null; 14202 cpr.notifyAll(); 14203 } 14204 } 14205 } 14206 } 14207 14208 skipCurrentReceiverLocked(app); 14209 14210 // Unregister any receivers. 14211 for (int i=app.receivers.size()-1; i>=0; i--) { 14212 removeReceiverLocked(app.receivers.valueAt(i)); 14213 } 14214 app.receivers.clear(); 14215 14216 // If the app is undergoing backup, tell the backup manager about it 14217 if (mBackupTarget != null && app.pid == mBackupTarget.app.pid) { 14218 if (DEBUG_BACKUP || DEBUG_CLEANUP) Slog.d(TAG, "App " 14219 + mBackupTarget.appInfo + " died during backup"); 14220 try { 14221 IBackupManager bm = IBackupManager.Stub.asInterface( 14222 ServiceManager.getService(Context.BACKUP_SERVICE)); 14223 bm.agentDisconnected(app.info.packageName); 14224 } catch (RemoteException e) { 14225 // can't happen; backup manager is local 14226 } 14227 } 14228 14229 for (int i = mPendingProcessChanges.size()-1; i>=0; i--) { 14230 ProcessChangeItem item = mPendingProcessChanges.get(i); 14231 if (item.pid == app.pid) { 14232 mPendingProcessChanges.remove(i); 14233 mAvailProcessChanges.add(item); 14234 } 14235 } 14236 mHandler.obtainMessage(DISPATCH_PROCESS_DIED, app.pid, app.info.uid, null).sendToTarget(); 14237 14238 // If the caller is restarting this app, then leave it in its 14239 // current lists and let the caller take care of it. 14240 if (restarting) { 14241 return; 14242 } 14243 14244 if (!app.persistent || app.isolated) { 14245 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, 14246 "Removing non-persistent process during cleanup: " + app); 14247 mProcessNames.remove(app.processName, app.uid); 14248 mIsolatedProcesses.remove(app.uid); 14249 if (mHeavyWeightProcess == app) { 14250 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 14251 mHeavyWeightProcess.userId, 0)); 14252 mHeavyWeightProcess = null; 14253 } 14254 } else if (!app.removed) { 14255 // This app is persistent, so we need to keep its record around. 14256 // If it is not already on the pending app list, add it there 14257 // and start a new process for it. 14258 if (mPersistentStartingProcesses.indexOf(app) < 0) { 14259 mPersistentStartingProcesses.add(app); 14260 restart = true; 14261 } 14262 } 14263 if ((DEBUG_PROCESSES || DEBUG_CLEANUP) && mProcessesOnHold.contains(app)) Slog.v(TAG, 14264 "Clean-up removing on hold: " + app); 14265 mProcessesOnHold.remove(app); 14266 14267 if (app == mHomeProcess) { 14268 mHomeProcess = null; 14269 } 14270 if (app == mPreviousProcess) { 14271 mPreviousProcess = null; 14272 } 14273 14274 if (restart && !app.isolated) { 14275 // We have components that still need to be running in the 14276 // process, so re-launch it. 14277 mProcessNames.put(app.processName, app.uid, app); 14278 startProcessLocked(app, "restart", app.processName); 14279 } else if (app.pid > 0 && app.pid != MY_PID) { 14280 // Goodbye! 14281 boolean removed; 14282 synchronized (mPidsSelfLocked) { 14283 mPidsSelfLocked.remove(app.pid); 14284 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 14285 } 14286 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 14287 if (app.isolated) { 14288 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 14289 } 14290 app.setPid(0); 14291 } 14292 } 14293 14294 boolean checkAppInLaunchingProvidersLocked(ProcessRecord app, boolean alwaysBad) { 14295 // Look through the content providers we are waiting to have launched, 14296 // and if any run in this process then either schedule a restart of 14297 // the process or kill the client waiting for it if this process has 14298 // gone bad. 14299 int NL = mLaunchingProviders.size(); 14300 boolean restart = false; 14301 for (int i=0; i<NL; i++) { 14302 ContentProviderRecord cpr = mLaunchingProviders.get(i); 14303 if (cpr.launchingApp == app) { 14304 if (!alwaysBad && !app.bad) { 14305 restart = true; 14306 } else { 14307 removeDyingProviderLocked(app, cpr, true); 14308 // cpr should have been removed from mLaunchingProviders 14309 NL = mLaunchingProviders.size(); 14310 i--; 14311 } 14312 } 14313 } 14314 return restart; 14315 } 14316 14317 // ========================================================= 14318 // SERVICES 14319 // ========================================================= 14320 14321 @Override 14322 public List<ActivityManager.RunningServiceInfo> getServices(int maxNum, 14323 int flags) { 14324 enforceNotIsolatedCaller("getServices"); 14325 synchronized (this) { 14326 return mServices.getRunningServiceInfoLocked(maxNum, flags); 14327 } 14328 } 14329 14330 @Override 14331 public PendingIntent getRunningServiceControlPanel(ComponentName name) { 14332 enforceNotIsolatedCaller("getRunningServiceControlPanel"); 14333 synchronized (this) { 14334 return mServices.getRunningServiceControlPanelLocked(name); 14335 } 14336 } 14337 14338 @Override 14339 public ComponentName startService(IApplicationThread caller, Intent service, 14340 String resolvedType, int userId) { 14341 enforceNotIsolatedCaller("startService"); 14342 // Refuse possible leaked file descriptors 14343 if (service != null && service.hasFileDescriptors() == true) { 14344 throw new IllegalArgumentException("File descriptors passed in Intent"); 14345 } 14346 14347 if (DEBUG_SERVICE) 14348 Slog.v(TAG, "startService: " + service + " type=" + resolvedType); 14349 synchronized(this) { 14350 final int callingPid = Binder.getCallingPid(); 14351 final int callingUid = Binder.getCallingUid(); 14352 final long origId = Binder.clearCallingIdentity(); 14353 ComponentName res = mServices.startServiceLocked(caller, service, 14354 resolvedType, callingPid, callingUid, userId); 14355 Binder.restoreCallingIdentity(origId); 14356 return res; 14357 } 14358 } 14359 14360 ComponentName startServiceInPackage(int uid, 14361 Intent service, String resolvedType, int userId) { 14362 synchronized(this) { 14363 if (DEBUG_SERVICE) 14364 Slog.v(TAG, "startServiceInPackage: " + service + " type=" + resolvedType); 14365 final long origId = Binder.clearCallingIdentity(); 14366 ComponentName res = mServices.startServiceLocked(null, service, 14367 resolvedType, -1, uid, userId); 14368 Binder.restoreCallingIdentity(origId); 14369 return res; 14370 } 14371 } 14372 14373 @Override 14374 public int stopService(IApplicationThread caller, Intent service, 14375 String resolvedType, int userId) { 14376 enforceNotIsolatedCaller("stopService"); 14377 // Refuse possible leaked file descriptors 14378 if (service != null && service.hasFileDescriptors() == true) { 14379 throw new IllegalArgumentException("File descriptors passed in Intent"); 14380 } 14381 14382 synchronized(this) { 14383 return mServices.stopServiceLocked(caller, service, resolvedType, userId); 14384 } 14385 } 14386 14387 @Override 14388 public IBinder peekService(Intent service, String resolvedType) { 14389 enforceNotIsolatedCaller("peekService"); 14390 // Refuse possible leaked file descriptors 14391 if (service != null && service.hasFileDescriptors() == true) { 14392 throw new IllegalArgumentException("File descriptors passed in Intent"); 14393 } 14394 synchronized(this) { 14395 return mServices.peekServiceLocked(service, resolvedType); 14396 } 14397 } 14398 14399 @Override 14400 public boolean stopServiceToken(ComponentName className, IBinder token, 14401 int startId) { 14402 synchronized(this) { 14403 return mServices.stopServiceTokenLocked(className, token, startId); 14404 } 14405 } 14406 14407 @Override 14408 public void setServiceForeground(ComponentName className, IBinder token, 14409 int id, Notification notification, boolean removeNotification) { 14410 synchronized(this) { 14411 mServices.setServiceForegroundLocked(className, token, id, notification, 14412 removeNotification); 14413 } 14414 } 14415 14416 @Override 14417 public int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 14418 boolean requireFull, String name, String callerPackage) { 14419 return handleIncomingUser(callingPid, callingUid, userId, allowAll, 14420 requireFull ? ALLOW_FULL_ONLY : ALLOW_NON_FULL, name, callerPackage); 14421 } 14422 14423 int unsafeConvertIncomingUser(int userId) { 14424 return (userId == UserHandle.USER_CURRENT || userId == UserHandle.USER_CURRENT_OR_SELF) 14425 ? mCurrentUserId : userId; 14426 } 14427 14428 int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 14429 int allowMode, String name, String callerPackage) { 14430 final int callingUserId = UserHandle.getUserId(callingUid); 14431 if (callingUserId == userId) { 14432 return userId; 14433 } 14434 14435 // Note that we may be accessing mCurrentUserId outside of a lock... 14436 // shouldn't be a big deal, if this is being called outside 14437 // of a locked context there is intrinsically a race with 14438 // the value the caller will receive and someone else changing it. 14439 // We assume that USER_CURRENT_OR_SELF will use the current user; later 14440 // we will switch to the calling user if access to the current user fails. 14441 int targetUserId = unsafeConvertIncomingUser(userId); 14442 14443 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 14444 final boolean allow; 14445 if (checkComponentPermission(INTERACT_ACROSS_USERS_FULL, callingPid, 14446 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED) { 14447 // If the caller has this permission, they always pass go. And collect $200. 14448 allow = true; 14449 } else if (allowMode == ALLOW_FULL_ONLY) { 14450 // We require full access, sucks to be you. 14451 allow = false; 14452 } else if (checkComponentPermission(INTERACT_ACROSS_USERS, callingPid, 14453 callingUid, -1, true) != PackageManager.PERMISSION_GRANTED) { 14454 // If the caller does not have either permission, they are always doomed. 14455 allow = false; 14456 } else if (allowMode == ALLOW_NON_FULL) { 14457 // We are blanket allowing non-full access, you lucky caller! 14458 allow = true; 14459 } else if (allowMode == ALLOW_NON_FULL_IN_PROFILE) { 14460 // We may or may not allow this depending on whether the two users are 14461 // in the same profile. 14462 synchronized (mUserProfileGroupIdsSelfLocked) { 14463 int callingProfile = mUserProfileGroupIdsSelfLocked.get(callingUserId, 14464 UserInfo.NO_PROFILE_GROUP_ID); 14465 int targetProfile = mUserProfileGroupIdsSelfLocked.get(targetUserId, 14466 UserInfo.NO_PROFILE_GROUP_ID); 14467 allow = callingProfile != UserInfo.NO_PROFILE_GROUP_ID 14468 && callingProfile == targetProfile; 14469 } 14470 } else { 14471 throw new IllegalArgumentException("Unknown mode: " + allowMode); 14472 } 14473 if (!allow) { 14474 if (userId == UserHandle.USER_CURRENT_OR_SELF) { 14475 // In this case, they would like to just execute as their 14476 // owner user instead of failing. 14477 targetUserId = callingUserId; 14478 } else { 14479 StringBuilder builder = new StringBuilder(128); 14480 builder.append("Permission Denial: "); 14481 builder.append(name); 14482 if (callerPackage != null) { 14483 builder.append(" from "); 14484 builder.append(callerPackage); 14485 } 14486 builder.append(" asks to run as user "); 14487 builder.append(userId); 14488 builder.append(" but is calling from user "); 14489 builder.append(UserHandle.getUserId(callingUid)); 14490 builder.append("; this requires "); 14491 builder.append(INTERACT_ACROSS_USERS_FULL); 14492 if (allowMode != ALLOW_FULL_ONLY) { 14493 builder.append(" or "); 14494 builder.append(INTERACT_ACROSS_USERS); 14495 } 14496 String msg = builder.toString(); 14497 Slog.w(TAG, msg); 14498 throw new SecurityException(msg); 14499 } 14500 } 14501 } 14502 if (!allowAll && targetUserId < 0) { 14503 throw new IllegalArgumentException( 14504 "Call does not support special user #" + targetUserId); 14505 } 14506 return targetUserId; 14507 } 14508 14509 boolean isSingleton(String componentProcessName, ApplicationInfo aInfo, 14510 String className, int flags) { 14511 boolean result = false; 14512 // For apps that don't have pre-defined UIDs, check for permission 14513 if (UserHandle.getAppId(aInfo.uid) >= Process.FIRST_APPLICATION_UID) { 14514 if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 14515 if (ActivityManager.checkUidPermission( 14516 INTERACT_ACROSS_USERS, 14517 aInfo.uid) != PackageManager.PERMISSION_GRANTED) { 14518 ComponentName comp = new ComponentName(aInfo.packageName, className); 14519 String msg = "Permission Denial: Component " + comp.flattenToShortString() 14520 + " requests FLAG_SINGLE_USER, but app does not hold " 14521 + INTERACT_ACROSS_USERS; 14522 Slog.w(TAG, msg); 14523 throw new SecurityException(msg); 14524 } 14525 // Permission passed 14526 result = true; 14527 } 14528 } else if ("system".equals(componentProcessName)) { 14529 result = true; 14530 } else if (UserHandle.isSameApp(aInfo.uid, Process.PHONE_UID) 14531 && (flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 14532 // Phone app is allowed to export singleuser providers. 14533 result = true; 14534 } else { 14535 // App with pre-defined UID, check if it's a persistent app 14536 result = (aInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0; 14537 } 14538 if (DEBUG_MU) { 14539 Slog.v(TAG, "isSingleton(" + componentProcessName + ", " + aInfo 14540 + ", " + className + ", 0x" + Integer.toHexString(flags) + ") = " + result); 14541 } 14542 return result; 14543 } 14544 14545 /** 14546 * Checks to see if the caller is in the same app as the singleton 14547 * component, or the component is in a special app. It allows special apps 14548 * to export singleton components but prevents exporting singleton 14549 * components for regular apps. 14550 */ 14551 boolean isValidSingletonCall(int callingUid, int componentUid) { 14552 int componentAppId = UserHandle.getAppId(componentUid); 14553 return UserHandle.isSameApp(callingUid, componentUid) 14554 || componentAppId == Process.SYSTEM_UID 14555 || componentAppId == Process.PHONE_UID 14556 || ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, componentUid) 14557 == PackageManager.PERMISSION_GRANTED; 14558 } 14559 14560 public int bindService(IApplicationThread caller, IBinder token, 14561 Intent service, String resolvedType, 14562 IServiceConnection connection, int flags, int userId) { 14563 enforceNotIsolatedCaller("bindService"); 14564 // Refuse possible leaked file descriptors 14565 if (service != null && service.hasFileDescriptors() == true) { 14566 throw new IllegalArgumentException("File descriptors passed in Intent"); 14567 } 14568 14569 synchronized(this) { 14570 return mServices.bindServiceLocked(caller, token, service, resolvedType, 14571 connection, flags, userId); 14572 } 14573 } 14574 14575 public boolean unbindService(IServiceConnection connection) { 14576 synchronized (this) { 14577 return mServices.unbindServiceLocked(connection); 14578 } 14579 } 14580 14581 public void publishService(IBinder token, Intent intent, IBinder service) { 14582 // Refuse possible leaked file descriptors 14583 if (intent != null && intent.hasFileDescriptors() == true) { 14584 throw new IllegalArgumentException("File descriptors passed in Intent"); 14585 } 14586 14587 synchronized(this) { 14588 if (!(token instanceof ServiceRecord)) { 14589 throw new IllegalArgumentException("Invalid service token"); 14590 } 14591 mServices.publishServiceLocked((ServiceRecord)token, intent, service); 14592 } 14593 } 14594 14595 public void unbindFinished(IBinder token, Intent intent, boolean doRebind) { 14596 // Refuse possible leaked file descriptors 14597 if (intent != null && intent.hasFileDescriptors() == true) { 14598 throw new IllegalArgumentException("File descriptors passed in Intent"); 14599 } 14600 14601 synchronized(this) { 14602 mServices.unbindFinishedLocked((ServiceRecord)token, intent, doRebind); 14603 } 14604 } 14605 14606 public void serviceDoneExecuting(IBinder token, int type, int startId, int res) { 14607 synchronized(this) { 14608 if (!(token instanceof ServiceRecord)) { 14609 throw new IllegalArgumentException("Invalid service token"); 14610 } 14611 mServices.serviceDoneExecutingLocked((ServiceRecord)token, type, startId, res); 14612 } 14613 } 14614 14615 // ========================================================= 14616 // BACKUP AND RESTORE 14617 // ========================================================= 14618 14619 // Cause the target app to be launched if necessary and its backup agent 14620 // instantiated. The backup agent will invoke backupAgentCreated() on the 14621 // activity manager to announce its creation. 14622 public boolean bindBackupAgent(ApplicationInfo app, int backupMode) { 14623 if (DEBUG_BACKUP) Slog.v(TAG, "bindBackupAgent: app=" + app + " mode=" + backupMode); 14624 enforceCallingPermission("android.permission.CONFIRM_FULL_BACKUP", "bindBackupAgent"); 14625 14626 synchronized(this) { 14627 // !!! TODO: currently no check here that we're already bound 14628 BatteryStatsImpl.Uid.Pkg.Serv ss = null; 14629 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 14630 synchronized (stats) { 14631 ss = stats.getServiceStatsLocked(app.uid, app.packageName, app.name); 14632 } 14633 14634 // Backup agent is now in use, its package can't be stopped. 14635 try { 14636 AppGlobals.getPackageManager().setPackageStoppedState( 14637 app.packageName, false, UserHandle.getUserId(app.uid)); 14638 } catch (RemoteException e) { 14639 } catch (IllegalArgumentException e) { 14640 Slog.w(TAG, "Failed trying to unstop package " 14641 + app.packageName + ": " + e); 14642 } 14643 14644 BackupRecord r = new BackupRecord(ss, app, backupMode); 14645 ComponentName hostingName = (backupMode == IApplicationThread.BACKUP_MODE_INCREMENTAL) 14646 ? new ComponentName(app.packageName, app.backupAgentName) 14647 : new ComponentName("android", "FullBackupAgent"); 14648 // startProcessLocked() returns existing proc's record if it's already running 14649 ProcessRecord proc = startProcessLocked(app.processName, app, 14650 false, 0, "backup", hostingName, false, false, false); 14651 if (proc == null) { 14652 Slog.e(TAG, "Unable to start backup agent process " + r); 14653 return false; 14654 } 14655 14656 r.app = proc; 14657 mBackupTarget = r; 14658 mBackupAppName = app.packageName; 14659 14660 // Try not to kill the process during backup 14661 updateOomAdjLocked(proc); 14662 14663 // If the process is already attached, schedule the creation of the backup agent now. 14664 // If it is not yet live, this will be done when it attaches to the framework. 14665 if (proc.thread != null) { 14666 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc already running: " + proc); 14667 try { 14668 proc.thread.scheduleCreateBackupAgent(app, 14669 compatibilityInfoForPackageLocked(app), backupMode); 14670 } catch (RemoteException e) { 14671 // Will time out on the backup manager side 14672 } 14673 } else { 14674 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc not running, waiting for attach"); 14675 } 14676 // Invariants: at this point, the target app process exists and the application 14677 // is either already running or in the process of coming up. mBackupTarget and 14678 // mBackupAppName describe the app, so that when it binds back to the AM we 14679 // know that it's scheduled for a backup-agent operation. 14680 } 14681 14682 return true; 14683 } 14684 14685 @Override 14686 public void clearPendingBackup() { 14687 if (DEBUG_BACKUP) Slog.v(TAG, "clearPendingBackup"); 14688 enforceCallingPermission("android.permission.BACKUP", "clearPendingBackup"); 14689 14690 synchronized (this) { 14691 mBackupTarget = null; 14692 mBackupAppName = null; 14693 } 14694 } 14695 14696 // A backup agent has just come up 14697 public void backupAgentCreated(String agentPackageName, IBinder agent) { 14698 if (DEBUG_BACKUP) Slog.v(TAG, "backupAgentCreated: " + agentPackageName 14699 + " = " + agent); 14700 14701 synchronized(this) { 14702 if (!agentPackageName.equals(mBackupAppName)) { 14703 Slog.e(TAG, "Backup agent created for " + agentPackageName + " but not requested!"); 14704 return; 14705 } 14706 } 14707 14708 long oldIdent = Binder.clearCallingIdentity(); 14709 try { 14710 IBackupManager bm = IBackupManager.Stub.asInterface( 14711 ServiceManager.getService(Context.BACKUP_SERVICE)); 14712 bm.agentConnected(agentPackageName, agent); 14713 } catch (RemoteException e) { 14714 // can't happen; the backup manager service is local 14715 } catch (Exception e) { 14716 Slog.w(TAG, "Exception trying to deliver BackupAgent binding: "); 14717 e.printStackTrace(); 14718 } finally { 14719 Binder.restoreCallingIdentity(oldIdent); 14720 } 14721 } 14722 14723 // done with this agent 14724 public void unbindBackupAgent(ApplicationInfo appInfo) { 14725 if (DEBUG_BACKUP) Slog.v(TAG, "unbindBackupAgent: " + appInfo); 14726 if (appInfo == null) { 14727 Slog.w(TAG, "unbind backup agent for null app"); 14728 return; 14729 } 14730 14731 synchronized(this) { 14732 try { 14733 if (mBackupAppName == null) { 14734 Slog.w(TAG, "Unbinding backup agent with no active backup"); 14735 return; 14736 } 14737 14738 if (!mBackupAppName.equals(appInfo.packageName)) { 14739 Slog.e(TAG, "Unbind of " + appInfo + " but is not the current backup target"); 14740 return; 14741 } 14742 14743 // Not backing this app up any more; reset its OOM adjustment 14744 final ProcessRecord proc = mBackupTarget.app; 14745 updateOomAdjLocked(proc); 14746 14747 // If the app crashed during backup, 'thread' will be null here 14748 if (proc.thread != null) { 14749 try { 14750 proc.thread.scheduleDestroyBackupAgent(appInfo, 14751 compatibilityInfoForPackageLocked(appInfo)); 14752 } catch (Exception e) { 14753 Slog.e(TAG, "Exception when unbinding backup agent:"); 14754 e.printStackTrace(); 14755 } 14756 } 14757 } finally { 14758 mBackupTarget = null; 14759 mBackupAppName = null; 14760 } 14761 } 14762 } 14763 // ========================================================= 14764 // BROADCASTS 14765 // ========================================================= 14766 14767 private final List getStickiesLocked(String action, IntentFilter filter, 14768 List cur, int userId) { 14769 final ContentResolver resolver = mContext.getContentResolver(); 14770 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 14771 if (stickies == null) { 14772 return cur; 14773 } 14774 final ArrayList<Intent> list = stickies.get(action); 14775 if (list == null) { 14776 return cur; 14777 } 14778 int N = list.size(); 14779 for (int i=0; i<N; i++) { 14780 Intent intent = list.get(i); 14781 if (filter.match(resolver, intent, true, TAG) >= 0) { 14782 if (cur == null) { 14783 cur = new ArrayList<Intent>(); 14784 } 14785 cur.add(intent); 14786 } 14787 } 14788 return cur; 14789 } 14790 14791 boolean isPendingBroadcastProcessLocked(int pid) { 14792 return mFgBroadcastQueue.isPendingBroadcastProcessLocked(pid) 14793 || mBgBroadcastQueue.isPendingBroadcastProcessLocked(pid); 14794 } 14795 14796 void skipPendingBroadcastLocked(int pid) { 14797 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 14798 for (BroadcastQueue queue : mBroadcastQueues) { 14799 queue.skipPendingBroadcastLocked(pid); 14800 } 14801 } 14802 14803 // The app just attached; send any pending broadcasts that it should receive 14804 boolean sendPendingBroadcastsLocked(ProcessRecord app) { 14805 boolean didSomething = false; 14806 for (BroadcastQueue queue : mBroadcastQueues) { 14807 didSomething |= queue.sendPendingBroadcastsLocked(app); 14808 } 14809 return didSomething; 14810 } 14811 14812 public Intent registerReceiver(IApplicationThread caller, String callerPackage, 14813 IIntentReceiver receiver, IntentFilter filter, String permission, int userId) { 14814 enforceNotIsolatedCaller("registerReceiver"); 14815 int callingUid; 14816 int callingPid; 14817 synchronized(this) { 14818 ProcessRecord callerApp = null; 14819 if (caller != null) { 14820 callerApp = getRecordForAppLocked(caller); 14821 if (callerApp == null) { 14822 throw new SecurityException( 14823 "Unable to find app for caller " + caller 14824 + " (pid=" + Binder.getCallingPid() 14825 + ") when registering receiver " + receiver); 14826 } 14827 if (callerApp.info.uid != Process.SYSTEM_UID && 14828 !callerApp.pkgList.containsKey(callerPackage) && 14829 !"android".equals(callerPackage)) { 14830 throw new SecurityException("Given caller package " + callerPackage 14831 + " is not running in process " + callerApp); 14832 } 14833 callingUid = callerApp.info.uid; 14834 callingPid = callerApp.pid; 14835 } else { 14836 callerPackage = null; 14837 callingUid = Binder.getCallingUid(); 14838 callingPid = Binder.getCallingPid(); 14839 } 14840 14841 userId = this.handleIncomingUser(callingPid, callingUid, userId, 14842 true, ALLOW_FULL_ONLY, "registerReceiver", callerPackage); 14843 14844 List allSticky = null; 14845 14846 // Look for any matching sticky broadcasts... 14847 Iterator actions = filter.actionsIterator(); 14848 if (actions != null) { 14849 while (actions.hasNext()) { 14850 String action = (String)actions.next(); 14851 allSticky = getStickiesLocked(action, filter, allSticky, 14852 UserHandle.USER_ALL); 14853 allSticky = getStickiesLocked(action, filter, allSticky, 14854 UserHandle.getUserId(callingUid)); 14855 } 14856 } else { 14857 allSticky = getStickiesLocked(null, filter, allSticky, 14858 UserHandle.USER_ALL); 14859 allSticky = getStickiesLocked(null, filter, allSticky, 14860 UserHandle.getUserId(callingUid)); 14861 } 14862 14863 // The first sticky in the list is returned directly back to 14864 // the client. 14865 Intent sticky = allSticky != null ? (Intent)allSticky.get(0) : null; 14866 14867 if (DEBUG_BROADCAST) Slog.v(TAG, "Register receiver " + filter 14868 + ": " + sticky); 14869 14870 if (receiver == null) { 14871 return sticky; 14872 } 14873 14874 ReceiverList rl 14875 = (ReceiverList)mRegisteredReceivers.get(receiver.asBinder()); 14876 if (rl == null) { 14877 rl = new ReceiverList(this, callerApp, callingPid, callingUid, 14878 userId, receiver); 14879 if (rl.app != null) { 14880 rl.app.receivers.add(rl); 14881 } else { 14882 try { 14883 receiver.asBinder().linkToDeath(rl, 0); 14884 } catch (RemoteException e) { 14885 return sticky; 14886 } 14887 rl.linkedToDeath = true; 14888 } 14889 mRegisteredReceivers.put(receiver.asBinder(), rl); 14890 } else if (rl.uid != callingUid) { 14891 throw new IllegalArgumentException( 14892 "Receiver requested to register for uid " + callingUid 14893 + " was previously registered for uid " + rl.uid); 14894 } else if (rl.pid != callingPid) { 14895 throw new IllegalArgumentException( 14896 "Receiver requested to register for pid " + callingPid 14897 + " was previously registered for pid " + rl.pid); 14898 } else if (rl.userId != userId) { 14899 throw new IllegalArgumentException( 14900 "Receiver requested to register for user " + userId 14901 + " was previously registered for user " + rl.userId); 14902 } 14903 BroadcastFilter bf = new BroadcastFilter(filter, rl, callerPackage, 14904 permission, callingUid, userId); 14905 rl.add(bf); 14906 if (!bf.debugCheck()) { 14907 Slog.w(TAG, "==> For Dynamic broadast"); 14908 } 14909 mReceiverResolver.addFilter(bf); 14910 14911 // Enqueue broadcasts for all existing stickies that match 14912 // this filter. 14913 if (allSticky != null) { 14914 ArrayList receivers = new ArrayList(); 14915 receivers.add(bf); 14916 14917 int N = allSticky.size(); 14918 for (int i=0; i<N; i++) { 14919 Intent intent = (Intent)allSticky.get(i); 14920 BroadcastQueue queue = broadcastQueueForIntent(intent); 14921 BroadcastRecord r = new BroadcastRecord(queue, intent, null, 14922 null, -1, -1, null, null, AppOpsManager.OP_NONE, receivers, null, 0, 14923 null, null, false, true, true, -1); 14924 queue.enqueueParallelBroadcastLocked(r); 14925 queue.scheduleBroadcastsLocked(); 14926 } 14927 } 14928 14929 return sticky; 14930 } 14931 } 14932 14933 public void unregisterReceiver(IIntentReceiver receiver) { 14934 if (DEBUG_BROADCAST) Slog.v(TAG, "Unregister receiver: " + receiver); 14935 14936 final long origId = Binder.clearCallingIdentity(); 14937 try { 14938 boolean doTrim = false; 14939 14940 synchronized(this) { 14941 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder()); 14942 if (rl != null) { 14943 if (rl.curBroadcast != null) { 14944 BroadcastRecord r = rl.curBroadcast; 14945 final boolean doNext = finishReceiverLocked( 14946 receiver.asBinder(), r.resultCode, r.resultData, 14947 r.resultExtras, r.resultAbort); 14948 if (doNext) { 14949 doTrim = true; 14950 r.queue.processNextBroadcast(false); 14951 } 14952 } 14953 14954 if (rl.app != null) { 14955 rl.app.receivers.remove(rl); 14956 } 14957 removeReceiverLocked(rl); 14958 if (rl.linkedToDeath) { 14959 rl.linkedToDeath = false; 14960 rl.receiver.asBinder().unlinkToDeath(rl, 0); 14961 } 14962 } 14963 } 14964 14965 // If we actually concluded any broadcasts, we might now be able 14966 // to trim the recipients' apps from our working set 14967 if (doTrim) { 14968 trimApplications(); 14969 return; 14970 } 14971 14972 } finally { 14973 Binder.restoreCallingIdentity(origId); 14974 } 14975 } 14976 14977 void removeReceiverLocked(ReceiverList rl) { 14978 mRegisteredReceivers.remove(rl.receiver.asBinder()); 14979 int N = rl.size(); 14980 for (int i=0; i<N; i++) { 14981 mReceiverResolver.removeFilter(rl.get(i)); 14982 } 14983 } 14984 14985 private final void sendPackageBroadcastLocked(int cmd, String[] packages, int userId) { 14986 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 14987 ProcessRecord r = mLruProcesses.get(i); 14988 if (r.thread != null && (userId == UserHandle.USER_ALL || r.userId == userId)) { 14989 try { 14990 r.thread.dispatchPackageBroadcast(cmd, packages); 14991 } catch (RemoteException ex) { 14992 } 14993 } 14994 } 14995 } 14996 14997 private List<ResolveInfo> collectReceiverComponents(Intent intent, String resolvedType, 14998 int[] users) { 14999 List<ResolveInfo> receivers = null; 15000 try { 15001 HashSet<ComponentName> singleUserReceivers = null; 15002 boolean scannedFirstReceivers = false; 15003 for (int user : users) { 15004 List<ResolveInfo> newReceivers = AppGlobals.getPackageManager() 15005 .queryIntentReceivers(intent, resolvedType, STOCK_PM_FLAGS, user); 15006 if (user != 0 && newReceivers != null) { 15007 // If this is not the primary user, we need to check for 15008 // any receivers that should be filtered out. 15009 for (int i=0; i<newReceivers.size(); i++) { 15010 ResolveInfo ri = newReceivers.get(i); 15011 if ((ri.activityInfo.flags&ActivityInfo.FLAG_PRIMARY_USER_ONLY) != 0) { 15012 newReceivers.remove(i); 15013 i--; 15014 } 15015 } 15016 } 15017 if (newReceivers != null && newReceivers.size() == 0) { 15018 newReceivers = null; 15019 } 15020 if (receivers == null) { 15021 receivers = newReceivers; 15022 } else if (newReceivers != null) { 15023 // We need to concatenate the additional receivers 15024 // found with what we have do far. This would be easy, 15025 // but we also need to de-dup any receivers that are 15026 // singleUser. 15027 if (!scannedFirstReceivers) { 15028 // Collect any single user receivers we had already retrieved. 15029 scannedFirstReceivers = true; 15030 for (int i=0; i<receivers.size(); i++) { 15031 ResolveInfo ri = receivers.get(i); 15032 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 15033 ComponentName cn = new ComponentName( 15034 ri.activityInfo.packageName, ri.activityInfo.name); 15035 if (singleUserReceivers == null) { 15036 singleUserReceivers = new HashSet<ComponentName>(); 15037 } 15038 singleUserReceivers.add(cn); 15039 } 15040 } 15041 } 15042 // Add the new results to the existing results, tracking 15043 // and de-dupping single user receivers. 15044 for (int i=0; i<newReceivers.size(); i++) { 15045 ResolveInfo ri = newReceivers.get(i); 15046 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 15047 ComponentName cn = new ComponentName( 15048 ri.activityInfo.packageName, ri.activityInfo.name); 15049 if (singleUserReceivers == null) { 15050 singleUserReceivers = new HashSet<ComponentName>(); 15051 } 15052 if (!singleUserReceivers.contains(cn)) { 15053 singleUserReceivers.add(cn); 15054 receivers.add(ri); 15055 } 15056 } else { 15057 receivers.add(ri); 15058 } 15059 } 15060 } 15061 } 15062 } catch (RemoteException ex) { 15063 // pm is in same process, this will never happen. 15064 } 15065 return receivers; 15066 } 15067 15068 private final int broadcastIntentLocked(ProcessRecord callerApp, 15069 String callerPackage, Intent intent, String resolvedType, 15070 IIntentReceiver resultTo, int resultCode, String resultData, 15071 Bundle map, String requiredPermission, int appOp, 15072 boolean ordered, boolean sticky, int callingPid, int callingUid, 15073 int userId) { 15074 intent = new Intent(intent); 15075 15076 // By default broadcasts do not go to stopped apps. 15077 intent.addFlags(Intent.FLAG_EXCLUDE_STOPPED_PACKAGES); 15078 15079 if (DEBUG_BROADCAST_LIGHT) Slog.v( 15080 TAG, (sticky ? "Broadcast sticky: ": "Broadcast: ") + intent 15081 + " ordered=" + ordered + " userid=" + userId); 15082 if ((resultTo != null) && !ordered) { 15083 Slog.w(TAG, "Broadcast " + intent + " not ordered but result callback requested!"); 15084 } 15085 15086 userId = handleIncomingUser(callingPid, callingUid, userId, 15087 true, ALLOW_NON_FULL, "broadcast", callerPackage); 15088 15089 // Make sure that the user who is receiving this broadcast is started. 15090 // If not, we will just skip it. 15091 15092 15093 if (userId != UserHandle.USER_ALL && mStartedUsers.get(userId) == null) { 15094 if (callingUid != Process.SYSTEM_UID || (intent.getFlags() 15095 & Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) { 15096 Slog.w(TAG, "Skipping broadcast of " + intent 15097 + ": user " + userId + " is stopped"); 15098 return ActivityManager.BROADCAST_SUCCESS; 15099 } 15100 } 15101 15102 /* 15103 * Prevent non-system code (defined here to be non-persistent 15104 * processes) from sending protected broadcasts. 15105 */ 15106 int callingAppId = UserHandle.getAppId(callingUid); 15107 if (callingAppId == Process.SYSTEM_UID || callingAppId == Process.PHONE_UID 15108 || callingAppId == Process.SHELL_UID || callingAppId == Process.BLUETOOTH_UID 15109 || callingAppId == Process.NFC_UID || callingUid == 0) { 15110 // Always okay. 15111 } else if (callerApp == null || !callerApp.persistent) { 15112 try { 15113 if (AppGlobals.getPackageManager().isProtectedBroadcast( 15114 intent.getAction())) { 15115 String msg = "Permission Denial: not allowed to send broadcast " 15116 + intent.getAction() + " from pid=" 15117 + callingPid + ", uid=" + callingUid; 15118 Slog.w(TAG, msg); 15119 throw new SecurityException(msg); 15120 } else if (AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(intent.getAction())) { 15121 // Special case for compatibility: we don't want apps to send this, 15122 // but historically it has not been protected and apps may be using it 15123 // to poke their own app widget. So, instead of making it protected, 15124 // just limit it to the caller. 15125 if (callerApp == null) { 15126 String msg = "Permission Denial: not allowed to send broadcast " 15127 + intent.getAction() + " from unknown caller."; 15128 Slog.w(TAG, msg); 15129 throw new SecurityException(msg); 15130 } else if (intent.getComponent() != null) { 15131 // They are good enough to send to an explicit component... verify 15132 // it is being sent to the calling app. 15133 if (!intent.getComponent().getPackageName().equals( 15134 callerApp.info.packageName)) { 15135 String msg = "Permission Denial: not allowed to send broadcast " 15136 + intent.getAction() + " to " 15137 + intent.getComponent().getPackageName() + " from " 15138 + callerApp.info.packageName; 15139 Slog.w(TAG, msg); 15140 throw new SecurityException(msg); 15141 } 15142 } else { 15143 // Limit broadcast to their own package. 15144 intent.setPackage(callerApp.info.packageName); 15145 } 15146 } 15147 } catch (RemoteException e) { 15148 Slog.w(TAG, "Remote exception", e); 15149 return ActivityManager.BROADCAST_SUCCESS; 15150 } 15151 } 15152 15153 // Handle special intents: if this broadcast is from the package 15154 // manager about a package being removed, we need to remove all of 15155 // its activities from the history stack. 15156 final boolean uidRemoved = Intent.ACTION_UID_REMOVED.equals( 15157 intent.getAction()); 15158 if (Intent.ACTION_PACKAGE_REMOVED.equals(intent.getAction()) 15159 || Intent.ACTION_PACKAGE_CHANGED.equals(intent.getAction()) 15160 || Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction()) 15161 || Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction()) 15162 || uidRemoved) { 15163 if (checkComponentPermission( 15164 android.Manifest.permission.BROADCAST_PACKAGE_REMOVED, 15165 callingPid, callingUid, -1, true) 15166 == PackageManager.PERMISSION_GRANTED) { 15167 if (uidRemoved) { 15168 final Bundle intentExtras = intent.getExtras(); 15169 final int uid = intentExtras != null 15170 ? intentExtras.getInt(Intent.EXTRA_UID) : -1; 15171 if (uid >= 0) { 15172 BatteryStatsImpl bs = mBatteryStatsService.getActiveStatistics(); 15173 synchronized (bs) { 15174 bs.removeUidStatsLocked(uid); 15175 } 15176 mAppOpsService.uidRemoved(uid); 15177 } 15178 } else { 15179 // If resources are unavailable just force stop all 15180 // those packages and flush the attribute cache as well. 15181 if (Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction())) { 15182 String list[] = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 15183 if (list != null && (list.length > 0)) { 15184 for (String pkg : list) { 15185 forceStopPackageLocked(pkg, -1, false, true, true, false, false, userId, 15186 "storage unmount"); 15187 } 15188 cleanupRecentTasksLocked(UserHandle.USER_ALL); 15189 sendPackageBroadcastLocked( 15190 IApplicationThread.EXTERNAL_STORAGE_UNAVAILABLE, list, userId); 15191 } 15192 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals( 15193 intent.getAction())) { 15194 cleanupRecentTasksLocked(UserHandle.USER_ALL); 15195 } else { 15196 Uri data = intent.getData(); 15197 String ssp; 15198 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 15199 boolean removed = Intent.ACTION_PACKAGE_REMOVED.equals( 15200 intent.getAction()); 15201 boolean fullUninstall = removed && 15202 !intent.getBooleanExtra(Intent.EXTRA_REPLACING, false); 15203 if (!intent.getBooleanExtra(Intent.EXTRA_DONT_KILL_APP, false)) { 15204 forceStopPackageLocked(ssp, UserHandle.getAppId( 15205 intent.getIntExtra(Intent.EXTRA_UID, -1)), false, true, true, 15206 false, fullUninstall, userId, 15207 removed ? "pkg removed" : "pkg changed"); 15208 } 15209 if (removed) { 15210 sendPackageBroadcastLocked(IApplicationThread.PACKAGE_REMOVED, 15211 new String[] {ssp}, userId); 15212 if (!intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)) { 15213 mAppOpsService.packageRemoved( 15214 intent.getIntExtra(Intent.EXTRA_UID, -1), ssp); 15215 15216 // Remove all permissions granted from/to this package 15217 removeUriPermissionsForPackageLocked(ssp, userId, true); 15218 } 15219 } 15220 } 15221 } 15222 } 15223 } else { 15224 String msg = "Permission Denial: " + intent.getAction() 15225 + " broadcast from " + callerPackage + " (pid=" + callingPid 15226 + ", uid=" + callingUid + ")" 15227 + " requires " 15228 + android.Manifest.permission.BROADCAST_PACKAGE_REMOVED; 15229 Slog.w(TAG, msg); 15230 throw new SecurityException(msg); 15231 } 15232 15233 // Special case for adding a package: by default turn on compatibility 15234 // mode. 15235 } else if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction())) { 15236 Uri data = intent.getData(); 15237 String ssp; 15238 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 15239 mCompatModePackages.handlePackageAddedLocked(ssp, 15240 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)); 15241 } 15242 } 15243 15244 /* 15245 * If this is the time zone changed action, queue up a message that will reset the timezone 15246 * of all currently running processes. This message will get queued up before the broadcast 15247 * happens. 15248 */ 15249 if (Intent.ACTION_TIMEZONE_CHANGED.equals(intent.getAction())) { 15250 mHandler.sendEmptyMessage(UPDATE_TIME_ZONE); 15251 } 15252 15253 /* 15254 * If the user set the time, let all running processes know. 15255 */ 15256 if (Intent.ACTION_TIME_CHANGED.equals(intent.getAction())) { 15257 final int is24Hour = intent.getBooleanExtra( 15258 Intent.EXTRA_TIME_PREF_24_HOUR_FORMAT, false) ? 1 : 0; 15259 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_TIME, is24Hour, 0)); 15260 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 15261 synchronized (stats) { 15262 stats.noteCurrentTimeChangedLocked(); 15263 } 15264 } 15265 15266 if (Intent.ACTION_CLEAR_DNS_CACHE.equals(intent.getAction())) { 15267 mHandler.sendEmptyMessage(CLEAR_DNS_CACHE_MSG); 15268 } 15269 15270 if (Proxy.PROXY_CHANGE_ACTION.equals(intent.getAction())) { 15271 ProxyInfo proxy = intent.getParcelableExtra(Proxy.EXTRA_PROXY_INFO); 15272 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_HTTP_PROXY_MSG, proxy)); 15273 } 15274 15275 // Add to the sticky list if requested. 15276 if (sticky) { 15277 if (checkPermission(android.Manifest.permission.BROADCAST_STICKY, 15278 callingPid, callingUid) 15279 != PackageManager.PERMISSION_GRANTED) { 15280 String msg = "Permission Denial: broadcastIntent() requesting a sticky broadcast from pid=" 15281 + callingPid + ", uid=" + callingUid 15282 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 15283 Slog.w(TAG, msg); 15284 throw new SecurityException(msg); 15285 } 15286 if (requiredPermission != null) { 15287 Slog.w(TAG, "Can't broadcast sticky intent " + intent 15288 + " and enforce permission " + requiredPermission); 15289 return ActivityManager.BROADCAST_STICKY_CANT_HAVE_PERMISSION; 15290 } 15291 if (intent.getComponent() != null) { 15292 throw new SecurityException( 15293 "Sticky broadcasts can't target a specific component"); 15294 } 15295 // We use userId directly here, since the "all" target is maintained 15296 // as a separate set of sticky broadcasts. 15297 if (userId != UserHandle.USER_ALL) { 15298 // But first, if this is not a broadcast to all users, then 15299 // make sure it doesn't conflict with an existing broadcast to 15300 // all users. 15301 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get( 15302 UserHandle.USER_ALL); 15303 if (stickies != null) { 15304 ArrayList<Intent> list = stickies.get(intent.getAction()); 15305 if (list != null) { 15306 int N = list.size(); 15307 int i; 15308 for (i=0; i<N; i++) { 15309 if (intent.filterEquals(list.get(i))) { 15310 throw new IllegalArgumentException( 15311 "Sticky broadcast " + intent + " for user " 15312 + userId + " conflicts with existing global broadcast"); 15313 } 15314 } 15315 } 15316 } 15317 } 15318 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 15319 if (stickies == null) { 15320 stickies = new ArrayMap<String, ArrayList<Intent>>(); 15321 mStickyBroadcasts.put(userId, stickies); 15322 } 15323 ArrayList<Intent> list = stickies.get(intent.getAction()); 15324 if (list == null) { 15325 list = new ArrayList<Intent>(); 15326 stickies.put(intent.getAction(), list); 15327 } 15328 int N = list.size(); 15329 int i; 15330 for (i=0; i<N; i++) { 15331 if (intent.filterEquals(list.get(i))) { 15332 // This sticky already exists, replace it. 15333 list.set(i, new Intent(intent)); 15334 break; 15335 } 15336 } 15337 if (i >= N) { 15338 list.add(new Intent(intent)); 15339 } 15340 } 15341 15342 int[] users; 15343 if (userId == UserHandle.USER_ALL) { 15344 // Caller wants broadcast to go to all started users. 15345 users = mStartedUserArray; 15346 } else { 15347 // Caller wants broadcast to go to one specific user. 15348 users = new int[] {userId}; 15349 } 15350 15351 // Figure out who all will receive this broadcast. 15352 List receivers = null; 15353 List<BroadcastFilter> registeredReceivers = null; 15354 // Need to resolve the intent to interested receivers... 15355 if ((intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) 15356 == 0) { 15357 receivers = collectReceiverComponents(intent, resolvedType, users); 15358 } 15359 if (intent.getComponent() == null) { 15360 registeredReceivers = mReceiverResolver.queryIntent(intent, 15361 resolvedType, false, userId); 15362 } 15363 15364 final boolean replacePending = 15365 (intent.getFlags()&Intent.FLAG_RECEIVER_REPLACE_PENDING) != 0; 15366 15367 if (DEBUG_BROADCAST) Slog.v(TAG, "Enqueing broadcast: " + intent.getAction() 15368 + " replacePending=" + replacePending); 15369 15370 int NR = registeredReceivers != null ? registeredReceivers.size() : 0; 15371 if (!ordered && NR > 0) { 15372 // If we are not serializing this broadcast, then send the 15373 // registered receivers separately so they don't wait for the 15374 // components to be launched. 15375 final BroadcastQueue queue = broadcastQueueForIntent(intent); 15376 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 15377 callerPackage, callingPid, callingUid, resolvedType, requiredPermission, 15378 appOp, registeredReceivers, resultTo, resultCode, resultData, map, 15379 ordered, sticky, false, userId); 15380 if (DEBUG_BROADCAST) Slog.v( 15381 TAG, "Enqueueing parallel broadcast " + r); 15382 final boolean replaced = replacePending && queue.replaceParallelBroadcastLocked(r); 15383 if (!replaced) { 15384 queue.enqueueParallelBroadcastLocked(r); 15385 queue.scheduleBroadcastsLocked(); 15386 } 15387 registeredReceivers = null; 15388 NR = 0; 15389 } 15390 15391 // Merge into one list. 15392 int ir = 0; 15393 if (receivers != null) { 15394 // A special case for PACKAGE_ADDED: do not allow the package 15395 // being added to see this broadcast. This prevents them from 15396 // using this as a back door to get run as soon as they are 15397 // installed. Maybe in the future we want to have a special install 15398 // broadcast or such for apps, but we'd like to deliberately make 15399 // this decision. 15400 String skipPackages[] = null; 15401 if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction()) 15402 || Intent.ACTION_PACKAGE_RESTARTED.equals(intent.getAction()) 15403 || Intent.ACTION_PACKAGE_DATA_CLEARED.equals(intent.getAction())) { 15404 Uri data = intent.getData(); 15405 if (data != null) { 15406 String pkgName = data.getSchemeSpecificPart(); 15407 if (pkgName != null) { 15408 skipPackages = new String[] { pkgName }; 15409 } 15410 } 15411 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction())) { 15412 skipPackages = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 15413 } 15414 if (skipPackages != null && (skipPackages.length > 0)) { 15415 for (String skipPackage : skipPackages) { 15416 if (skipPackage != null) { 15417 int NT = receivers.size(); 15418 for (int it=0; it<NT; it++) { 15419 ResolveInfo curt = (ResolveInfo)receivers.get(it); 15420 if (curt.activityInfo.packageName.equals(skipPackage)) { 15421 receivers.remove(it); 15422 it--; 15423 NT--; 15424 } 15425 } 15426 } 15427 } 15428 } 15429 15430 int NT = receivers != null ? receivers.size() : 0; 15431 int it = 0; 15432 ResolveInfo curt = null; 15433 BroadcastFilter curr = null; 15434 while (it < NT && ir < NR) { 15435 if (curt == null) { 15436 curt = (ResolveInfo)receivers.get(it); 15437 } 15438 if (curr == null) { 15439 curr = registeredReceivers.get(ir); 15440 } 15441 if (curr.getPriority() >= curt.priority) { 15442 // Insert this broadcast record into the final list. 15443 receivers.add(it, curr); 15444 ir++; 15445 curr = null; 15446 it++; 15447 NT++; 15448 } else { 15449 // Skip to the next ResolveInfo in the final list. 15450 it++; 15451 curt = null; 15452 } 15453 } 15454 } 15455 while (ir < NR) { 15456 if (receivers == null) { 15457 receivers = new ArrayList(); 15458 } 15459 receivers.add(registeredReceivers.get(ir)); 15460 ir++; 15461 } 15462 15463 if ((receivers != null && receivers.size() > 0) 15464 || resultTo != null) { 15465 BroadcastQueue queue = broadcastQueueForIntent(intent); 15466 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 15467 callerPackage, callingPid, callingUid, resolvedType, 15468 requiredPermission, appOp, receivers, resultTo, resultCode, 15469 resultData, map, ordered, sticky, false, userId); 15470 if (DEBUG_BROADCAST) Slog.v( 15471 TAG, "Enqueueing ordered broadcast " + r 15472 + ": prev had " + queue.mOrderedBroadcasts.size()); 15473 if (DEBUG_BROADCAST) { 15474 int seq = r.intent.getIntExtra("seq", -1); 15475 Slog.i(TAG, "Enqueueing broadcast " + r.intent.getAction() + " seq=" + seq); 15476 } 15477 boolean replaced = replacePending && queue.replaceOrderedBroadcastLocked(r); 15478 if (!replaced) { 15479 queue.enqueueOrderedBroadcastLocked(r); 15480 queue.scheduleBroadcastsLocked(); 15481 } 15482 } 15483 15484 return ActivityManager.BROADCAST_SUCCESS; 15485 } 15486 15487 final Intent verifyBroadcastLocked(Intent intent) { 15488 // Refuse possible leaked file descriptors 15489 if (intent != null && intent.hasFileDescriptors() == true) { 15490 throw new IllegalArgumentException("File descriptors passed in Intent"); 15491 } 15492 15493 int flags = intent.getFlags(); 15494 15495 if (!mProcessesReady) { 15496 // if the caller really truly claims to know what they're doing, go 15497 // ahead and allow the broadcast without launching any receivers 15498 if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT) != 0) { 15499 intent = new Intent(intent); 15500 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 15501 } else if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) { 15502 Slog.e(TAG, "Attempt to launch receivers of broadcast intent " + intent 15503 + " before boot completion"); 15504 throw new IllegalStateException("Cannot broadcast before boot completed"); 15505 } 15506 } 15507 15508 if ((flags&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 15509 throw new IllegalArgumentException( 15510 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 15511 } 15512 15513 return intent; 15514 } 15515 15516 public final int broadcastIntent(IApplicationThread caller, 15517 Intent intent, String resolvedType, IIntentReceiver resultTo, 15518 int resultCode, String resultData, Bundle map, 15519 String requiredPermission, int appOp, boolean serialized, boolean sticky, int userId) { 15520 enforceNotIsolatedCaller("broadcastIntent"); 15521 synchronized(this) { 15522 intent = verifyBroadcastLocked(intent); 15523 15524 final ProcessRecord callerApp = getRecordForAppLocked(caller); 15525 final int callingPid = Binder.getCallingPid(); 15526 final int callingUid = Binder.getCallingUid(); 15527 final long origId = Binder.clearCallingIdentity(); 15528 int res = broadcastIntentLocked(callerApp, 15529 callerApp != null ? callerApp.info.packageName : null, 15530 intent, resolvedType, resultTo, 15531 resultCode, resultData, map, requiredPermission, appOp, serialized, sticky, 15532 callingPid, callingUid, userId); 15533 Binder.restoreCallingIdentity(origId); 15534 return res; 15535 } 15536 } 15537 15538 int broadcastIntentInPackage(String packageName, int uid, 15539 Intent intent, String resolvedType, IIntentReceiver resultTo, 15540 int resultCode, String resultData, Bundle map, 15541 String requiredPermission, boolean serialized, boolean sticky, int userId) { 15542 synchronized(this) { 15543 intent = verifyBroadcastLocked(intent); 15544 15545 final long origId = Binder.clearCallingIdentity(); 15546 int res = broadcastIntentLocked(null, packageName, intent, resolvedType, 15547 resultTo, resultCode, resultData, map, requiredPermission, 15548 AppOpsManager.OP_NONE, serialized, sticky, -1, uid, userId); 15549 Binder.restoreCallingIdentity(origId); 15550 return res; 15551 } 15552 } 15553 15554 public final void unbroadcastIntent(IApplicationThread caller, Intent intent, int userId) { 15555 // Refuse possible leaked file descriptors 15556 if (intent != null && intent.hasFileDescriptors() == true) { 15557 throw new IllegalArgumentException("File descriptors passed in Intent"); 15558 } 15559 15560 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 15561 userId, true, ALLOW_NON_FULL, "removeStickyBroadcast", null); 15562 15563 synchronized(this) { 15564 if (checkCallingPermission(android.Manifest.permission.BROADCAST_STICKY) 15565 != PackageManager.PERMISSION_GRANTED) { 15566 String msg = "Permission Denial: unbroadcastIntent() from pid=" 15567 + Binder.getCallingPid() 15568 + ", uid=" + Binder.getCallingUid() 15569 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 15570 Slog.w(TAG, msg); 15571 throw new SecurityException(msg); 15572 } 15573 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 15574 if (stickies != null) { 15575 ArrayList<Intent> list = stickies.get(intent.getAction()); 15576 if (list != null) { 15577 int N = list.size(); 15578 int i; 15579 for (i=0; i<N; i++) { 15580 if (intent.filterEquals(list.get(i))) { 15581 list.remove(i); 15582 break; 15583 } 15584 } 15585 if (list.size() <= 0) { 15586 stickies.remove(intent.getAction()); 15587 } 15588 } 15589 if (stickies.size() <= 0) { 15590 mStickyBroadcasts.remove(userId); 15591 } 15592 } 15593 } 15594 } 15595 15596 private final boolean finishReceiverLocked(IBinder receiver, int resultCode, 15597 String resultData, Bundle resultExtras, boolean resultAbort) { 15598 final BroadcastRecord r = broadcastRecordForReceiverLocked(receiver); 15599 if (r == null) { 15600 Slog.w(TAG, "finishReceiver called but not found on queue"); 15601 return false; 15602 } 15603 15604 return r.queue.finishReceiverLocked(r, resultCode, resultData, resultExtras, resultAbort, false); 15605 } 15606 15607 void backgroundServicesFinishedLocked(int userId) { 15608 for (BroadcastQueue queue : mBroadcastQueues) { 15609 queue.backgroundServicesFinishedLocked(userId); 15610 } 15611 } 15612 15613 public void finishReceiver(IBinder who, int resultCode, String resultData, 15614 Bundle resultExtras, boolean resultAbort) { 15615 if (DEBUG_BROADCAST) Slog.v(TAG, "Finish receiver: " + who); 15616 15617 // Refuse possible leaked file descriptors 15618 if (resultExtras != null && resultExtras.hasFileDescriptors()) { 15619 throw new IllegalArgumentException("File descriptors passed in Bundle"); 15620 } 15621 15622 final long origId = Binder.clearCallingIdentity(); 15623 try { 15624 boolean doNext = false; 15625 BroadcastRecord r; 15626 15627 synchronized(this) { 15628 r = broadcastRecordForReceiverLocked(who); 15629 if (r != null) { 15630 doNext = r.queue.finishReceiverLocked(r, resultCode, 15631 resultData, resultExtras, resultAbort, true); 15632 } 15633 } 15634 15635 if (doNext) { 15636 r.queue.processNextBroadcast(false); 15637 } 15638 trimApplications(); 15639 } finally { 15640 Binder.restoreCallingIdentity(origId); 15641 } 15642 } 15643 15644 // ========================================================= 15645 // INSTRUMENTATION 15646 // ========================================================= 15647 15648 public boolean startInstrumentation(ComponentName className, 15649 String profileFile, int flags, Bundle arguments, 15650 IInstrumentationWatcher watcher, IUiAutomationConnection uiAutomationConnection, 15651 int userId, String abiOverride) { 15652 enforceNotIsolatedCaller("startInstrumentation"); 15653 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 15654 userId, false, ALLOW_FULL_ONLY, "startInstrumentation", null); 15655 // Refuse possible leaked file descriptors 15656 if (arguments != null && arguments.hasFileDescriptors()) { 15657 throw new IllegalArgumentException("File descriptors passed in Bundle"); 15658 } 15659 15660 synchronized(this) { 15661 InstrumentationInfo ii = null; 15662 ApplicationInfo ai = null; 15663 try { 15664 ii = mContext.getPackageManager().getInstrumentationInfo( 15665 className, STOCK_PM_FLAGS); 15666 ai = AppGlobals.getPackageManager().getApplicationInfo( 15667 ii.targetPackage, STOCK_PM_FLAGS, userId); 15668 } catch (PackageManager.NameNotFoundException e) { 15669 } catch (RemoteException e) { 15670 } 15671 if (ii == null) { 15672 reportStartInstrumentationFailure(watcher, className, 15673 "Unable to find instrumentation info for: " + className); 15674 return false; 15675 } 15676 if (ai == null) { 15677 reportStartInstrumentationFailure(watcher, className, 15678 "Unable to find instrumentation target package: " + ii.targetPackage); 15679 return false; 15680 } 15681 15682 int match = mContext.getPackageManager().checkSignatures( 15683 ii.targetPackage, ii.packageName); 15684 if (match < 0 && match != PackageManager.SIGNATURE_FIRST_NOT_SIGNED) { 15685 String msg = "Permission Denial: starting instrumentation " 15686 + className + " from pid=" 15687 + Binder.getCallingPid() 15688 + ", uid=" + Binder.getCallingPid() 15689 + " not allowed because package " + ii.packageName 15690 + " does not have a signature matching the target " 15691 + ii.targetPackage; 15692 reportStartInstrumentationFailure(watcher, className, msg); 15693 throw new SecurityException(msg); 15694 } 15695 15696 final long origId = Binder.clearCallingIdentity(); 15697 // Instrumentation can kill and relaunch even persistent processes 15698 forceStopPackageLocked(ii.targetPackage, -1, true, false, true, true, false, userId, 15699 "start instr"); 15700 ProcessRecord app = addAppLocked(ai, false, abiOverride); 15701 app.instrumentationClass = className; 15702 app.instrumentationInfo = ai; 15703 app.instrumentationProfileFile = profileFile; 15704 app.instrumentationArguments = arguments; 15705 app.instrumentationWatcher = watcher; 15706 app.instrumentationUiAutomationConnection = uiAutomationConnection; 15707 app.instrumentationResultClass = className; 15708 Binder.restoreCallingIdentity(origId); 15709 } 15710 15711 return true; 15712 } 15713 15714 /** 15715 * Report errors that occur while attempting to start Instrumentation. Always writes the 15716 * error to the logs, but if somebody is watching, send the report there too. This enables 15717 * the "am" command to report errors with more information. 15718 * 15719 * @param watcher The IInstrumentationWatcher. Null if there isn't one. 15720 * @param cn The component name of the instrumentation. 15721 * @param report The error report. 15722 */ 15723 private void reportStartInstrumentationFailure(IInstrumentationWatcher watcher, 15724 ComponentName cn, String report) { 15725 Slog.w(TAG, report); 15726 try { 15727 if (watcher != null) { 15728 Bundle results = new Bundle(); 15729 results.putString(Instrumentation.REPORT_KEY_IDENTIFIER, "ActivityManagerService"); 15730 results.putString("Error", report); 15731 watcher.instrumentationStatus(cn, -1, results); 15732 } 15733 } catch (RemoteException e) { 15734 Slog.w(TAG, e); 15735 } 15736 } 15737 15738 void finishInstrumentationLocked(ProcessRecord app, int resultCode, Bundle results) { 15739 if (app.instrumentationWatcher != null) { 15740 try { 15741 // NOTE: IInstrumentationWatcher *must* be oneway here 15742 app.instrumentationWatcher.instrumentationFinished( 15743 app.instrumentationClass, 15744 resultCode, 15745 results); 15746 } catch (RemoteException e) { 15747 } 15748 } 15749 if (app.instrumentationUiAutomationConnection != null) { 15750 try { 15751 app.instrumentationUiAutomationConnection.shutdown(); 15752 } catch (RemoteException re) { 15753 /* ignore */ 15754 } 15755 // Only a UiAutomation can set this flag and now that 15756 // it is finished we make sure it is reset to its default. 15757 mUserIsMonkey = false; 15758 } 15759 app.instrumentationWatcher = null; 15760 app.instrumentationUiAutomationConnection = null; 15761 app.instrumentationClass = null; 15762 app.instrumentationInfo = null; 15763 app.instrumentationProfileFile = null; 15764 app.instrumentationArguments = null; 15765 15766 forceStopPackageLocked(app.info.packageName, -1, false, false, true, true, false, app.userId, 15767 "finished inst"); 15768 } 15769 15770 public void finishInstrumentation(IApplicationThread target, 15771 int resultCode, Bundle results) { 15772 int userId = UserHandle.getCallingUserId(); 15773 // Refuse possible leaked file descriptors 15774 if (results != null && results.hasFileDescriptors()) { 15775 throw new IllegalArgumentException("File descriptors passed in Intent"); 15776 } 15777 15778 synchronized(this) { 15779 ProcessRecord app = getRecordForAppLocked(target); 15780 if (app == null) { 15781 Slog.w(TAG, "finishInstrumentation: no app for " + target); 15782 return; 15783 } 15784 final long origId = Binder.clearCallingIdentity(); 15785 finishInstrumentationLocked(app, resultCode, results); 15786 Binder.restoreCallingIdentity(origId); 15787 } 15788 } 15789 15790 // ========================================================= 15791 // CONFIGURATION 15792 // ========================================================= 15793 15794 public ConfigurationInfo getDeviceConfigurationInfo() { 15795 ConfigurationInfo config = new ConfigurationInfo(); 15796 synchronized (this) { 15797 config.reqTouchScreen = mConfiguration.touchscreen; 15798 config.reqKeyboardType = mConfiguration.keyboard; 15799 config.reqNavigation = mConfiguration.navigation; 15800 if (mConfiguration.navigation == Configuration.NAVIGATION_DPAD 15801 || mConfiguration.navigation == Configuration.NAVIGATION_TRACKBALL) { 15802 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_FIVE_WAY_NAV; 15803 } 15804 if (mConfiguration.keyboard != Configuration.KEYBOARD_UNDEFINED 15805 && mConfiguration.keyboard != Configuration.KEYBOARD_NOKEYS) { 15806 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_HARD_KEYBOARD; 15807 } 15808 config.reqGlEsVersion = GL_ES_VERSION; 15809 } 15810 return config; 15811 } 15812 15813 ActivityStack getFocusedStack() { 15814 return mStackSupervisor.getFocusedStack(); 15815 } 15816 15817 public Configuration getConfiguration() { 15818 Configuration ci; 15819 synchronized(this) { 15820 ci = new Configuration(mConfiguration); 15821 } 15822 return ci; 15823 } 15824 15825 public void updatePersistentConfiguration(Configuration values) { 15826 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 15827 "updateConfiguration()"); 15828 enforceCallingPermission(android.Manifest.permission.WRITE_SETTINGS, 15829 "updateConfiguration()"); 15830 if (values == null) { 15831 throw new NullPointerException("Configuration must not be null"); 15832 } 15833 15834 synchronized(this) { 15835 final long origId = Binder.clearCallingIdentity(); 15836 updateConfigurationLocked(values, null, true, false); 15837 Binder.restoreCallingIdentity(origId); 15838 } 15839 } 15840 15841 public void updateConfiguration(Configuration values) { 15842 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 15843 "updateConfiguration()"); 15844 15845 synchronized(this) { 15846 if (values == null && mWindowManager != null) { 15847 // sentinel: fetch the current configuration from the window manager 15848 values = mWindowManager.computeNewConfiguration(); 15849 } 15850 15851 if (mWindowManager != null) { 15852 mProcessList.applyDisplaySize(mWindowManager); 15853 } 15854 15855 final long origId = Binder.clearCallingIdentity(); 15856 if (values != null) { 15857 Settings.System.clearConfiguration(values); 15858 } 15859 updateConfigurationLocked(values, null, false, false); 15860 Binder.restoreCallingIdentity(origId); 15861 } 15862 } 15863 15864 /** 15865 * Do either or both things: (1) change the current configuration, and (2) 15866 * make sure the given activity is running with the (now) current 15867 * configuration. Returns true if the activity has been left running, or 15868 * false if <var>starting</var> is being destroyed to match the new 15869 * configuration. 15870 * @param persistent TODO 15871 */ 15872 boolean updateConfigurationLocked(Configuration values, 15873 ActivityRecord starting, boolean persistent, boolean initLocale) { 15874 int changes = 0; 15875 15876 if (values != null) { 15877 Configuration newConfig = new Configuration(mConfiguration); 15878 changes = newConfig.updateFrom(values); 15879 if (changes != 0) { 15880 if (DEBUG_SWITCH || DEBUG_CONFIGURATION) { 15881 Slog.i(TAG, "Updating configuration to: " + values); 15882 } 15883 15884 EventLog.writeEvent(EventLogTags.CONFIGURATION_CHANGED, changes); 15885 15886 if (values.locale != null && !initLocale) { 15887 saveLocaleLocked(values.locale, 15888 !values.locale.equals(mConfiguration.locale), 15889 values.userSetLocale); 15890 } 15891 15892 mConfigurationSeq++; 15893 if (mConfigurationSeq <= 0) { 15894 mConfigurationSeq = 1; 15895 } 15896 newConfig.seq = mConfigurationSeq; 15897 mConfiguration = newConfig; 15898 Slog.i(TAG, "Config changes=" + Integer.toHexString(changes) + " " + newConfig); 15899 //mUsageStatsService.noteStartConfig(newConfig); 15900 15901 final Configuration configCopy = new Configuration(mConfiguration); 15902 15903 // TODO: If our config changes, should we auto dismiss any currently 15904 // showing dialogs? 15905 mShowDialogs = shouldShowDialogs(newConfig); 15906 15907 AttributeCache ac = AttributeCache.instance(); 15908 if (ac != null) { 15909 ac.updateConfiguration(configCopy); 15910 } 15911 15912 // Make sure all resources in our process are updated 15913 // right now, so that anyone who is going to retrieve 15914 // resource values after we return will be sure to get 15915 // the new ones. This is especially important during 15916 // boot, where the first config change needs to guarantee 15917 // all resources have that config before following boot 15918 // code is executed. 15919 mSystemThread.applyConfigurationToResources(configCopy); 15920 15921 if (persistent && Settings.System.hasInterestingConfigurationChanges(changes)) { 15922 Message msg = mHandler.obtainMessage(UPDATE_CONFIGURATION_MSG); 15923 msg.obj = new Configuration(configCopy); 15924 mHandler.sendMessage(msg); 15925 } 15926 15927 for (int i=mLruProcesses.size()-1; i>=0; i--) { 15928 ProcessRecord app = mLruProcesses.get(i); 15929 try { 15930 if (app.thread != null) { 15931 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Sending to proc " 15932 + app.processName + " new config " + mConfiguration); 15933 app.thread.scheduleConfigurationChanged(configCopy); 15934 } 15935 } catch (Exception e) { 15936 } 15937 } 15938 Intent intent = new Intent(Intent.ACTION_CONFIGURATION_CHANGED); 15939 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 15940 | Intent.FLAG_RECEIVER_REPLACE_PENDING 15941 | Intent.FLAG_RECEIVER_FOREGROUND); 15942 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, 15943 null, AppOpsManager.OP_NONE, false, false, MY_PID, 15944 Process.SYSTEM_UID, UserHandle.USER_ALL); 15945 if ((changes&ActivityInfo.CONFIG_LOCALE) != 0) { 15946 intent = new Intent(Intent.ACTION_LOCALE_CHANGED); 15947 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 15948 broadcastIntentLocked(null, null, intent, 15949 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 15950 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 15951 } 15952 } 15953 } 15954 15955 boolean kept = true; 15956 final ActivityStack mainStack = mStackSupervisor.getFocusedStack(); 15957 // mainStack is null during startup. 15958 if (mainStack != null) { 15959 if (changes != 0 && starting == null) { 15960 // If the configuration changed, and the caller is not already 15961 // in the process of starting an activity, then find the top 15962 // activity to check if its configuration needs to change. 15963 starting = mainStack.topRunningActivityLocked(null); 15964 } 15965 15966 if (starting != null) { 15967 kept = mainStack.ensureActivityConfigurationLocked(starting, changes); 15968 // And we need to make sure at this point that all other activities 15969 // are made visible with the correct configuration. 15970 mStackSupervisor.ensureActivitiesVisibleLocked(starting, changes); 15971 } 15972 } 15973 15974 if (values != null && mWindowManager != null) { 15975 mWindowManager.setNewConfiguration(mConfiguration); 15976 } 15977 15978 return kept; 15979 } 15980 15981 /** 15982 * Decide based on the configuration whether we should shouw the ANR, 15983 * crash, etc dialogs. The idea is that if there is no affordnace to 15984 * press the on-screen buttons, we shouldn't show the dialog. 15985 * 15986 * A thought: SystemUI might also want to get told about this, the Power 15987 * dialog / global actions also might want different behaviors. 15988 */ 15989 private static final boolean shouldShowDialogs(Configuration config) { 15990 return !(config.keyboard == Configuration.KEYBOARD_NOKEYS 15991 && config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH); 15992 } 15993 15994 /** 15995 * Save the locale. You must be inside a synchronized (this) block. 15996 */ 15997 private void saveLocaleLocked(Locale l, boolean isDiff, boolean isPersist) { 15998 if(isDiff) { 15999 SystemProperties.set("user.language", l.getLanguage()); 16000 SystemProperties.set("user.region", l.getCountry()); 16001 } 16002 16003 if(isPersist) { 16004 SystemProperties.set("persist.sys.language", l.getLanguage()); 16005 SystemProperties.set("persist.sys.country", l.getCountry()); 16006 SystemProperties.set("persist.sys.localevar", l.getVariant()); 16007 } 16008 } 16009 16010 @Override 16011 public boolean shouldUpRecreateTask(IBinder token, String destAffinity) { 16012 synchronized (this) { 16013 ActivityRecord srec = ActivityRecord.forToken(token); 16014 if (srec.task != null && srec.task.stack != null) { 16015 return srec.task.stack.shouldUpRecreateTaskLocked(srec, destAffinity); 16016 } 16017 } 16018 return false; 16019 } 16020 16021 public boolean navigateUpTo(IBinder token, Intent destIntent, int resultCode, 16022 Intent resultData) { 16023 16024 synchronized (this) { 16025 final ActivityStack stack = ActivityRecord.getStackLocked(token); 16026 if (stack != null) { 16027 return stack.navigateUpToLocked(token, destIntent, resultCode, resultData); 16028 } 16029 return false; 16030 } 16031 } 16032 16033 public int getLaunchedFromUid(IBinder activityToken) { 16034 ActivityRecord srec = ActivityRecord.forToken(activityToken); 16035 if (srec == null) { 16036 return -1; 16037 } 16038 return srec.launchedFromUid; 16039 } 16040 16041 public String getLaunchedFromPackage(IBinder activityToken) { 16042 ActivityRecord srec = ActivityRecord.forToken(activityToken); 16043 if (srec == null) { 16044 return null; 16045 } 16046 return srec.launchedFromPackage; 16047 } 16048 16049 // ========================================================= 16050 // LIFETIME MANAGEMENT 16051 // ========================================================= 16052 16053 // Returns which broadcast queue the app is the current [or imminent] receiver 16054 // on, or 'null' if the app is not an active broadcast recipient. 16055 private BroadcastQueue isReceivingBroadcast(ProcessRecord app) { 16056 BroadcastRecord r = app.curReceiver; 16057 if (r != null) { 16058 return r.queue; 16059 } 16060 16061 // It's not the current receiver, but it might be starting up to become one 16062 synchronized (this) { 16063 for (BroadcastQueue queue : mBroadcastQueues) { 16064 r = queue.mPendingBroadcast; 16065 if (r != null && r.curApp == app) { 16066 // found it; report which queue it's in 16067 return queue; 16068 } 16069 } 16070 } 16071 16072 return null; 16073 } 16074 16075 private final int computeOomAdjLocked(ProcessRecord app, int cachedAdj, ProcessRecord TOP_APP, 16076 boolean doingAll, long now) { 16077 if (mAdjSeq == app.adjSeq) { 16078 // This adjustment has already been computed. 16079 return app.curRawAdj; 16080 } 16081 16082 if (app.thread == null) { 16083 app.adjSeq = mAdjSeq; 16084 app.curSchedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16085 app.curProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16086 return (app.curAdj=app.curRawAdj=ProcessList.CACHED_APP_MAX_ADJ); 16087 } 16088 16089 app.adjTypeCode = ActivityManager.RunningAppProcessInfo.REASON_UNKNOWN; 16090 app.adjSource = null; 16091 app.adjTarget = null; 16092 app.empty = false; 16093 app.cached = false; 16094 16095 final int activitiesSize = app.activities.size(); 16096 16097 if (app.maxAdj <= ProcessList.FOREGROUND_APP_ADJ) { 16098 // The max adjustment doesn't allow this app to be anything 16099 // below foreground, so it is not worth doing work for it. 16100 app.adjType = "fixed"; 16101 app.adjSeq = mAdjSeq; 16102 app.curRawAdj = app.maxAdj; 16103 app.foregroundActivities = false; 16104 app.curSchedGroup = Process.THREAD_GROUP_DEFAULT; 16105 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT; 16106 // System processes can do UI, and when they do we want to have 16107 // them trim their memory after the user leaves the UI. To 16108 // facilitate this, here we need to determine whether or not it 16109 // is currently showing UI. 16110 app.systemNoUi = true; 16111 if (app == TOP_APP) { 16112 app.systemNoUi = false; 16113 } else if (activitiesSize > 0) { 16114 for (int j = 0; j < activitiesSize; j++) { 16115 final ActivityRecord r = app.activities.get(j); 16116 if (r.visible) { 16117 app.systemNoUi = false; 16118 } 16119 } 16120 } 16121 if (!app.systemNoUi) { 16122 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT_UI; 16123 } 16124 return (app.curAdj=app.maxAdj); 16125 } 16126 16127 app.systemNoUi = false; 16128 16129 // Determine the importance of the process, starting with most 16130 // important to least, and assign an appropriate OOM adjustment. 16131 int adj; 16132 int schedGroup; 16133 int procState; 16134 boolean foregroundActivities = false; 16135 BroadcastQueue queue; 16136 if (app == TOP_APP) { 16137 // The last app on the list is the foreground app. 16138 adj = ProcessList.FOREGROUND_APP_ADJ; 16139 schedGroup = Process.THREAD_GROUP_DEFAULT; 16140 app.adjType = "top-activity"; 16141 foregroundActivities = true; 16142 procState = ActivityManager.PROCESS_STATE_TOP; 16143 } else if (app.instrumentationClass != null) { 16144 // Don't want to kill running instrumentation. 16145 adj = ProcessList.FOREGROUND_APP_ADJ; 16146 schedGroup = Process.THREAD_GROUP_DEFAULT; 16147 app.adjType = "instrumentation"; 16148 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16149 } else if ((queue = isReceivingBroadcast(app)) != null) { 16150 // An app that is currently receiving a broadcast also 16151 // counts as being in the foreground for OOM killer purposes. 16152 // It's placed in a sched group based on the nature of the 16153 // broadcast as reflected by which queue it's active in. 16154 adj = ProcessList.FOREGROUND_APP_ADJ; 16155 schedGroup = (queue == mFgBroadcastQueue) 16156 ? Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 16157 app.adjType = "broadcast"; 16158 procState = ActivityManager.PROCESS_STATE_RECEIVER; 16159 } else if (app.executingServices.size() > 0) { 16160 // An app that is currently executing a service callback also 16161 // counts as being in the foreground. 16162 adj = ProcessList.FOREGROUND_APP_ADJ; 16163 schedGroup = app.execServicesFg ? 16164 Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 16165 app.adjType = "exec-service"; 16166 procState = ActivityManager.PROCESS_STATE_SERVICE; 16167 //Slog.i(TAG, "EXEC " + (app.execServicesFg ? "FG" : "BG") + ": " + app); 16168 } else { 16169 // As far as we know the process is empty. We may change our mind later. 16170 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16171 // At this point we don't actually know the adjustment. Use the cached adj 16172 // value that the caller wants us to. 16173 adj = cachedAdj; 16174 procState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16175 app.cached = true; 16176 app.empty = true; 16177 app.adjType = "cch-empty"; 16178 } 16179 16180 // Examine all activities if not already foreground. 16181 if (!foregroundActivities && activitiesSize > 0) { 16182 for (int j = 0; j < activitiesSize; j++) { 16183 final ActivityRecord r = app.activities.get(j); 16184 if (r.app != app) { 16185 Slog.w(TAG, "Wtf, activity " + r + " in proc activity list not using proc " 16186 + app + "?!?"); 16187 continue; 16188 } 16189 if (r.visible) { 16190 // App has a visible activity; only upgrade adjustment. 16191 if (adj > ProcessList.VISIBLE_APP_ADJ) { 16192 adj = ProcessList.VISIBLE_APP_ADJ; 16193 app.adjType = "visible"; 16194 } 16195 if (procState > ActivityManager.PROCESS_STATE_TOP) { 16196 procState = ActivityManager.PROCESS_STATE_TOP; 16197 } 16198 schedGroup = Process.THREAD_GROUP_DEFAULT; 16199 app.cached = false; 16200 app.empty = false; 16201 foregroundActivities = true; 16202 break; 16203 } else if (r.state == ActivityState.PAUSING || r.state == ActivityState.PAUSED) { 16204 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16205 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16206 app.adjType = "pausing"; 16207 } 16208 if (procState > ActivityManager.PROCESS_STATE_TOP) { 16209 procState = ActivityManager.PROCESS_STATE_TOP; 16210 } 16211 schedGroup = Process.THREAD_GROUP_DEFAULT; 16212 app.cached = false; 16213 app.empty = false; 16214 foregroundActivities = true; 16215 } else if (r.state == ActivityState.STOPPING) { 16216 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16217 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16218 app.adjType = "stopping"; 16219 } 16220 // For the process state, we will at this point consider the 16221 // process to be cached. It will be cached either as an activity 16222 // or empty depending on whether the activity is finishing. We do 16223 // this so that we can treat the process as cached for purposes of 16224 // memory trimming (determing current memory level, trim command to 16225 // send to process) since there can be an arbitrary number of stopping 16226 // processes and they should soon all go into the cached state. 16227 if (!r.finishing) { 16228 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 16229 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 16230 } 16231 } 16232 app.cached = false; 16233 app.empty = false; 16234 foregroundActivities = true; 16235 } else { 16236 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 16237 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 16238 app.adjType = "cch-act"; 16239 } 16240 } 16241 } 16242 } 16243 16244 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16245 if (app.foregroundServices) { 16246 // The user is aware of this app, so make it visible. 16247 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16248 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16249 app.cached = false; 16250 app.adjType = "fg-service"; 16251 schedGroup = Process.THREAD_GROUP_DEFAULT; 16252 } else if (app.forcingToForeground != null) { 16253 // The user is aware of this app, so make it visible. 16254 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16255 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16256 app.cached = false; 16257 app.adjType = "force-fg"; 16258 app.adjSource = app.forcingToForeground; 16259 schedGroup = Process.THREAD_GROUP_DEFAULT; 16260 } 16261 } 16262 16263 if (app == mHeavyWeightProcess) { 16264 if (adj > ProcessList.HEAVY_WEIGHT_APP_ADJ) { 16265 // We don't want to kill the current heavy-weight process. 16266 adj = ProcessList.HEAVY_WEIGHT_APP_ADJ; 16267 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16268 app.cached = false; 16269 app.adjType = "heavy"; 16270 } 16271 if (procState > ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 16272 procState = ActivityManager.PROCESS_STATE_HEAVY_WEIGHT; 16273 } 16274 } 16275 16276 if (app == mHomeProcess) { 16277 if (adj > ProcessList.HOME_APP_ADJ) { 16278 // This process is hosting what we currently consider to be the 16279 // home app, so we don't want to let it go into the background. 16280 adj = ProcessList.HOME_APP_ADJ; 16281 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16282 app.cached = false; 16283 app.adjType = "home"; 16284 } 16285 if (procState > ActivityManager.PROCESS_STATE_HOME) { 16286 procState = ActivityManager.PROCESS_STATE_HOME; 16287 } 16288 } 16289 16290 if (app == mPreviousProcess && app.activities.size() > 0) { 16291 if (adj > ProcessList.PREVIOUS_APP_ADJ) { 16292 // This was the previous process that showed UI to the user. 16293 // We want to try to keep it around more aggressively, to give 16294 // a good experience around switching between two apps. 16295 adj = ProcessList.PREVIOUS_APP_ADJ; 16296 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16297 app.cached = false; 16298 app.adjType = "previous"; 16299 } 16300 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 16301 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 16302 } 16303 } 16304 16305 if (false) Slog.i(TAG, "OOM " + app + ": initial adj=" + adj 16306 + " reason=" + app.adjType); 16307 16308 // By default, we use the computed adjustment. It may be changed if 16309 // there are applications dependent on our services or providers, but 16310 // this gives us a baseline and makes sure we don't get into an 16311 // infinite recursion. 16312 app.adjSeq = mAdjSeq; 16313 app.curRawAdj = adj; 16314 app.hasStartedServices = false; 16315 16316 if (mBackupTarget != null && app == mBackupTarget.app) { 16317 // If possible we want to avoid killing apps while they're being backed up 16318 if (adj > ProcessList.BACKUP_APP_ADJ) { 16319 if (DEBUG_BACKUP) Slog.v(TAG, "oom BACKUP_APP_ADJ for " + app); 16320 adj = ProcessList.BACKUP_APP_ADJ; 16321 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 16322 procState = ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 16323 } 16324 app.adjType = "backup"; 16325 app.cached = false; 16326 } 16327 if (procState > ActivityManager.PROCESS_STATE_BACKUP) { 16328 procState = ActivityManager.PROCESS_STATE_BACKUP; 16329 } 16330 } 16331 16332 boolean mayBeTop = false; 16333 16334 for (int is = app.services.size()-1; 16335 is >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 16336 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16337 || procState > ActivityManager.PROCESS_STATE_TOP); 16338 is--) { 16339 ServiceRecord s = app.services.valueAt(is); 16340 if (s.startRequested) { 16341 app.hasStartedServices = true; 16342 if (procState > ActivityManager.PROCESS_STATE_SERVICE) { 16343 procState = ActivityManager.PROCESS_STATE_SERVICE; 16344 } 16345 if (app.hasShownUi && app != mHomeProcess) { 16346 // If this process has shown some UI, let it immediately 16347 // go to the LRU list because it may be pretty heavy with 16348 // UI stuff. We'll tag it with a label just to help 16349 // debug and understand what is going on. 16350 if (adj > ProcessList.SERVICE_ADJ) { 16351 app.adjType = "cch-started-ui-services"; 16352 } 16353 } else { 16354 if (now < (s.lastActivity + ActiveServices.MAX_SERVICE_INACTIVITY)) { 16355 // This service has seen some activity within 16356 // recent memory, so we will keep its process ahead 16357 // of the background processes. 16358 if (adj > ProcessList.SERVICE_ADJ) { 16359 adj = ProcessList.SERVICE_ADJ; 16360 app.adjType = "started-services"; 16361 app.cached = false; 16362 } 16363 } 16364 // If we have let the service slide into the background 16365 // state, still have some text describing what it is doing 16366 // even though the service no longer has an impact. 16367 if (adj > ProcessList.SERVICE_ADJ) { 16368 app.adjType = "cch-started-services"; 16369 } 16370 } 16371 } 16372 for (int conni = s.connections.size()-1; 16373 conni >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 16374 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16375 || procState > ActivityManager.PROCESS_STATE_TOP); 16376 conni--) { 16377 ArrayList<ConnectionRecord> clist = s.connections.valueAt(conni); 16378 for (int i = 0; 16379 i < clist.size() && (adj > ProcessList.FOREGROUND_APP_ADJ 16380 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16381 || procState > ActivityManager.PROCESS_STATE_TOP); 16382 i++) { 16383 // XXX should compute this based on the max of 16384 // all connected clients. 16385 ConnectionRecord cr = clist.get(i); 16386 if (cr.binding.client == app) { 16387 // Binding to ourself is not interesting. 16388 continue; 16389 } 16390 if ((cr.flags&Context.BIND_WAIVE_PRIORITY) == 0) { 16391 ProcessRecord client = cr.binding.client; 16392 int clientAdj = computeOomAdjLocked(client, cachedAdj, 16393 TOP_APP, doingAll, now); 16394 int clientProcState = client.curProcState; 16395 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 16396 // If the other app is cached for any reason, for purposes here 16397 // we are going to consider it empty. The specific cached state 16398 // doesn't propagate except under certain conditions. 16399 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16400 } 16401 String adjType = null; 16402 if ((cr.flags&Context.BIND_ALLOW_OOM_MANAGEMENT) != 0) { 16403 // Not doing bind OOM management, so treat 16404 // this guy more like a started service. 16405 if (app.hasShownUi && app != mHomeProcess) { 16406 // If this process has shown some UI, let it immediately 16407 // go to the LRU list because it may be pretty heavy with 16408 // UI stuff. We'll tag it with a label just to help 16409 // debug and understand what is going on. 16410 if (adj > clientAdj) { 16411 adjType = "cch-bound-ui-services"; 16412 } 16413 app.cached = false; 16414 clientAdj = adj; 16415 clientProcState = procState; 16416 } else { 16417 if (now >= (s.lastActivity 16418 + ActiveServices.MAX_SERVICE_INACTIVITY)) { 16419 // This service has not seen activity within 16420 // recent memory, so allow it to drop to the 16421 // LRU list if there is no other reason to keep 16422 // it around. We'll also tag it with a label just 16423 // to help debug and undertand what is going on. 16424 if (adj > clientAdj) { 16425 adjType = "cch-bound-services"; 16426 } 16427 clientAdj = adj; 16428 } 16429 } 16430 } 16431 if (adj > clientAdj) { 16432 // If this process has recently shown UI, and 16433 // the process that is binding to it is less 16434 // important than being visible, then we don't 16435 // care about the binding as much as we care 16436 // about letting this process get into the LRU 16437 // list to be killed and restarted if needed for 16438 // memory. 16439 if (app.hasShownUi && app != mHomeProcess 16440 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16441 adjType = "cch-bound-ui-services"; 16442 } else { 16443 if ((cr.flags&(Context.BIND_ABOVE_CLIENT 16444 |Context.BIND_IMPORTANT)) != 0) { 16445 adj = clientAdj; 16446 } else if ((cr.flags&Context.BIND_NOT_VISIBLE) != 0 16447 && clientAdj < ProcessList.PERCEPTIBLE_APP_ADJ 16448 && adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16449 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16450 } else if (clientAdj > ProcessList.VISIBLE_APP_ADJ) { 16451 adj = clientAdj; 16452 } else { 16453 if (adj > ProcessList.VISIBLE_APP_ADJ) { 16454 adj = ProcessList.VISIBLE_APP_ADJ; 16455 } 16456 } 16457 if (!client.cached) { 16458 app.cached = false; 16459 } 16460 adjType = "service"; 16461 } 16462 } 16463 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 16464 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 16465 schedGroup = Process.THREAD_GROUP_DEFAULT; 16466 } 16467 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 16468 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 16469 // Special handling of clients who are in the top state. 16470 // We *may* want to consider this process to be in the 16471 // top state as well, but only if there is not another 16472 // reason for it to be running. Being on the top is a 16473 // special state, meaning you are specifically running 16474 // for the current top app. If the process is already 16475 // running in the background for some other reason, it 16476 // is more important to continue considering it to be 16477 // in the background state. 16478 mayBeTop = true; 16479 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16480 } else { 16481 // Special handling for above-top states (persistent 16482 // processes). These should not bring the current process 16483 // into the top state, since they are not on top. Instead 16484 // give them the best state after that. 16485 clientProcState = 16486 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16487 } 16488 } 16489 } else { 16490 if (clientProcState < 16491 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 16492 clientProcState = 16493 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 16494 } 16495 } 16496 if (procState > clientProcState) { 16497 procState = clientProcState; 16498 } 16499 if (procState < ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 16500 && (cr.flags&Context.BIND_SHOWING_UI) != 0) { 16501 app.pendingUiClean = true; 16502 } 16503 if (adjType != null) { 16504 app.adjType = adjType; 16505 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 16506 .REASON_SERVICE_IN_USE; 16507 app.adjSource = cr.binding.client; 16508 app.adjSourceProcState = clientProcState; 16509 app.adjTarget = s.name; 16510 } 16511 } 16512 if ((cr.flags&Context.BIND_TREAT_LIKE_ACTIVITY) != 0) { 16513 app.treatLikeActivity = true; 16514 } 16515 final ActivityRecord a = cr.activity; 16516 if ((cr.flags&Context.BIND_ADJUST_WITH_ACTIVITY) != 0) { 16517 if (a != null && adj > ProcessList.FOREGROUND_APP_ADJ && 16518 (a.visible || a.state == ActivityState.RESUMED 16519 || a.state == ActivityState.PAUSING)) { 16520 adj = ProcessList.FOREGROUND_APP_ADJ; 16521 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 16522 schedGroup = Process.THREAD_GROUP_DEFAULT; 16523 } 16524 app.cached = false; 16525 app.adjType = "service"; 16526 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 16527 .REASON_SERVICE_IN_USE; 16528 app.adjSource = a; 16529 app.adjSourceProcState = procState; 16530 app.adjTarget = s.name; 16531 } 16532 } 16533 } 16534 } 16535 } 16536 16537 for (int provi = app.pubProviders.size()-1; 16538 provi >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 16539 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16540 || procState > ActivityManager.PROCESS_STATE_TOP); 16541 provi--) { 16542 ContentProviderRecord cpr = app.pubProviders.valueAt(provi); 16543 for (int i = cpr.connections.size()-1; 16544 i >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 16545 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16546 || procState > ActivityManager.PROCESS_STATE_TOP); 16547 i--) { 16548 ContentProviderConnection conn = cpr.connections.get(i); 16549 ProcessRecord client = conn.client; 16550 if (client == app) { 16551 // Being our own client is not interesting. 16552 continue; 16553 } 16554 int clientAdj = computeOomAdjLocked(client, cachedAdj, TOP_APP, doingAll, now); 16555 int clientProcState = client.curProcState; 16556 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 16557 // If the other app is cached for any reason, for purposes here 16558 // we are going to consider it empty. 16559 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16560 } 16561 if (adj > clientAdj) { 16562 if (app.hasShownUi && app != mHomeProcess 16563 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16564 app.adjType = "cch-ui-provider"; 16565 } else { 16566 adj = clientAdj > ProcessList.FOREGROUND_APP_ADJ 16567 ? clientAdj : ProcessList.FOREGROUND_APP_ADJ; 16568 app.adjType = "provider"; 16569 } 16570 app.cached &= client.cached; 16571 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 16572 .REASON_PROVIDER_IN_USE; 16573 app.adjSource = client; 16574 app.adjSourceProcState = clientProcState; 16575 app.adjTarget = cpr.name; 16576 } 16577 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 16578 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 16579 // Special handling of clients who are in the top state. 16580 // We *may* want to consider this process to be in the 16581 // top state as well, but only if there is not another 16582 // reason for it to be running. Being on the top is a 16583 // special state, meaning you are specifically running 16584 // for the current top app. If the process is already 16585 // running in the background for some other reason, it 16586 // is more important to continue considering it to be 16587 // in the background state. 16588 mayBeTop = true; 16589 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16590 } else { 16591 // Special handling for above-top states (persistent 16592 // processes). These should not bring the current process 16593 // into the top state, since they are not on top. Instead 16594 // give them the best state after that. 16595 clientProcState = 16596 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16597 } 16598 } 16599 if (procState > clientProcState) { 16600 procState = clientProcState; 16601 } 16602 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 16603 schedGroup = Process.THREAD_GROUP_DEFAULT; 16604 } 16605 } 16606 // If the provider has external (non-framework) process 16607 // dependencies, ensure that its adjustment is at least 16608 // FOREGROUND_APP_ADJ. 16609 if (cpr.hasExternalProcessHandles()) { 16610 if (adj > ProcessList.FOREGROUND_APP_ADJ) { 16611 adj = ProcessList.FOREGROUND_APP_ADJ; 16612 schedGroup = Process.THREAD_GROUP_DEFAULT; 16613 app.cached = false; 16614 app.adjType = "provider"; 16615 app.adjTarget = cpr.name; 16616 } 16617 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) { 16618 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16619 } 16620 } 16621 } 16622 16623 if (mayBeTop && procState > ActivityManager.PROCESS_STATE_TOP) { 16624 // A client of one of our services or providers is in the top state. We 16625 // *may* want to be in the top state, but not if we are already running in 16626 // the background for some other reason. For the decision here, we are going 16627 // to pick out a few specific states that we want to remain in when a client 16628 // is top (states that tend to be longer-term) and otherwise allow it to go 16629 // to the top state. 16630 switch (procState) { 16631 case ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND: 16632 case ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND: 16633 case ActivityManager.PROCESS_STATE_SERVICE: 16634 // These all are longer-term states, so pull them up to the top 16635 // of the background states, but not all the way to the top state. 16636 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16637 break; 16638 default: 16639 // Otherwise, top is a better choice, so take it. 16640 procState = ActivityManager.PROCESS_STATE_TOP; 16641 break; 16642 } 16643 } 16644 16645 if (procState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 16646 if (app.hasClientActivities) { 16647 // This is a cached process, but with client activities. Mark it so. 16648 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT; 16649 app.adjType = "cch-client-act"; 16650 } else if (app.treatLikeActivity) { 16651 // This is a cached process, but somebody wants us to treat it like it has 16652 // an activity, okay! 16653 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 16654 app.adjType = "cch-as-act"; 16655 } 16656 } 16657 16658 if (adj == ProcessList.SERVICE_ADJ) { 16659 if (doingAll) { 16660 app.serviceb = mNewNumAServiceProcs > (mNumServiceProcs/3); 16661 mNewNumServiceProcs++; 16662 //Slog.i(TAG, "ADJ " + app + " serviceb=" + app.serviceb); 16663 if (!app.serviceb) { 16664 // This service isn't far enough down on the LRU list to 16665 // normally be a B service, but if we are low on RAM and it 16666 // is large we want to force it down since we would prefer to 16667 // keep launcher over it. 16668 if (mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 16669 && app.lastPss >= mProcessList.getCachedRestoreThresholdKb()) { 16670 app.serviceHighRam = true; 16671 app.serviceb = true; 16672 //Slog.i(TAG, "ADJ " + app + " high ram!"); 16673 } else { 16674 mNewNumAServiceProcs++; 16675 //Slog.i(TAG, "ADJ " + app + " not high ram!"); 16676 } 16677 } else { 16678 app.serviceHighRam = false; 16679 } 16680 } 16681 if (app.serviceb) { 16682 adj = ProcessList.SERVICE_B_ADJ; 16683 } 16684 } 16685 16686 app.curRawAdj = adj; 16687 16688 //Slog.i(TAG, "OOM ADJ " + app + ": pid=" + app.pid + 16689 // " adj=" + adj + " curAdj=" + app.curAdj + " maxAdj=" + app.maxAdj); 16690 if (adj > app.maxAdj) { 16691 adj = app.maxAdj; 16692 if (app.maxAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 16693 schedGroup = Process.THREAD_GROUP_DEFAULT; 16694 } 16695 } 16696 16697 // Do final modification to adj. Everything we do between here and applying 16698 // the final setAdj must be done in this function, because we will also use 16699 // it when computing the final cached adj later. Note that we don't need to 16700 // worry about this for max adj above, since max adj will always be used to 16701 // keep it out of the cached vaues. 16702 app.curAdj = app.modifyRawOomAdj(adj); 16703 app.curSchedGroup = schedGroup; 16704 app.curProcState = procState; 16705 app.foregroundActivities = foregroundActivities; 16706 16707 return app.curRawAdj; 16708 } 16709 16710 /** 16711 * Schedule PSS collection of a process. 16712 */ 16713 void requestPssLocked(ProcessRecord proc, int procState) { 16714 if (mPendingPssProcesses.contains(proc)) { 16715 return; 16716 } 16717 if (mPendingPssProcesses.size() == 0) { 16718 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 16719 } 16720 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of: " + proc); 16721 proc.pssProcState = procState; 16722 mPendingPssProcesses.add(proc); 16723 } 16724 16725 /** 16726 * Schedule PSS collection of all processes. 16727 */ 16728 void requestPssAllProcsLocked(long now, boolean always, boolean memLowered) { 16729 if (!always) { 16730 if (now < (mLastFullPssTime + 16731 (memLowered ? FULL_PSS_LOWERED_INTERVAL : FULL_PSS_MIN_INTERVAL))) { 16732 return; 16733 } 16734 } 16735 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of all procs! memLowered=" + memLowered); 16736 mLastFullPssTime = now; 16737 mFullPssPending = true; 16738 mPendingPssProcesses.ensureCapacity(mLruProcesses.size()); 16739 mPendingPssProcesses.clear(); 16740 for (int i=mLruProcesses.size()-1; i>=0; i--) { 16741 ProcessRecord app = mLruProcesses.get(i); 16742 if (memLowered || now > (app.lastStateTime+ProcessList.PSS_ALL_INTERVAL)) { 16743 app.pssProcState = app.setProcState; 16744 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 16745 isSleeping(), now); 16746 mPendingPssProcesses.add(app); 16747 } 16748 } 16749 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 16750 } 16751 16752 /** 16753 * Ask a given process to GC right now. 16754 */ 16755 final void performAppGcLocked(ProcessRecord app) { 16756 try { 16757 app.lastRequestedGc = SystemClock.uptimeMillis(); 16758 if (app.thread != null) { 16759 if (app.reportLowMemory) { 16760 app.reportLowMemory = false; 16761 app.thread.scheduleLowMemory(); 16762 } else { 16763 app.thread.processInBackground(); 16764 } 16765 } 16766 } catch (Exception e) { 16767 // whatever. 16768 } 16769 } 16770 16771 /** 16772 * Returns true if things are idle enough to perform GCs. 16773 */ 16774 private final boolean canGcNowLocked() { 16775 boolean processingBroadcasts = false; 16776 for (BroadcastQueue q : mBroadcastQueues) { 16777 if (q.mParallelBroadcasts.size() != 0 || q.mOrderedBroadcasts.size() != 0) { 16778 processingBroadcasts = true; 16779 } 16780 } 16781 return !processingBroadcasts 16782 && (isSleeping() || mStackSupervisor.allResumedActivitiesIdle()); 16783 } 16784 16785 /** 16786 * Perform GCs on all processes that are waiting for it, but only 16787 * if things are idle. 16788 */ 16789 final void performAppGcsLocked() { 16790 final int N = mProcessesToGc.size(); 16791 if (N <= 0) { 16792 return; 16793 } 16794 if (canGcNowLocked()) { 16795 while (mProcessesToGc.size() > 0) { 16796 ProcessRecord proc = mProcessesToGc.remove(0); 16797 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ || proc.reportLowMemory) { 16798 if ((proc.lastRequestedGc+GC_MIN_INTERVAL) 16799 <= SystemClock.uptimeMillis()) { 16800 // To avoid spamming the system, we will GC processes one 16801 // at a time, waiting a few seconds between each. 16802 performAppGcLocked(proc); 16803 scheduleAppGcsLocked(); 16804 return; 16805 } else { 16806 // It hasn't been long enough since we last GCed this 16807 // process... put it in the list to wait for its time. 16808 addProcessToGcListLocked(proc); 16809 break; 16810 } 16811 } 16812 } 16813 16814 scheduleAppGcsLocked(); 16815 } 16816 } 16817 16818 /** 16819 * If all looks good, perform GCs on all processes waiting for them. 16820 */ 16821 final void performAppGcsIfAppropriateLocked() { 16822 if (canGcNowLocked()) { 16823 performAppGcsLocked(); 16824 return; 16825 } 16826 // Still not idle, wait some more. 16827 scheduleAppGcsLocked(); 16828 } 16829 16830 /** 16831 * Schedule the execution of all pending app GCs. 16832 */ 16833 final void scheduleAppGcsLocked() { 16834 mHandler.removeMessages(GC_BACKGROUND_PROCESSES_MSG); 16835 16836 if (mProcessesToGc.size() > 0) { 16837 // Schedule a GC for the time to the next process. 16838 ProcessRecord proc = mProcessesToGc.get(0); 16839 Message msg = mHandler.obtainMessage(GC_BACKGROUND_PROCESSES_MSG); 16840 16841 long when = proc.lastRequestedGc + GC_MIN_INTERVAL; 16842 long now = SystemClock.uptimeMillis(); 16843 if (when < (now+GC_TIMEOUT)) { 16844 when = now + GC_TIMEOUT; 16845 } 16846 mHandler.sendMessageAtTime(msg, when); 16847 } 16848 } 16849 16850 /** 16851 * Add a process to the array of processes waiting to be GCed. Keeps the 16852 * list in sorted order by the last GC time. The process can't already be 16853 * on the list. 16854 */ 16855 final void addProcessToGcListLocked(ProcessRecord proc) { 16856 boolean added = false; 16857 for (int i=mProcessesToGc.size()-1; i>=0; i--) { 16858 if (mProcessesToGc.get(i).lastRequestedGc < 16859 proc.lastRequestedGc) { 16860 added = true; 16861 mProcessesToGc.add(i+1, proc); 16862 break; 16863 } 16864 } 16865 if (!added) { 16866 mProcessesToGc.add(0, proc); 16867 } 16868 } 16869 16870 /** 16871 * Set up to ask a process to GC itself. This will either do it 16872 * immediately, or put it on the list of processes to gc the next 16873 * time things are idle. 16874 */ 16875 final void scheduleAppGcLocked(ProcessRecord app) { 16876 long now = SystemClock.uptimeMillis(); 16877 if ((app.lastRequestedGc+GC_MIN_INTERVAL) > now) { 16878 return; 16879 } 16880 if (!mProcessesToGc.contains(app)) { 16881 addProcessToGcListLocked(app); 16882 scheduleAppGcsLocked(); 16883 } 16884 } 16885 16886 final void checkExcessivePowerUsageLocked(boolean doKills) { 16887 updateCpuStatsNow(); 16888 16889 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 16890 boolean doWakeKills = doKills; 16891 boolean doCpuKills = doKills; 16892 if (mLastPowerCheckRealtime == 0) { 16893 doWakeKills = false; 16894 } 16895 if (mLastPowerCheckUptime == 0) { 16896 doCpuKills = false; 16897 } 16898 if (stats.isScreenOn()) { 16899 doWakeKills = false; 16900 } 16901 final long curRealtime = SystemClock.elapsedRealtime(); 16902 final long realtimeSince = curRealtime - mLastPowerCheckRealtime; 16903 final long curUptime = SystemClock.uptimeMillis(); 16904 final long uptimeSince = curUptime - mLastPowerCheckUptime; 16905 mLastPowerCheckRealtime = curRealtime; 16906 mLastPowerCheckUptime = curUptime; 16907 if (realtimeSince < WAKE_LOCK_MIN_CHECK_DURATION) { 16908 doWakeKills = false; 16909 } 16910 if (uptimeSince < CPU_MIN_CHECK_DURATION) { 16911 doCpuKills = false; 16912 } 16913 int i = mLruProcesses.size(); 16914 while (i > 0) { 16915 i--; 16916 ProcessRecord app = mLruProcesses.get(i); 16917 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 16918 long wtime; 16919 synchronized (stats) { 16920 wtime = stats.getProcessWakeTime(app.info.uid, 16921 app.pid, curRealtime); 16922 } 16923 long wtimeUsed = wtime - app.lastWakeTime; 16924 long cputimeUsed = app.curCpuTime - app.lastCpuTime; 16925 if (DEBUG_POWER) { 16926 StringBuilder sb = new StringBuilder(128); 16927 sb.append("Wake for "); 16928 app.toShortString(sb); 16929 sb.append(": over "); 16930 TimeUtils.formatDuration(realtimeSince, sb); 16931 sb.append(" used "); 16932 TimeUtils.formatDuration(wtimeUsed, sb); 16933 sb.append(" ("); 16934 sb.append((wtimeUsed*100)/realtimeSince); 16935 sb.append("%)"); 16936 Slog.i(TAG, sb.toString()); 16937 sb.setLength(0); 16938 sb.append("CPU for "); 16939 app.toShortString(sb); 16940 sb.append(": over "); 16941 TimeUtils.formatDuration(uptimeSince, sb); 16942 sb.append(" used "); 16943 TimeUtils.formatDuration(cputimeUsed, sb); 16944 sb.append(" ("); 16945 sb.append((cputimeUsed*100)/uptimeSince); 16946 sb.append("%)"); 16947 Slog.i(TAG, sb.toString()); 16948 } 16949 // If a process has held a wake lock for more 16950 // than 50% of the time during this period, 16951 // that sounds bad. Kill! 16952 if (doWakeKills && realtimeSince > 0 16953 && ((wtimeUsed*100)/realtimeSince) >= 50) { 16954 synchronized (stats) { 16955 stats.reportExcessiveWakeLocked(app.info.uid, app.processName, 16956 realtimeSince, wtimeUsed); 16957 } 16958 app.kill("excessive wake held " + wtimeUsed + " during " + realtimeSince, true); 16959 app.baseProcessTracker.reportExcessiveWake(app.pkgList); 16960 } else if (doCpuKills && uptimeSince > 0 16961 && ((cputimeUsed*100)/uptimeSince) >= 25) { 16962 synchronized (stats) { 16963 stats.reportExcessiveCpuLocked(app.info.uid, app.processName, 16964 uptimeSince, cputimeUsed); 16965 } 16966 app.kill("excessive cpu " + cputimeUsed + " during " + uptimeSince, true); 16967 app.baseProcessTracker.reportExcessiveCpu(app.pkgList); 16968 } else { 16969 app.lastWakeTime = wtime; 16970 app.lastCpuTime = app.curCpuTime; 16971 } 16972 } 16973 } 16974 } 16975 16976 private final boolean applyOomAdjLocked(ProcessRecord app, 16977 ProcessRecord TOP_APP, boolean doingAll, long now) { 16978 boolean success = true; 16979 16980 if (app.curRawAdj != app.setRawAdj) { 16981 app.setRawAdj = app.curRawAdj; 16982 } 16983 16984 int changes = 0; 16985 16986 if (app.curAdj != app.setAdj) { 16987 ProcessList.setOomAdj(app.pid, app.info.uid, app.curAdj); 16988 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v( 16989 TAG, "Set " + app.pid + " " + app.processName + 16990 " adj " + app.curAdj + ": " + app.adjType); 16991 app.setAdj = app.curAdj; 16992 } 16993 16994 if (app.setSchedGroup != app.curSchedGroup) { 16995 app.setSchedGroup = app.curSchedGroup; 16996 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16997 "Setting process group of " + app.processName 16998 + " to " + app.curSchedGroup); 16999 if (app.waitingToKill != null && 17000 app.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 17001 app.kill(app.waitingToKill, true); 17002 success = false; 17003 } else { 17004 if (true) { 17005 long oldId = Binder.clearCallingIdentity(); 17006 try { 17007 Process.setProcessGroup(app.pid, app.curSchedGroup); 17008 } catch (Exception e) { 17009 Slog.w(TAG, "Failed setting process group of " + app.pid 17010 + " to " + app.curSchedGroup); 17011 e.printStackTrace(); 17012 } finally { 17013 Binder.restoreCallingIdentity(oldId); 17014 } 17015 } else { 17016 if (app.thread != null) { 17017 try { 17018 app.thread.setSchedulingGroup(app.curSchedGroup); 17019 } catch (RemoteException e) { 17020 } 17021 } 17022 } 17023 Process.setSwappiness(app.pid, 17024 app.curSchedGroup <= Process.THREAD_GROUP_BG_NONINTERACTIVE); 17025 } 17026 } 17027 if (app.repForegroundActivities != app.foregroundActivities) { 17028 app.repForegroundActivities = app.foregroundActivities; 17029 changes |= ProcessChangeItem.CHANGE_ACTIVITIES; 17030 } 17031 if (app.repProcState != app.curProcState) { 17032 app.repProcState = app.curProcState; 17033 changes |= ProcessChangeItem.CHANGE_PROCESS_STATE; 17034 if (app.thread != null) { 17035 try { 17036 if (false) { 17037 //RuntimeException h = new RuntimeException("here"); 17038 Slog.i(TAG, "Sending new process state " + app.repProcState 17039 + " to " + app /*, h*/); 17040 } 17041 app.thread.setProcessState(app.repProcState); 17042 } catch (RemoteException e) { 17043 } 17044 } 17045 } 17046 if (app.setProcState < 0 || ProcessList.procStatesDifferForMem(app.curProcState, 17047 app.setProcState)) { 17048 app.lastStateTime = now; 17049 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 17050 isSleeping(), now); 17051 if (DEBUG_PSS) Slog.d(TAG, "Process state change from " 17052 + ProcessList.makeProcStateString(app.setProcState) + " to " 17053 + ProcessList.makeProcStateString(app.curProcState) + " next pss in " 17054 + (app.nextPssTime-now) + ": " + app); 17055 } else { 17056 if (now > app.nextPssTime || (now > (app.lastPssTime+ProcessList.PSS_MAX_INTERVAL) 17057 && now > (app.lastStateTime+ProcessList.PSS_MIN_TIME_FROM_STATE_CHANGE))) { 17058 requestPssLocked(app, app.setProcState); 17059 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, false, 17060 isSleeping(), now); 17061 } else if (false && DEBUG_PSS) { 17062 Slog.d(TAG, "Not requesting PSS of " + app + ": next=" + (app.nextPssTime-now)); 17063 } 17064 } 17065 if (app.setProcState != app.curProcState) { 17066 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17067 "Proc state change of " + app.processName 17068 + " to " + app.curProcState); 17069 boolean setImportant = app.setProcState < ActivityManager.PROCESS_STATE_SERVICE; 17070 boolean curImportant = app.curProcState < ActivityManager.PROCESS_STATE_SERVICE; 17071 if (setImportant && !curImportant) { 17072 // This app is no longer something we consider important enough to allow to 17073 // use arbitrary amounts of battery power. Note 17074 // its current wake lock time to later know to kill it if 17075 // it is not behaving well. 17076 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 17077 synchronized (stats) { 17078 app.lastWakeTime = stats.getProcessWakeTime(app.info.uid, 17079 app.pid, SystemClock.elapsedRealtime()); 17080 } 17081 app.lastCpuTime = app.curCpuTime; 17082 17083 } 17084 app.setProcState = app.curProcState; 17085 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 17086 app.notCachedSinceIdle = false; 17087 } 17088 if (!doingAll) { 17089 setProcessTrackerStateLocked(app, mProcessStats.getMemFactorLocked(), now); 17090 } else { 17091 app.procStateChanged = true; 17092 } 17093 } 17094 17095 if (changes != 0) { 17096 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Changes in " + app + ": " + changes); 17097 int i = mPendingProcessChanges.size()-1; 17098 ProcessChangeItem item = null; 17099 while (i >= 0) { 17100 item = mPendingProcessChanges.get(i); 17101 if (item.pid == app.pid) { 17102 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Re-using existing item: " + item); 17103 break; 17104 } 17105 i--; 17106 } 17107 if (i < 0) { 17108 // No existing item in pending changes; need a new one. 17109 final int NA = mAvailProcessChanges.size(); 17110 if (NA > 0) { 17111 item = mAvailProcessChanges.remove(NA-1); 17112 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Retreiving available item: " + item); 17113 } else { 17114 item = new ProcessChangeItem(); 17115 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Allocating new item: " + item); 17116 } 17117 item.changes = 0; 17118 item.pid = app.pid; 17119 item.uid = app.info.uid; 17120 if (mPendingProcessChanges.size() == 0) { 17121 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, 17122 "*** Enqueueing dispatch processes changed!"); 17123 mHandler.obtainMessage(DISPATCH_PROCESSES_CHANGED).sendToTarget(); 17124 } 17125 mPendingProcessChanges.add(item); 17126 } 17127 item.changes |= changes; 17128 item.processState = app.repProcState; 17129 item.foregroundActivities = app.repForegroundActivities; 17130 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Item " 17131 + Integer.toHexString(System.identityHashCode(item)) 17132 + " " + app.toShortString() + ": changes=" + item.changes 17133 + " procState=" + item.processState 17134 + " foreground=" + item.foregroundActivities 17135 + " type=" + app.adjType + " source=" + app.adjSource 17136 + " target=" + app.adjTarget); 17137 } 17138 17139 return success; 17140 } 17141 17142 private final void setProcessTrackerStateLocked(ProcessRecord proc, int memFactor, long now) { 17143 if (proc.thread != null) { 17144 if (proc.baseProcessTracker != null) { 17145 proc.baseProcessTracker.setState(proc.repProcState, memFactor, now, proc.pkgList); 17146 } 17147 if (proc.repProcState >= 0) { 17148 mBatteryStatsService.noteProcessState(proc.processName, proc.info.uid, 17149 proc.repProcState); 17150 } 17151 } 17152 } 17153 17154 private final boolean updateOomAdjLocked(ProcessRecord app, int cachedAdj, 17155 ProcessRecord TOP_APP, boolean doingAll, long now) { 17156 if (app.thread == null) { 17157 return false; 17158 } 17159 17160 computeOomAdjLocked(app, cachedAdj, TOP_APP, doingAll, now); 17161 17162 return applyOomAdjLocked(app, TOP_APP, doingAll, now); 17163 } 17164 17165 final void updateProcessForegroundLocked(ProcessRecord proc, boolean isForeground, 17166 boolean oomAdj) { 17167 if (isForeground != proc.foregroundServices) { 17168 proc.foregroundServices = isForeground; 17169 ArrayList<ProcessRecord> curProcs = mForegroundPackages.get(proc.info.packageName, 17170 proc.info.uid); 17171 if (isForeground) { 17172 if (curProcs == null) { 17173 curProcs = new ArrayList<ProcessRecord>(); 17174 mForegroundPackages.put(proc.info.packageName, proc.info.uid, curProcs); 17175 } 17176 if (!curProcs.contains(proc)) { 17177 curProcs.add(proc); 17178 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_FOREGROUND_START, 17179 proc.info.packageName, proc.info.uid); 17180 } 17181 } else { 17182 if (curProcs != null) { 17183 if (curProcs.remove(proc)) { 17184 mBatteryStatsService.noteEvent( 17185 BatteryStats.HistoryItem.EVENT_FOREGROUND_FINISH, 17186 proc.info.packageName, proc.info.uid); 17187 if (curProcs.size() <= 0) { 17188 mForegroundPackages.remove(proc.info.packageName, proc.info.uid); 17189 } 17190 } 17191 } 17192 } 17193 if (oomAdj) { 17194 updateOomAdjLocked(); 17195 } 17196 } 17197 } 17198 17199 private final ActivityRecord resumedAppLocked() { 17200 ActivityRecord act = mStackSupervisor.resumedAppLocked(); 17201 String pkg; 17202 int uid; 17203 if (act != null) { 17204 pkg = act.packageName; 17205 uid = act.info.applicationInfo.uid; 17206 } else { 17207 pkg = null; 17208 uid = -1; 17209 } 17210 // Has the UID or resumed package name changed? 17211 if (uid != mCurResumedUid || (pkg != mCurResumedPackage 17212 && (pkg == null || !pkg.equals(mCurResumedPackage)))) { 17213 if (mCurResumedPackage != null) { 17214 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_FINISH, 17215 mCurResumedPackage, mCurResumedUid); 17216 } 17217 mCurResumedPackage = pkg; 17218 mCurResumedUid = uid; 17219 if (mCurResumedPackage != null) { 17220 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_START, 17221 mCurResumedPackage, mCurResumedUid); 17222 } 17223 } 17224 return act; 17225 } 17226 17227 final boolean updateOomAdjLocked(ProcessRecord app) { 17228 final ActivityRecord TOP_ACT = resumedAppLocked(); 17229 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 17230 final boolean wasCached = app.cached; 17231 17232 mAdjSeq++; 17233 17234 // This is the desired cached adjusment we want to tell it to use. 17235 // If our app is currently cached, we know it, and that is it. Otherwise, 17236 // we don't know it yet, and it needs to now be cached we will then 17237 // need to do a complete oom adj. 17238 final int cachedAdj = app.curRawAdj >= ProcessList.CACHED_APP_MIN_ADJ 17239 ? app.curRawAdj : ProcessList.UNKNOWN_ADJ; 17240 boolean success = updateOomAdjLocked(app, cachedAdj, TOP_APP, false, 17241 SystemClock.uptimeMillis()); 17242 if (wasCached != app.cached || app.curRawAdj == ProcessList.UNKNOWN_ADJ) { 17243 // Changed to/from cached state, so apps after it in the LRU 17244 // list may also be changed. 17245 updateOomAdjLocked(); 17246 } 17247 return success; 17248 } 17249 17250 final void updateOomAdjLocked() { 17251 final ActivityRecord TOP_ACT = resumedAppLocked(); 17252 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 17253 final long now = SystemClock.uptimeMillis(); 17254 final long oldTime = now - ProcessList.MAX_EMPTY_TIME; 17255 final int N = mLruProcesses.size(); 17256 17257 if (false) { 17258 RuntimeException e = new RuntimeException(); 17259 e.fillInStackTrace(); 17260 Slog.i(TAG, "updateOomAdj: top=" + TOP_ACT, e); 17261 } 17262 17263 mAdjSeq++; 17264 mNewNumServiceProcs = 0; 17265 mNewNumAServiceProcs = 0; 17266 17267 final int emptyProcessLimit; 17268 final int cachedProcessLimit; 17269 if (mProcessLimit <= 0) { 17270 emptyProcessLimit = cachedProcessLimit = 0; 17271 } else if (mProcessLimit == 1) { 17272 emptyProcessLimit = 1; 17273 cachedProcessLimit = 0; 17274 } else { 17275 emptyProcessLimit = ProcessList.computeEmptyProcessLimit(mProcessLimit); 17276 cachedProcessLimit = mProcessLimit - emptyProcessLimit; 17277 } 17278 17279 // Let's determine how many processes we have running vs. 17280 // how many slots we have for background processes; we may want 17281 // to put multiple processes in a slot of there are enough of 17282 // them. 17283 int numSlots = (ProcessList.CACHED_APP_MAX_ADJ 17284 - ProcessList.CACHED_APP_MIN_ADJ + 1) / 2; 17285 int numEmptyProcs = N - mNumNonCachedProcs - mNumCachedHiddenProcs; 17286 if (numEmptyProcs > cachedProcessLimit) { 17287 // If there are more empty processes than our limit on cached 17288 // processes, then use the cached process limit for the factor. 17289 // This ensures that the really old empty processes get pushed 17290 // down to the bottom, so if we are running low on memory we will 17291 // have a better chance at keeping around more cached processes 17292 // instead of a gazillion empty processes. 17293 numEmptyProcs = cachedProcessLimit; 17294 } 17295 int emptyFactor = numEmptyProcs/numSlots; 17296 if (emptyFactor < 1) emptyFactor = 1; 17297 int cachedFactor = (mNumCachedHiddenProcs > 0 ? mNumCachedHiddenProcs : 1)/numSlots; 17298 if (cachedFactor < 1) cachedFactor = 1; 17299 int stepCached = 0; 17300 int stepEmpty = 0; 17301 int numCached = 0; 17302 int numEmpty = 0; 17303 int numTrimming = 0; 17304 17305 mNumNonCachedProcs = 0; 17306 mNumCachedHiddenProcs = 0; 17307 17308 // First update the OOM adjustment for each of the 17309 // application processes based on their current state. 17310 int curCachedAdj = ProcessList.CACHED_APP_MIN_ADJ; 17311 int nextCachedAdj = curCachedAdj+1; 17312 int curEmptyAdj = ProcessList.CACHED_APP_MIN_ADJ; 17313 int nextEmptyAdj = curEmptyAdj+2; 17314 for (int i=N-1; i>=0; i--) { 17315 ProcessRecord app = mLruProcesses.get(i); 17316 if (!app.killedByAm && app.thread != null) { 17317 app.procStateChanged = false; 17318 computeOomAdjLocked(app, ProcessList.UNKNOWN_ADJ, TOP_APP, true, now); 17319 17320 // If we haven't yet assigned the final cached adj 17321 // to the process, do that now. 17322 if (app.curAdj >= ProcessList.UNKNOWN_ADJ) { 17323 switch (app.curProcState) { 17324 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 17325 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 17326 // This process is a cached process holding activities... 17327 // assign it the next cached value for that type, and then 17328 // step that cached level. 17329 app.curRawAdj = curCachedAdj; 17330 app.curAdj = app.modifyRawOomAdj(curCachedAdj); 17331 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning activity LRU #" + i 17332 + " adj: " + app.curAdj + " (curCachedAdj=" + curCachedAdj 17333 + ")"); 17334 if (curCachedAdj != nextCachedAdj) { 17335 stepCached++; 17336 if (stepCached >= cachedFactor) { 17337 stepCached = 0; 17338 curCachedAdj = nextCachedAdj; 17339 nextCachedAdj += 2; 17340 if (nextCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) { 17341 nextCachedAdj = ProcessList.CACHED_APP_MAX_ADJ; 17342 } 17343 } 17344 } 17345 break; 17346 default: 17347 // For everything else, assign next empty cached process 17348 // level and bump that up. Note that this means that 17349 // long-running services that have dropped down to the 17350 // cached level will be treated as empty (since their process 17351 // state is still as a service), which is what we want. 17352 app.curRawAdj = curEmptyAdj; 17353 app.curAdj = app.modifyRawOomAdj(curEmptyAdj); 17354 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning empty LRU #" + i 17355 + " adj: " + app.curAdj + " (curEmptyAdj=" + curEmptyAdj 17356 + ")"); 17357 if (curEmptyAdj != nextEmptyAdj) { 17358 stepEmpty++; 17359 if (stepEmpty >= emptyFactor) { 17360 stepEmpty = 0; 17361 curEmptyAdj = nextEmptyAdj; 17362 nextEmptyAdj += 2; 17363 if (nextEmptyAdj > ProcessList.CACHED_APP_MAX_ADJ) { 17364 nextEmptyAdj = ProcessList.CACHED_APP_MAX_ADJ; 17365 } 17366 } 17367 } 17368 break; 17369 } 17370 } 17371 17372 applyOomAdjLocked(app, TOP_APP, true, now); 17373 17374 // Count the number of process types. 17375 switch (app.curProcState) { 17376 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 17377 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 17378 mNumCachedHiddenProcs++; 17379 numCached++; 17380 if (numCached > cachedProcessLimit) { 17381 app.kill("cached #" + numCached, true); 17382 } 17383 break; 17384 case ActivityManager.PROCESS_STATE_CACHED_EMPTY: 17385 if (numEmpty > ProcessList.TRIM_EMPTY_APPS 17386 && app.lastActivityTime < oldTime) { 17387 app.kill("empty for " 17388 + ((oldTime + ProcessList.MAX_EMPTY_TIME - app.lastActivityTime) 17389 / 1000) + "s", true); 17390 } else { 17391 numEmpty++; 17392 if (numEmpty > emptyProcessLimit) { 17393 app.kill("empty #" + numEmpty, true); 17394 } 17395 } 17396 break; 17397 default: 17398 mNumNonCachedProcs++; 17399 break; 17400 } 17401 17402 if (app.isolated && app.services.size() <= 0) { 17403 // If this is an isolated process, and there are no 17404 // services running in it, then the process is no longer 17405 // needed. We agressively kill these because we can by 17406 // definition not re-use the same process again, and it is 17407 // good to avoid having whatever code was running in them 17408 // left sitting around after no longer needed. 17409 app.kill("isolated not needed", true); 17410 } 17411 17412 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 17413 && !app.killedByAm) { 17414 numTrimming++; 17415 } 17416 } 17417 } 17418 17419 mNumServiceProcs = mNewNumServiceProcs; 17420 17421 // Now determine the memory trimming level of background processes. 17422 // Unfortunately we need to start at the back of the list to do this 17423 // properly. We only do this if the number of background apps we 17424 // are managing to keep around is less than half the maximum we desire; 17425 // if we are keeping a good number around, we'll let them use whatever 17426 // memory they want. 17427 final int numCachedAndEmpty = numCached + numEmpty; 17428 int memFactor; 17429 if (numCached <= ProcessList.TRIM_CACHED_APPS 17430 && numEmpty <= ProcessList.TRIM_EMPTY_APPS) { 17431 if (numCachedAndEmpty <= ProcessList.TRIM_CRITICAL_THRESHOLD) { 17432 memFactor = ProcessStats.ADJ_MEM_FACTOR_CRITICAL; 17433 } else if (numCachedAndEmpty <= ProcessList.TRIM_LOW_THRESHOLD) { 17434 memFactor = ProcessStats.ADJ_MEM_FACTOR_LOW; 17435 } else { 17436 memFactor = ProcessStats.ADJ_MEM_FACTOR_MODERATE; 17437 } 17438 } else { 17439 memFactor = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 17440 } 17441 // We always allow the memory level to go up (better). We only allow it to go 17442 // down if we are in a state where that is allowed, *and* the total number of processes 17443 // has gone down since last time. 17444 if (DEBUG_OOM_ADJ) Slog.d(TAG, "oom: memFactor=" + memFactor + " last=" + mLastMemoryLevel 17445 + " allowLow=" + mAllowLowerMemLevel + " numProcs=" + mLruProcesses.size() 17446 + " last=" + mLastNumProcesses); 17447 if (memFactor > mLastMemoryLevel) { 17448 if (!mAllowLowerMemLevel || mLruProcesses.size() >= mLastNumProcesses) { 17449 memFactor = mLastMemoryLevel; 17450 if (DEBUG_OOM_ADJ) Slog.d(TAG, "Keeping last mem factor!"); 17451 } 17452 } 17453 mLastMemoryLevel = memFactor; 17454 mLastNumProcesses = mLruProcesses.size(); 17455 boolean allChanged = mProcessStats.setMemFactorLocked(memFactor, !isSleeping(), now); 17456 final int trackerMemFactor = mProcessStats.getMemFactorLocked(); 17457 if (memFactor != ProcessStats.ADJ_MEM_FACTOR_NORMAL) { 17458 if (mLowRamStartTime == 0) { 17459 mLowRamStartTime = now; 17460 } 17461 int step = 0; 17462 int fgTrimLevel; 17463 switch (memFactor) { 17464 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 17465 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_CRITICAL; 17466 break; 17467 case ProcessStats.ADJ_MEM_FACTOR_LOW: 17468 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_LOW; 17469 break; 17470 default: 17471 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_MODERATE; 17472 break; 17473 } 17474 int factor = numTrimming/3; 17475 int minFactor = 2; 17476 if (mHomeProcess != null) minFactor++; 17477 if (mPreviousProcess != null) minFactor++; 17478 if (factor < minFactor) factor = minFactor; 17479 int curLevel = ComponentCallbacks2.TRIM_MEMORY_COMPLETE; 17480 for (int i=N-1; i>=0; i--) { 17481 ProcessRecord app = mLruProcesses.get(i); 17482 if (allChanged || app.procStateChanged) { 17483 setProcessTrackerStateLocked(app, trackerMemFactor, now); 17484 app.procStateChanged = false; 17485 } 17486 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 17487 && !app.killedByAm) { 17488 if (app.trimMemoryLevel < curLevel && app.thread != null) { 17489 try { 17490 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17491 "Trimming memory of " + app.processName 17492 + " to " + curLevel); 17493 app.thread.scheduleTrimMemory(curLevel); 17494 } catch (RemoteException e) { 17495 } 17496 if (false) { 17497 // For now we won't do this; our memory trimming seems 17498 // to be good enough at this point that destroying 17499 // activities causes more harm than good. 17500 if (curLevel >= ComponentCallbacks2.TRIM_MEMORY_COMPLETE 17501 && app != mHomeProcess && app != mPreviousProcess) { 17502 // Need to do this on its own message because the stack may not 17503 // be in a consistent state at this point. 17504 // For these apps we will also finish their activities 17505 // to help them free memory. 17506 mStackSupervisor.scheduleDestroyAllActivities(app, "trim"); 17507 } 17508 } 17509 } 17510 app.trimMemoryLevel = curLevel; 17511 step++; 17512 if (step >= factor) { 17513 step = 0; 17514 switch (curLevel) { 17515 case ComponentCallbacks2.TRIM_MEMORY_COMPLETE: 17516 curLevel = ComponentCallbacks2.TRIM_MEMORY_MODERATE; 17517 break; 17518 case ComponentCallbacks2.TRIM_MEMORY_MODERATE: 17519 curLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 17520 break; 17521 } 17522 } 17523 } else if (app.curProcState == ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 17524 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_BACKGROUND 17525 && app.thread != null) { 17526 try { 17527 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17528 "Trimming memory of heavy-weight " + app.processName 17529 + " to " + ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 17530 app.thread.scheduleTrimMemory( 17531 ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 17532 } catch (RemoteException e) { 17533 } 17534 } 17535 app.trimMemoryLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 17536 } else { 17537 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 17538 || app.systemNoUi) && app.pendingUiClean) { 17539 // If this application is now in the background and it 17540 // had done UI, then give it the special trim level to 17541 // have it free UI resources. 17542 final int level = ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN; 17543 if (app.trimMemoryLevel < level && app.thread != null) { 17544 try { 17545 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17546 "Trimming memory of bg-ui " + app.processName 17547 + " to " + level); 17548 app.thread.scheduleTrimMemory(level); 17549 } catch (RemoteException e) { 17550 } 17551 } 17552 app.pendingUiClean = false; 17553 } 17554 if (app.trimMemoryLevel < fgTrimLevel && app.thread != null) { 17555 try { 17556 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17557 "Trimming memory of fg " + app.processName 17558 + " to " + fgTrimLevel); 17559 app.thread.scheduleTrimMemory(fgTrimLevel); 17560 } catch (RemoteException e) { 17561 } 17562 } 17563 app.trimMemoryLevel = fgTrimLevel; 17564 } 17565 } 17566 } else { 17567 if (mLowRamStartTime != 0) { 17568 mLowRamTimeSinceLastIdle += now - mLowRamStartTime; 17569 mLowRamStartTime = 0; 17570 } 17571 for (int i=N-1; i>=0; i--) { 17572 ProcessRecord app = mLruProcesses.get(i); 17573 if (allChanged || app.procStateChanged) { 17574 setProcessTrackerStateLocked(app, trackerMemFactor, now); 17575 app.procStateChanged = false; 17576 } 17577 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 17578 || app.systemNoUi) && app.pendingUiClean) { 17579 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN 17580 && app.thread != null) { 17581 try { 17582 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17583 "Trimming memory of ui hidden " + app.processName 17584 + " to " + ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 17585 app.thread.scheduleTrimMemory( 17586 ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 17587 } catch (RemoteException e) { 17588 } 17589 } 17590 app.pendingUiClean = false; 17591 } 17592 app.trimMemoryLevel = 0; 17593 } 17594 } 17595 17596 if (mAlwaysFinishActivities) { 17597 // Need to do this on its own message because the stack may not 17598 // be in a consistent state at this point. 17599 mStackSupervisor.scheduleDestroyAllActivities(null, "always-finish"); 17600 } 17601 17602 if (allChanged) { 17603 requestPssAllProcsLocked(now, false, mProcessStats.isMemFactorLowered()); 17604 } 17605 17606 if (mProcessStats.shouldWriteNowLocked(now)) { 17607 mHandler.post(new Runnable() { 17608 @Override public void run() { 17609 synchronized (ActivityManagerService.this) { 17610 mProcessStats.writeStateAsyncLocked(); 17611 } 17612 } 17613 }); 17614 } 17615 17616 if (DEBUG_OOM_ADJ) { 17617 Slog.d(TAG, "Did OOM ADJ in " + (SystemClock.uptimeMillis()-now) + "ms"); 17618 } 17619 } 17620 17621 final void trimApplications() { 17622 synchronized (this) { 17623 int i; 17624 17625 // First remove any unused application processes whose package 17626 // has been removed. 17627 for (i=mRemovedProcesses.size()-1; i>=0; i--) { 17628 final ProcessRecord app = mRemovedProcesses.get(i); 17629 if (app.activities.size() == 0 17630 && app.curReceiver == null && app.services.size() == 0) { 17631 Slog.i( 17632 TAG, "Exiting empty application process " 17633 + app.processName + " (" 17634 + (app.thread != null ? app.thread.asBinder() : null) 17635 + ")\n"); 17636 if (app.pid > 0 && app.pid != MY_PID) { 17637 app.kill("empty", false); 17638 } else { 17639 try { 17640 app.thread.scheduleExit(); 17641 } catch (Exception e) { 17642 // Ignore exceptions. 17643 } 17644 } 17645 cleanUpApplicationRecordLocked(app, false, true, -1); 17646 mRemovedProcesses.remove(i); 17647 17648 if (app.persistent) { 17649 addAppLocked(app.info, false, null /* ABI override */); 17650 } 17651 } 17652 } 17653 17654 // Now update the oom adj for all processes. 17655 updateOomAdjLocked(); 17656 } 17657 } 17658 17659 /** This method sends the specified signal to each of the persistent apps */ 17660 public void signalPersistentProcesses(int sig) throws RemoteException { 17661 if (sig != Process.SIGNAL_USR1) { 17662 throw new SecurityException("Only SIGNAL_USR1 is allowed"); 17663 } 17664 17665 synchronized (this) { 17666 if (checkCallingPermission(android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES) 17667 != PackageManager.PERMISSION_GRANTED) { 17668 throw new SecurityException("Requires permission " 17669 + android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES); 17670 } 17671 17672 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 17673 ProcessRecord r = mLruProcesses.get(i); 17674 if (r.thread != null && r.persistent) { 17675 Process.sendSignal(r.pid, sig); 17676 } 17677 } 17678 } 17679 } 17680 17681 private void stopProfilerLocked(ProcessRecord proc, int profileType) { 17682 if (proc == null || proc == mProfileProc) { 17683 proc = mProfileProc; 17684 profileType = mProfileType; 17685 clearProfilerLocked(); 17686 } 17687 if (proc == null) { 17688 return; 17689 } 17690 try { 17691 proc.thread.profilerControl(false, null, profileType); 17692 } catch (RemoteException e) { 17693 throw new IllegalStateException("Process disappeared"); 17694 } 17695 } 17696 17697 private void clearProfilerLocked() { 17698 if (mProfileFd != null) { 17699 try { 17700 mProfileFd.close(); 17701 } catch (IOException e) { 17702 } 17703 } 17704 mProfileApp = null; 17705 mProfileProc = null; 17706 mProfileFile = null; 17707 mProfileType = 0; 17708 mAutoStopProfiler = false; 17709 mSamplingInterval = 0; 17710 } 17711 17712 public boolean profileControl(String process, int userId, boolean start, 17713 ProfilerInfo profilerInfo, int profileType) throws RemoteException { 17714 17715 try { 17716 synchronized (this) { 17717 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 17718 // its own permission. 17719 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 17720 != PackageManager.PERMISSION_GRANTED) { 17721 throw new SecurityException("Requires permission " 17722 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 17723 } 17724 17725 if (start && (profilerInfo == null || profilerInfo.profileFd == null)) { 17726 throw new IllegalArgumentException("null profile info or fd"); 17727 } 17728 17729 ProcessRecord proc = null; 17730 if (process != null) { 17731 proc = findProcessLocked(process, userId, "profileControl"); 17732 } 17733 17734 if (start && (proc == null || proc.thread == null)) { 17735 throw new IllegalArgumentException("Unknown process: " + process); 17736 } 17737 17738 if (start) { 17739 stopProfilerLocked(null, 0); 17740 setProfileApp(proc.info, proc.processName, profilerInfo); 17741 mProfileProc = proc; 17742 mProfileType = profileType; 17743 ParcelFileDescriptor fd = profilerInfo.profileFd; 17744 try { 17745 fd = fd.dup(); 17746 } catch (IOException e) { 17747 fd = null; 17748 } 17749 profilerInfo.profileFd = fd; 17750 proc.thread.profilerControl(start, profilerInfo, profileType); 17751 fd = null; 17752 mProfileFd = null; 17753 } else { 17754 stopProfilerLocked(proc, profileType); 17755 if (profilerInfo != null && profilerInfo.profileFd != null) { 17756 try { 17757 profilerInfo.profileFd.close(); 17758 } catch (IOException e) { 17759 } 17760 } 17761 } 17762 17763 return true; 17764 } 17765 } catch (RemoteException e) { 17766 throw new IllegalStateException("Process disappeared"); 17767 } finally { 17768 if (profilerInfo != null && profilerInfo.profileFd != null) { 17769 try { 17770 profilerInfo.profileFd.close(); 17771 } catch (IOException e) { 17772 } 17773 } 17774 } 17775 } 17776 17777 private ProcessRecord findProcessLocked(String process, int userId, String callName) { 17778 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 17779 userId, true, ALLOW_FULL_ONLY, callName, null); 17780 ProcessRecord proc = null; 17781 try { 17782 int pid = Integer.parseInt(process); 17783 synchronized (mPidsSelfLocked) { 17784 proc = mPidsSelfLocked.get(pid); 17785 } 17786 } catch (NumberFormatException e) { 17787 } 17788 17789 if (proc == null) { 17790 ArrayMap<String, SparseArray<ProcessRecord>> all 17791 = mProcessNames.getMap(); 17792 SparseArray<ProcessRecord> procs = all.get(process); 17793 if (procs != null && procs.size() > 0) { 17794 proc = procs.valueAt(0); 17795 if (userId != UserHandle.USER_ALL && proc.userId != userId) { 17796 for (int i=1; i<procs.size(); i++) { 17797 ProcessRecord thisProc = procs.valueAt(i); 17798 if (thisProc.userId == userId) { 17799 proc = thisProc; 17800 break; 17801 } 17802 } 17803 } 17804 } 17805 } 17806 17807 return proc; 17808 } 17809 17810 public boolean dumpHeap(String process, int userId, boolean managed, 17811 String path, ParcelFileDescriptor fd) throws RemoteException { 17812 17813 try { 17814 synchronized (this) { 17815 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 17816 // its own permission (same as profileControl). 17817 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 17818 != PackageManager.PERMISSION_GRANTED) { 17819 throw new SecurityException("Requires permission " 17820 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 17821 } 17822 17823 if (fd == null) { 17824 throw new IllegalArgumentException("null fd"); 17825 } 17826 17827 ProcessRecord proc = findProcessLocked(process, userId, "dumpHeap"); 17828 if (proc == null || proc.thread == null) { 17829 throw new IllegalArgumentException("Unknown process: " + process); 17830 } 17831 17832 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 17833 if (!isDebuggable) { 17834 if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 17835 throw new SecurityException("Process not debuggable: " + proc); 17836 } 17837 } 17838 17839 proc.thread.dumpHeap(managed, path, fd); 17840 fd = null; 17841 return true; 17842 } 17843 } catch (RemoteException e) { 17844 throw new IllegalStateException("Process disappeared"); 17845 } finally { 17846 if (fd != null) { 17847 try { 17848 fd.close(); 17849 } catch (IOException e) { 17850 } 17851 } 17852 } 17853 } 17854 17855 /** In this method we try to acquire our lock to make sure that we have not deadlocked */ 17856 public void monitor() { 17857 synchronized (this) { } 17858 } 17859 17860 void onCoreSettingsChange(Bundle settings) { 17861 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 17862 ProcessRecord processRecord = mLruProcesses.get(i); 17863 try { 17864 if (processRecord.thread != null) { 17865 processRecord.thread.setCoreSettings(settings); 17866 } 17867 } catch (RemoteException re) { 17868 /* ignore */ 17869 } 17870 } 17871 } 17872 17873 // Multi-user methods 17874 17875 /** 17876 * Start user, if its not already running, but don't bring it to foreground. 17877 */ 17878 @Override 17879 public boolean startUserInBackground(final int userId) { 17880 return startUser(userId, /* foreground */ false); 17881 } 17882 17883 /** 17884 * Start user, if its not already running, and bring it to foreground. 17885 */ 17886 boolean startUserInForeground(final int userId, Dialog dlg) { 17887 boolean result = startUser(userId, /* foreground */ true); 17888 dlg.dismiss(); 17889 return result; 17890 } 17891 17892 /** 17893 * Refreshes the list of users related to the current user when either a 17894 * user switch happens or when a new related user is started in the 17895 * background. 17896 */ 17897 private void updateCurrentProfileIdsLocked() { 17898 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17899 mCurrentUserId, false /* enabledOnly */); 17900 int[] currentProfileIds = new int[profiles.size()]; // profiles will not be null 17901 for (int i = 0; i < currentProfileIds.length; i++) { 17902 currentProfileIds[i] = profiles.get(i).id; 17903 } 17904 mCurrentProfileIds = currentProfileIds; 17905 17906 synchronized (mUserProfileGroupIdsSelfLocked) { 17907 mUserProfileGroupIdsSelfLocked.clear(); 17908 final List<UserInfo> users = getUserManagerLocked().getUsers(false); 17909 for (int i = 0; i < users.size(); i++) { 17910 UserInfo user = users.get(i); 17911 if (user.profileGroupId != UserInfo.NO_PROFILE_GROUP_ID) { 17912 mUserProfileGroupIdsSelfLocked.put(user.id, user.profileGroupId); 17913 } 17914 } 17915 } 17916 } 17917 17918 private Set getProfileIdsLocked(int userId) { 17919 Set userIds = new HashSet<Integer>(); 17920 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17921 userId, false /* enabledOnly */); 17922 for (UserInfo user : profiles) { 17923 userIds.add(Integer.valueOf(user.id)); 17924 } 17925 return userIds; 17926 } 17927 17928 @Override 17929 public boolean switchUser(final int userId) { 17930 String userName; 17931 synchronized (this) { 17932 UserInfo userInfo = getUserManagerLocked().getUserInfo(userId); 17933 if (userInfo == null) { 17934 Slog.w(TAG, "No user info for user #" + userId); 17935 return false; 17936 } 17937 if (userInfo.isManagedProfile()) { 17938 Slog.w(TAG, "Cannot switch to User #" + userId + ": not a full user"); 17939 return false; 17940 } 17941 userName = userInfo.name; 17942 } 17943 mHandler.removeMessages(START_USER_SWITCH_MSG); 17944 mHandler.sendMessage(mHandler.obtainMessage(START_USER_SWITCH_MSG, userId, 0, userName)); 17945 return true; 17946 } 17947 17948 private void showUserSwitchDialog(int userId, String userName) { 17949 // The dialog will show and then initiate the user switch by calling startUserInForeground 17950 Dialog d = new UserSwitchingDialog(this, mContext, userId, userName, 17951 true /* above system */); 17952 d.show(); 17953 } 17954 17955 private boolean startUser(final int userId, final boolean foreground) { 17956 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17957 != PackageManager.PERMISSION_GRANTED) { 17958 String msg = "Permission Denial: switchUser() from pid=" 17959 + Binder.getCallingPid() 17960 + ", uid=" + Binder.getCallingUid() 17961 + " requires " + INTERACT_ACROSS_USERS_FULL; 17962 Slog.w(TAG, msg); 17963 throw new SecurityException(msg); 17964 } 17965 17966 if (DEBUG_MU) Slog.i(TAG_MU, "starting userid:" + userId + " fore:" + foreground); 17967 17968 final long ident = Binder.clearCallingIdentity(); 17969 try { 17970 synchronized (this) { 17971 final int oldUserId = mCurrentUserId; 17972 if (oldUserId == userId) { 17973 return true; 17974 } 17975 17976 mStackSupervisor.setLockTaskModeLocked(null, false); 17977 17978 final UserInfo userInfo = getUserManagerLocked().getUserInfo(userId); 17979 if (userInfo == null) { 17980 Slog.w(TAG, "No user info for user #" + userId); 17981 return false; 17982 } 17983 if (foreground && userInfo.isManagedProfile()) { 17984 Slog.w(TAG, "Cannot switch to User #" + userId + ": not a full user"); 17985 return false; 17986 } 17987 17988 if (foreground) { 17989 mWindowManager.startFreezingScreen(R.anim.screen_user_exit, 17990 R.anim.screen_user_enter); 17991 } 17992 17993 boolean needStart = false; 17994 17995 // If the user we are switching to is not currently started, then 17996 // we need to start it now. 17997 if (mStartedUsers.get(userId) == null) { 17998 mStartedUsers.put(userId, new UserStartedState(new UserHandle(userId), false)); 17999 updateStartedUserArrayLocked(); 18000 needStart = true; 18001 } 18002 18003 final Integer userIdInt = Integer.valueOf(userId); 18004 mUserLru.remove(userIdInt); 18005 mUserLru.add(userIdInt); 18006 18007 if (foreground) { 18008 mCurrentUserId = userId; 18009 updateCurrentProfileIdsLocked(); 18010 mWindowManager.setCurrentUser(userId, mCurrentProfileIds); 18011 // Once the internal notion of the active user has switched, we lock the device 18012 // with the option to show the user switcher on the keyguard. 18013 mWindowManager.lockNow(null); 18014 } else { 18015 final Integer currentUserIdInt = Integer.valueOf(mCurrentUserId); 18016 updateCurrentProfileIdsLocked(); 18017 mWindowManager.setCurrentProfileIds(mCurrentProfileIds); 18018 mUserLru.remove(currentUserIdInt); 18019 mUserLru.add(currentUserIdInt); 18020 } 18021 18022 final UserStartedState uss = mStartedUsers.get(userId); 18023 18024 // Make sure user is in the started state. If it is currently 18025 // stopping, we need to knock that off. 18026 if (uss.mState == UserStartedState.STATE_STOPPING) { 18027 // If we are stopping, we haven't sent ACTION_SHUTDOWN, 18028 // so we can just fairly silently bring the user back from 18029 // the almost-dead. 18030 uss.mState = UserStartedState.STATE_RUNNING; 18031 updateStartedUserArrayLocked(); 18032 needStart = true; 18033 } else if (uss.mState == UserStartedState.STATE_SHUTDOWN) { 18034 // This means ACTION_SHUTDOWN has been sent, so we will 18035 // need to treat this as a new boot of the user. 18036 uss.mState = UserStartedState.STATE_BOOTING; 18037 updateStartedUserArrayLocked(); 18038 needStart = true; 18039 } 18040 18041 if (uss.mState == UserStartedState.STATE_BOOTING) { 18042 // Booting up a new user, need to tell system services about it. 18043 // Note that this is on the same handler as scheduling of broadcasts, 18044 // which is important because it needs to go first. 18045 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_START_MSG, userId, 0)); 18046 } 18047 18048 if (foreground) { 18049 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_CURRENT_MSG, userId, 18050 oldUserId)); 18051 mHandler.removeMessages(REPORT_USER_SWITCH_MSG); 18052 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 18053 mHandler.sendMessage(mHandler.obtainMessage(REPORT_USER_SWITCH_MSG, 18054 oldUserId, userId, uss)); 18055 mHandler.sendMessageDelayed(mHandler.obtainMessage(USER_SWITCH_TIMEOUT_MSG, 18056 oldUserId, userId, uss), USER_SWITCH_TIMEOUT); 18057 } 18058 18059 if (needStart) { 18060 // Send USER_STARTED broadcast 18061 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 18062 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 18063 | Intent.FLAG_RECEIVER_FOREGROUND); 18064 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 18065 broadcastIntentLocked(null, null, intent, 18066 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 18067 false, false, MY_PID, Process.SYSTEM_UID, userId); 18068 } 18069 18070 if ((userInfo.flags&UserInfo.FLAG_INITIALIZED) == 0) { 18071 if (userId != UserHandle.USER_OWNER) { 18072 Intent intent = new Intent(Intent.ACTION_USER_INITIALIZE); 18073 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 18074 broadcastIntentLocked(null, null, intent, null, 18075 new IIntentReceiver.Stub() { 18076 public void performReceive(Intent intent, int resultCode, 18077 String data, Bundle extras, boolean ordered, 18078 boolean sticky, int sendingUser) { 18079 onUserInitialized(uss, foreground, oldUserId, userId); 18080 } 18081 }, 0, null, null, null, AppOpsManager.OP_NONE, 18082 true, false, MY_PID, Process.SYSTEM_UID, 18083 userId); 18084 uss.initializing = true; 18085 } else { 18086 getUserManagerLocked().makeInitialized(userInfo.id); 18087 } 18088 } 18089 18090 if (foreground) { 18091 if (!uss.initializing) { 18092 moveUserToForeground(uss, oldUserId, userId); 18093 } 18094 } else { 18095 mStackSupervisor.startBackgroundUserLocked(userId, uss); 18096 } 18097 18098 if (needStart) { 18099 Intent intent = new Intent(Intent.ACTION_USER_STARTING); 18100 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 18101 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 18102 broadcastIntentLocked(null, null, intent, 18103 null, new IIntentReceiver.Stub() { 18104 @Override 18105 public void performReceive(Intent intent, int resultCode, String data, 18106 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 18107 throws RemoteException { 18108 } 18109 }, 0, null, null, 18110 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 18111 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 18112 } 18113 } 18114 } finally { 18115 Binder.restoreCallingIdentity(ident); 18116 } 18117 18118 return true; 18119 } 18120 18121 void sendUserSwitchBroadcastsLocked(int oldUserId, int newUserId) { 18122 long ident = Binder.clearCallingIdentity(); 18123 try { 18124 Intent intent; 18125 if (oldUserId >= 0) { 18126 // Send USER_BACKGROUND broadcast to all profiles of the outgoing user 18127 List<UserInfo> profiles = mUserManager.getProfiles(oldUserId, false); 18128 int count = profiles.size(); 18129 for (int i = 0; i < count; i++) { 18130 int profileUserId = profiles.get(i).id; 18131 intent = new Intent(Intent.ACTION_USER_BACKGROUND); 18132 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 18133 | Intent.FLAG_RECEIVER_FOREGROUND); 18134 intent.putExtra(Intent.EXTRA_USER_HANDLE, profileUserId); 18135 broadcastIntentLocked(null, null, intent, 18136 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 18137 false, false, MY_PID, Process.SYSTEM_UID, profileUserId); 18138 } 18139 } 18140 if (newUserId >= 0) { 18141 // Send USER_FOREGROUND broadcast to all profiles of the incoming user 18142 List<UserInfo> profiles = mUserManager.getProfiles(newUserId, false); 18143 int count = profiles.size(); 18144 for (int i = 0; i < count; i++) { 18145 int profileUserId = profiles.get(i).id; 18146 intent = new Intent(Intent.ACTION_USER_FOREGROUND); 18147 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 18148 | Intent.FLAG_RECEIVER_FOREGROUND); 18149 intent.putExtra(Intent.EXTRA_USER_HANDLE, profileUserId); 18150 broadcastIntentLocked(null, null, intent, 18151 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 18152 false, false, MY_PID, Process.SYSTEM_UID, profileUserId); 18153 } 18154 intent = new Intent(Intent.ACTION_USER_SWITCHED); 18155 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 18156 | Intent.FLAG_RECEIVER_FOREGROUND); 18157 intent.putExtra(Intent.EXTRA_USER_HANDLE, newUserId); 18158 broadcastIntentLocked(null, null, intent, 18159 null, null, 0, null, null, 18160 android.Manifest.permission.MANAGE_USERS, AppOpsManager.OP_NONE, 18161 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 18162 } 18163 } finally { 18164 Binder.restoreCallingIdentity(ident); 18165 } 18166 } 18167 18168 void dispatchUserSwitch(final UserStartedState uss, final int oldUserId, 18169 final int newUserId) { 18170 final int N = mUserSwitchObservers.beginBroadcast(); 18171 if (N > 0) { 18172 final IRemoteCallback callback = new IRemoteCallback.Stub() { 18173 int mCount = 0; 18174 @Override 18175 public void sendResult(Bundle data) throws RemoteException { 18176 synchronized (ActivityManagerService.this) { 18177 if (mCurUserSwitchCallback == this) { 18178 mCount++; 18179 if (mCount == N) { 18180 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 18181 } 18182 } 18183 } 18184 } 18185 }; 18186 synchronized (this) { 18187 uss.switching = true; 18188 mCurUserSwitchCallback = callback; 18189 } 18190 for (int i=0; i<N; i++) { 18191 try { 18192 mUserSwitchObservers.getBroadcastItem(i).onUserSwitching( 18193 newUserId, callback); 18194 } catch (RemoteException e) { 18195 } 18196 } 18197 } else { 18198 synchronized (this) { 18199 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 18200 } 18201 } 18202 mUserSwitchObservers.finishBroadcast(); 18203 } 18204 18205 void timeoutUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 18206 synchronized (this) { 18207 Slog.w(TAG, "User switch timeout: from " + oldUserId + " to " + newUserId); 18208 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 18209 } 18210 } 18211 18212 void sendContinueUserSwitchLocked(UserStartedState uss, int oldUserId, int newUserId) { 18213 mCurUserSwitchCallback = null; 18214 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 18215 mHandler.sendMessage(mHandler.obtainMessage(CONTINUE_USER_SWITCH_MSG, 18216 oldUserId, newUserId, uss)); 18217 } 18218 18219 void onUserInitialized(UserStartedState uss, boolean foreground, int oldUserId, int newUserId) { 18220 synchronized (this) { 18221 if (foreground) { 18222 moveUserToForeground(uss, oldUserId, newUserId); 18223 } 18224 } 18225 18226 completeSwitchAndInitalize(uss, newUserId, true, false); 18227 } 18228 18229 void moveUserToForeground(UserStartedState uss, int oldUserId, int newUserId) { 18230 boolean homeInFront = mStackSupervisor.switchUserLocked(newUserId, uss); 18231 if (homeInFront) { 18232 startHomeActivityLocked(newUserId); 18233 } else { 18234 mStackSupervisor.resumeTopActivitiesLocked(); 18235 } 18236 EventLogTags.writeAmSwitchUser(newUserId); 18237 getUserManagerLocked().userForeground(newUserId); 18238 sendUserSwitchBroadcastsLocked(oldUserId, newUserId); 18239 } 18240 18241 void continueUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 18242 completeSwitchAndInitalize(uss, newUserId, false, true); 18243 } 18244 18245 void completeSwitchAndInitalize(UserStartedState uss, int newUserId, 18246 boolean clearInitializing, boolean clearSwitching) { 18247 boolean unfrozen = false; 18248 synchronized (this) { 18249 if (clearInitializing) { 18250 uss.initializing = false; 18251 getUserManagerLocked().makeInitialized(uss.mHandle.getIdentifier()); 18252 } 18253 if (clearSwitching) { 18254 uss.switching = false; 18255 } 18256 if (!uss.switching && !uss.initializing) { 18257 mWindowManager.stopFreezingScreen(); 18258 unfrozen = true; 18259 } 18260 } 18261 if (unfrozen) { 18262 final int N = mUserSwitchObservers.beginBroadcast(); 18263 for (int i=0; i<N; i++) { 18264 try { 18265 mUserSwitchObservers.getBroadcastItem(i).onUserSwitchComplete(newUserId); 18266 } catch (RemoteException e) { 18267 } 18268 } 18269 mUserSwitchObservers.finishBroadcast(); 18270 } 18271 } 18272 18273 void scheduleStartProfilesLocked() { 18274 if (!mHandler.hasMessages(START_PROFILES_MSG)) { 18275 mHandler.sendMessageDelayed(mHandler.obtainMessage(START_PROFILES_MSG), 18276 DateUtils.SECOND_IN_MILLIS); 18277 } 18278 } 18279 18280 void startProfilesLocked() { 18281 if (DEBUG_MU) Slog.i(TAG_MU, "startProfilesLocked"); 18282 List<UserInfo> profiles = getUserManagerLocked().getProfiles( 18283 mCurrentUserId, false /* enabledOnly */); 18284 List<UserInfo> toStart = new ArrayList<UserInfo>(profiles.size()); 18285 for (UserInfo user : profiles) { 18286 if ((user.flags & UserInfo.FLAG_INITIALIZED) == UserInfo.FLAG_INITIALIZED 18287 && user.id != mCurrentUserId) { 18288 toStart.add(user); 18289 } 18290 } 18291 final int n = toStart.size(); 18292 int i = 0; 18293 for (; i < n && i < (MAX_RUNNING_USERS - 1); ++i) { 18294 startUserInBackground(toStart.get(i).id); 18295 } 18296 if (i < n) { 18297 Slog.w(TAG_MU, "More profiles than MAX_RUNNING_USERS"); 18298 } 18299 } 18300 18301 void finishUserBoot(UserStartedState uss) { 18302 synchronized (this) { 18303 if (uss.mState == UserStartedState.STATE_BOOTING 18304 && mStartedUsers.get(uss.mHandle.getIdentifier()) == uss) { 18305 uss.mState = UserStartedState.STATE_RUNNING; 18306 final int userId = uss.mHandle.getIdentifier(); 18307 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 18308 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 18309 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 18310 broadcastIntentLocked(null, null, intent, 18311 null, null, 0, null, null, 18312 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, AppOpsManager.OP_NONE, 18313 true, false, MY_PID, Process.SYSTEM_UID, userId); 18314 } 18315 } 18316 } 18317 18318 void finishUserSwitch(UserStartedState uss) { 18319 synchronized (this) { 18320 finishUserBoot(uss); 18321 18322 startProfilesLocked(); 18323 18324 int num = mUserLru.size(); 18325 int i = 0; 18326 while (num > MAX_RUNNING_USERS && i < mUserLru.size()) { 18327 Integer oldUserId = mUserLru.get(i); 18328 UserStartedState oldUss = mStartedUsers.get(oldUserId); 18329 if (oldUss == null) { 18330 // Shouldn't happen, but be sane if it does. 18331 mUserLru.remove(i); 18332 num--; 18333 continue; 18334 } 18335 if (oldUss.mState == UserStartedState.STATE_STOPPING 18336 || oldUss.mState == UserStartedState.STATE_SHUTDOWN) { 18337 // This user is already stopping, doesn't count. 18338 num--; 18339 i++; 18340 continue; 18341 } 18342 if (oldUserId == UserHandle.USER_OWNER || oldUserId == mCurrentUserId) { 18343 // Owner and current can't be stopped, but count as running. 18344 i++; 18345 continue; 18346 } 18347 // This is a user to be stopped. 18348 stopUserLocked(oldUserId, null); 18349 num--; 18350 i++; 18351 } 18352 } 18353 } 18354 18355 @Override 18356 public int stopUser(final int userId, final IStopUserCallback callback) { 18357 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 18358 != PackageManager.PERMISSION_GRANTED) { 18359 String msg = "Permission Denial: switchUser() from pid=" 18360 + Binder.getCallingPid() 18361 + ", uid=" + Binder.getCallingUid() 18362 + " requires " + INTERACT_ACROSS_USERS_FULL; 18363 Slog.w(TAG, msg); 18364 throw new SecurityException(msg); 18365 } 18366 if (userId <= 0) { 18367 throw new IllegalArgumentException("Can't stop primary user " + userId); 18368 } 18369 synchronized (this) { 18370 return stopUserLocked(userId, callback); 18371 } 18372 } 18373 18374 private int stopUserLocked(final int userId, final IStopUserCallback callback) { 18375 if (DEBUG_MU) Slog.i(TAG_MU, "stopUserLocked userId=" + userId); 18376 if (mCurrentUserId == userId) { 18377 return ActivityManager.USER_OP_IS_CURRENT; 18378 } 18379 18380 final UserStartedState uss = mStartedUsers.get(userId); 18381 if (uss == null) { 18382 // User is not started, nothing to do... but we do need to 18383 // callback if requested. 18384 if (callback != null) { 18385 mHandler.post(new Runnable() { 18386 @Override 18387 public void run() { 18388 try { 18389 callback.userStopped(userId); 18390 } catch (RemoteException e) { 18391 } 18392 } 18393 }); 18394 } 18395 return ActivityManager.USER_OP_SUCCESS; 18396 } 18397 18398 if (callback != null) { 18399 uss.mStopCallbacks.add(callback); 18400 } 18401 18402 if (uss.mState != UserStartedState.STATE_STOPPING 18403 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 18404 uss.mState = UserStartedState.STATE_STOPPING; 18405 updateStartedUserArrayLocked(); 18406 18407 long ident = Binder.clearCallingIdentity(); 18408 try { 18409 // We are going to broadcast ACTION_USER_STOPPING and then 18410 // once that is done send a final ACTION_SHUTDOWN and then 18411 // stop the user. 18412 final Intent stoppingIntent = new Intent(Intent.ACTION_USER_STOPPING); 18413 stoppingIntent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 18414 stoppingIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 18415 stoppingIntent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 18416 final Intent shutdownIntent = new Intent(Intent.ACTION_SHUTDOWN); 18417 // This is the result receiver for the final shutdown broadcast. 18418 final IIntentReceiver shutdownReceiver = new IIntentReceiver.Stub() { 18419 @Override 18420 public void performReceive(Intent intent, int resultCode, String data, 18421 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 18422 finishUserStop(uss); 18423 } 18424 }; 18425 // This is the result receiver for the initial stopping broadcast. 18426 final IIntentReceiver stoppingReceiver = new IIntentReceiver.Stub() { 18427 @Override 18428 public void performReceive(Intent intent, int resultCode, String data, 18429 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 18430 // On to the next. 18431 synchronized (ActivityManagerService.this) { 18432 if (uss.mState != UserStartedState.STATE_STOPPING) { 18433 // Whoops, we are being started back up. Abort, abort! 18434 return; 18435 } 18436 uss.mState = UserStartedState.STATE_SHUTDOWN; 18437 } 18438 mBatteryStatsService.noteEvent( 18439 BatteryStats.HistoryItem.EVENT_USER_RUNNING_FINISH, 18440 Integer.toString(userId), userId); 18441 mSystemServiceManager.stopUser(userId); 18442 broadcastIntentLocked(null, null, shutdownIntent, 18443 null, shutdownReceiver, 0, null, null, null, AppOpsManager.OP_NONE, 18444 true, false, MY_PID, Process.SYSTEM_UID, userId); 18445 } 18446 }; 18447 // Kick things off. 18448 broadcastIntentLocked(null, null, stoppingIntent, 18449 null, stoppingReceiver, 0, null, null, 18450 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 18451 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 18452 } finally { 18453 Binder.restoreCallingIdentity(ident); 18454 } 18455 } 18456 18457 return ActivityManager.USER_OP_SUCCESS; 18458 } 18459 18460 void finishUserStop(UserStartedState uss) { 18461 final int userId = uss.mHandle.getIdentifier(); 18462 boolean stopped; 18463 ArrayList<IStopUserCallback> callbacks; 18464 synchronized (this) { 18465 callbacks = new ArrayList<IStopUserCallback>(uss.mStopCallbacks); 18466 if (mStartedUsers.get(userId) != uss) { 18467 stopped = false; 18468 } else if (uss.mState != UserStartedState.STATE_SHUTDOWN) { 18469 stopped = false; 18470 } else { 18471 stopped = true; 18472 // User can no longer run. 18473 mStartedUsers.remove(userId); 18474 mUserLru.remove(Integer.valueOf(userId)); 18475 updateStartedUserArrayLocked(); 18476 18477 // Clean up all state and processes associated with the user. 18478 // Kill all the processes for the user. 18479 forceStopUserLocked(userId, "finish user"); 18480 } 18481 18482 // Explicitly remove the old information in mRecentTasks. 18483 removeRecentTasksForUserLocked(userId); 18484 } 18485 18486 for (int i=0; i<callbacks.size(); i++) { 18487 try { 18488 if (stopped) callbacks.get(i).userStopped(userId); 18489 else callbacks.get(i).userStopAborted(userId); 18490 } catch (RemoteException e) { 18491 } 18492 } 18493 18494 if (stopped) { 18495 mSystemServiceManager.cleanupUser(userId); 18496 synchronized (this) { 18497 mStackSupervisor.removeUserLocked(userId); 18498 } 18499 } 18500 } 18501 18502 @Override 18503 public UserInfo getCurrentUser() { 18504 if ((checkCallingPermission(INTERACT_ACROSS_USERS) 18505 != PackageManager.PERMISSION_GRANTED) && ( 18506 checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 18507 != PackageManager.PERMISSION_GRANTED)) { 18508 String msg = "Permission Denial: getCurrentUser() from pid=" 18509 + Binder.getCallingPid() 18510 + ", uid=" + Binder.getCallingUid() 18511 + " requires " + INTERACT_ACROSS_USERS; 18512 Slog.w(TAG, msg); 18513 throw new SecurityException(msg); 18514 } 18515 synchronized (this) { 18516 return getUserManagerLocked().getUserInfo(mCurrentUserId); 18517 } 18518 } 18519 18520 int getCurrentUserIdLocked() { 18521 return mCurrentUserId; 18522 } 18523 18524 @Override 18525 public boolean isUserRunning(int userId, boolean orStopped) { 18526 if (checkCallingPermission(INTERACT_ACROSS_USERS) 18527 != PackageManager.PERMISSION_GRANTED) { 18528 String msg = "Permission Denial: isUserRunning() from pid=" 18529 + Binder.getCallingPid() 18530 + ", uid=" + Binder.getCallingUid() 18531 + " requires " + INTERACT_ACROSS_USERS; 18532 Slog.w(TAG, msg); 18533 throw new SecurityException(msg); 18534 } 18535 synchronized (this) { 18536 return isUserRunningLocked(userId, orStopped); 18537 } 18538 } 18539 18540 boolean isUserRunningLocked(int userId, boolean orStopped) { 18541 UserStartedState state = mStartedUsers.get(userId); 18542 if (state == null) { 18543 return false; 18544 } 18545 if (orStopped) { 18546 return true; 18547 } 18548 return state.mState != UserStartedState.STATE_STOPPING 18549 && state.mState != UserStartedState.STATE_SHUTDOWN; 18550 } 18551 18552 @Override 18553 public int[] getRunningUserIds() { 18554 if (checkCallingPermission(INTERACT_ACROSS_USERS) 18555 != PackageManager.PERMISSION_GRANTED) { 18556 String msg = "Permission Denial: isUserRunning() from pid=" 18557 + Binder.getCallingPid() 18558 + ", uid=" + Binder.getCallingUid() 18559 + " requires " + INTERACT_ACROSS_USERS; 18560 Slog.w(TAG, msg); 18561 throw new SecurityException(msg); 18562 } 18563 synchronized (this) { 18564 return mStartedUserArray; 18565 } 18566 } 18567 18568 private void updateStartedUserArrayLocked() { 18569 int num = 0; 18570 for (int i=0; i<mStartedUsers.size(); i++) { 18571 UserStartedState uss = mStartedUsers.valueAt(i); 18572 // This list does not include stopping users. 18573 if (uss.mState != UserStartedState.STATE_STOPPING 18574 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 18575 num++; 18576 } 18577 } 18578 mStartedUserArray = new int[num]; 18579 num = 0; 18580 for (int i=0; i<mStartedUsers.size(); i++) { 18581 UserStartedState uss = mStartedUsers.valueAt(i); 18582 if (uss.mState != UserStartedState.STATE_STOPPING 18583 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 18584 mStartedUserArray[num] = mStartedUsers.keyAt(i); 18585 num++; 18586 } 18587 } 18588 } 18589 18590 @Override 18591 public void registerUserSwitchObserver(IUserSwitchObserver observer) { 18592 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 18593 != PackageManager.PERMISSION_GRANTED) { 18594 String msg = "Permission Denial: registerUserSwitchObserver() from pid=" 18595 + Binder.getCallingPid() 18596 + ", uid=" + Binder.getCallingUid() 18597 + " requires " + INTERACT_ACROSS_USERS_FULL; 18598 Slog.w(TAG, msg); 18599 throw new SecurityException(msg); 18600 } 18601 18602 mUserSwitchObservers.register(observer); 18603 } 18604 18605 @Override 18606 public void unregisterUserSwitchObserver(IUserSwitchObserver observer) { 18607 mUserSwitchObservers.unregister(observer); 18608 } 18609 18610 private boolean userExists(int userId) { 18611 if (userId == 0) { 18612 return true; 18613 } 18614 UserManagerService ums = getUserManagerLocked(); 18615 return ums != null ? (ums.getUserInfo(userId) != null) : false; 18616 } 18617 18618 int[] getUsersLocked() { 18619 UserManagerService ums = getUserManagerLocked(); 18620 return ums != null ? ums.getUserIds() : new int[] { 0 }; 18621 } 18622 18623 UserManagerService getUserManagerLocked() { 18624 if (mUserManager == null) { 18625 IBinder b = ServiceManager.getService(Context.USER_SERVICE); 18626 mUserManager = (UserManagerService)IUserManager.Stub.asInterface(b); 18627 } 18628 return mUserManager; 18629 } 18630 18631 private int applyUserId(int uid, int userId) { 18632 return UserHandle.getUid(userId, uid); 18633 } 18634 18635 ApplicationInfo getAppInfoForUser(ApplicationInfo info, int userId) { 18636 if (info == null) return null; 18637 ApplicationInfo newInfo = new ApplicationInfo(info); 18638 newInfo.uid = applyUserId(info.uid, userId); 18639 newInfo.dataDir = USER_DATA_DIR + userId + "/" 18640 + info.packageName; 18641 return newInfo; 18642 } 18643 18644 ActivityInfo getActivityInfoForUser(ActivityInfo aInfo, int userId) { 18645 if (aInfo == null 18646 || (userId < 1 && aInfo.applicationInfo.uid < UserHandle.PER_USER_RANGE)) { 18647 return aInfo; 18648 } 18649 18650 ActivityInfo info = new ActivityInfo(aInfo); 18651 info.applicationInfo = getAppInfoForUser(info.applicationInfo, userId); 18652 return info; 18653 } 18654 18655 private final class LocalService extends ActivityManagerInternal { 18656 @Override 18657 public void goingToSleep() { 18658 ActivityManagerService.this.goingToSleep(); 18659 } 18660 18661 @Override 18662 public void wakingUp() { 18663 ActivityManagerService.this.wakingUp(); 18664 } 18665 18666 @Override 18667 public int startIsolatedProcess(String entryPoint, String[] entryPointArgs, 18668 String processName, String abiOverride, int uid, Runnable crashHandler) { 18669 return ActivityManagerService.this.startIsolatedProcess(entryPoint, entryPointArgs, 18670 processName, abiOverride, uid, crashHandler); 18671 } 18672 } 18673 18674 /** 18675 * An implementation of IAppTask, that allows an app to manage its own tasks via 18676 * {@link android.app.ActivityManager.AppTask}. We keep track of the callingUid to ensure that 18677 * only the process that calls getAppTasks() can call the AppTask methods. 18678 */ 18679 class AppTaskImpl extends IAppTask.Stub { 18680 private int mTaskId; 18681 private int mCallingUid; 18682 18683 public AppTaskImpl(int taskId, int callingUid) { 18684 mTaskId = taskId; 18685 mCallingUid = callingUid; 18686 } 18687 18688 private void checkCaller() { 18689 if (mCallingUid != Binder.getCallingUid()) { 18690 throw new SecurityException("Caller " + mCallingUid 18691 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 18692 } 18693 } 18694 18695 @Override 18696 public void finishAndRemoveTask() { 18697 checkCaller(); 18698 18699 synchronized (ActivityManagerService.this) { 18700 long origId = Binder.clearCallingIdentity(); 18701 try { 18702 TaskRecord tr = recentTaskForIdLocked(mTaskId); 18703 if (tr == null) { 18704 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 18705 } 18706 // Only kill the process if we are not a new document 18707 int flags = tr.getBaseIntent().getFlags(); 18708 boolean isDocument = (flags & Intent.FLAG_ACTIVITY_NEW_DOCUMENT) == 18709 Intent.FLAG_ACTIVITY_NEW_DOCUMENT; 18710 removeTaskByIdLocked(mTaskId, 18711 !isDocument ? ActivityManager.REMOVE_TASK_KILL_PROCESS : 0); 18712 } finally { 18713 Binder.restoreCallingIdentity(origId); 18714 } 18715 } 18716 } 18717 18718 @Override 18719 public ActivityManager.RecentTaskInfo getTaskInfo() { 18720 checkCaller(); 18721 18722 synchronized (ActivityManagerService.this) { 18723 long origId = Binder.clearCallingIdentity(); 18724 try { 18725 TaskRecord tr = recentTaskForIdLocked(mTaskId); 18726 if (tr == null) { 18727 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 18728 } 18729 return createRecentTaskInfoFromTaskRecord(tr); 18730 } finally { 18731 Binder.restoreCallingIdentity(origId); 18732 } 18733 } 18734 } 18735 18736 @Override 18737 public void moveToFront() { 18738 checkCaller(); 18739 18740 final TaskRecord tr; 18741 synchronized (ActivityManagerService.this) { 18742 tr = recentTaskForIdLocked(mTaskId); 18743 if (tr == null) { 18744 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 18745 } 18746 if (tr.getRootActivity() != null) { 18747 long origId = Binder.clearCallingIdentity(); 18748 try { 18749 moveTaskToFrontLocked(tr.taskId, 0, null); 18750 return; 18751 } finally { 18752 Binder.restoreCallingIdentity(origId); 18753 } 18754 } 18755 } 18756 18757 startActivityFromRecentsInner(tr.taskId, null); 18758 } 18759 18760 @Override 18761 public int startActivity(IBinder whoThread, String callingPackage, 18762 Intent intent, String resolvedType, Bundle options) { 18763 checkCaller(); 18764 18765 int callingUser = UserHandle.getCallingUserId(); 18766 TaskRecord tr; 18767 IApplicationThread appThread; 18768 synchronized (ActivityManagerService.this) { 18769 tr = recentTaskForIdLocked(mTaskId); 18770 if (tr == null) { 18771 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 18772 } 18773 appThread = ApplicationThreadNative.asInterface(whoThread); 18774 if (appThread == null) { 18775 throw new IllegalArgumentException("Bad app thread " + appThread); 18776 } 18777 } 18778 return mStackSupervisor.startActivityMayWait(appThread, -1, callingPackage, intent, 18779 resolvedType, null, null, null, null, 0, 0, null, null, 18780 null, options, callingUser, null, tr); 18781 } 18782 18783 @Override 18784 public void setExcludeFromRecents(boolean exclude) { 18785 checkCaller(); 18786 18787 synchronized (ActivityManagerService.this) { 18788 long origId = Binder.clearCallingIdentity(); 18789 try { 18790 TaskRecord tr = recentTaskForIdLocked(mTaskId); 18791 if (tr == null) { 18792 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 18793 } 18794 Intent intent = tr.getBaseIntent(); 18795 if (exclude) { 18796 intent.addFlags(Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 18797 } else { 18798 intent.setFlags(intent.getFlags() 18799 & ~Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 18800 } 18801 } finally { 18802 Binder.restoreCallingIdentity(origId); 18803 } 18804 } 18805 } 18806 } 18807} 18808