ActivityManagerService.java revision 83bb610fad994b9046acc3feeba9d9a5264fd918
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.IActivityContainer; 37import android.app.IActivityContainerCallback; 38import android.app.IAppTask; 39import android.app.admin.DevicePolicyManager; 40import android.app.usage.UsageEvents; 41import android.app.usage.UsageStatsManagerInternal; 42import android.appwidget.AppWidgetManager; 43import android.content.res.Resources; 44import android.graphics.Bitmap; 45import android.graphics.Point; 46import android.graphics.Rect; 47import android.os.BatteryStats; 48import android.os.PersistableBundle; 49import android.service.voice.IVoiceInteractionSession; 50import android.util.ArrayMap; 51import android.util.ArraySet; 52import android.util.SparseIntArray; 53 54import com.android.internal.R; 55import com.android.internal.annotations.GuardedBy; 56import com.android.internal.app.IAppOpsService; 57import com.android.internal.app.IVoiceInteractor; 58import com.android.internal.app.ProcessMap; 59import com.android.internal.app.ProcessStats; 60import com.android.internal.content.PackageMonitor; 61import com.android.internal.os.BackgroundThread; 62import com.android.internal.os.BatteryStatsImpl; 63import com.android.internal.os.ProcessCpuTracker; 64import com.android.internal.os.TransferPipe; 65import com.android.internal.os.Zygote; 66import com.android.internal.util.FastPrintWriter; 67import com.android.internal.util.FastXmlSerializer; 68import com.android.internal.util.MemInfoReader; 69import com.android.internal.util.Preconditions; 70import com.android.server.AppOpsService; 71import com.android.server.AttributeCache; 72import com.android.server.IntentResolver; 73import com.android.server.LocalServices; 74import com.android.server.ServiceThread; 75import com.android.server.SystemService; 76import com.android.server.SystemServiceManager; 77import com.android.server.Watchdog; 78import com.android.server.am.ActivityStack.ActivityState; 79import com.android.server.firewall.IntentFirewall; 80import com.android.server.pm.UserManagerService; 81import com.android.server.wm.AppTransition; 82import com.android.server.wm.WindowManagerService; 83import com.google.android.collect.Lists; 84import com.google.android.collect.Maps; 85 86import libcore.io.IoUtils; 87 88import org.xmlpull.v1.XmlPullParser; 89import org.xmlpull.v1.XmlPullParserException; 90import org.xmlpull.v1.XmlSerializer; 91 92import android.app.Activity; 93import android.app.ActivityManager; 94import android.app.ActivityManager.RunningTaskInfo; 95import android.app.ActivityManager.StackInfo; 96import android.app.ActivityManagerInternal; 97import android.app.ActivityManagerNative; 98import android.app.ActivityOptions; 99import android.app.ActivityThread; 100import android.app.AlertDialog; 101import android.app.AppGlobals; 102import android.app.ApplicationErrorReport; 103import android.app.Dialog; 104import android.app.IActivityController; 105import android.app.IApplicationThread; 106import android.app.IInstrumentationWatcher; 107import android.app.INotificationManager; 108import android.app.IProcessObserver; 109import android.app.IServiceConnection; 110import android.app.IStopUserCallback; 111import android.app.IUiAutomationConnection; 112import android.app.IUserSwitchObserver; 113import android.app.Instrumentation; 114import android.app.Notification; 115import android.app.NotificationManager; 116import android.app.PendingIntent; 117import android.app.backup.IBackupManager; 118import android.content.ActivityNotFoundException; 119import android.content.BroadcastReceiver; 120import android.content.ClipData; 121import android.content.ComponentCallbacks2; 122import android.content.ComponentName; 123import android.content.ContentProvider; 124import android.content.ContentResolver; 125import android.content.Context; 126import android.content.DialogInterface; 127import android.content.IContentProvider; 128import android.content.IIntentReceiver; 129import android.content.IIntentSender; 130import android.content.Intent; 131import android.content.IntentFilter; 132import android.content.IntentSender; 133import android.content.pm.ActivityInfo; 134import android.content.pm.ApplicationInfo; 135import android.content.pm.ConfigurationInfo; 136import android.content.pm.IPackageDataObserver; 137import android.content.pm.IPackageManager; 138import android.content.pm.InstrumentationInfo; 139import android.content.pm.PackageInfo; 140import android.content.pm.PackageManager; 141import android.content.pm.ParceledListSlice; 142import android.content.pm.UserInfo; 143import android.content.pm.PackageManager.NameNotFoundException; 144import android.content.pm.PathPermission; 145import android.content.pm.ProviderInfo; 146import android.content.pm.ResolveInfo; 147import android.content.pm.ServiceInfo; 148import android.content.res.CompatibilityInfo; 149import android.content.res.Configuration; 150import android.net.Proxy; 151import android.net.ProxyInfo; 152import android.net.Uri; 153import android.os.Binder; 154import android.os.Build; 155import android.os.Bundle; 156import android.os.Debug; 157import android.os.DropBoxManager; 158import android.os.Environment; 159import android.os.FactoryTest; 160import android.os.FileObserver; 161import android.os.FileUtils; 162import android.os.Handler; 163import android.os.IBinder; 164import android.os.IPermissionController; 165import android.os.IRemoteCallback; 166import android.os.IUserManager; 167import android.os.Looper; 168import android.os.Message; 169import android.os.Parcel; 170import android.os.ParcelFileDescriptor; 171import android.os.Process; 172import android.os.RemoteCallbackList; 173import android.os.RemoteException; 174import android.os.SELinux; 175import android.os.ServiceManager; 176import android.os.StrictMode; 177import android.os.SystemClock; 178import android.os.SystemProperties; 179import android.os.UpdateLock; 180import android.os.UserHandle; 181import android.provider.Settings; 182import android.text.format.DateUtils; 183import android.text.format.Time; 184import android.util.AtomicFile; 185import android.util.EventLog; 186import android.util.Log; 187import android.util.Pair; 188import android.util.PrintWriterPrinter; 189import android.util.Slog; 190import android.util.SparseArray; 191import android.util.TimeUtils; 192import android.util.Xml; 193import android.view.Gravity; 194import android.view.LayoutInflater; 195import android.view.View; 196import android.view.WindowManager; 197 198import java.io.BufferedInputStream; 199import java.io.BufferedOutputStream; 200import java.io.DataInputStream; 201import java.io.DataOutputStream; 202import java.io.File; 203import java.io.FileDescriptor; 204import java.io.FileInputStream; 205import java.io.FileNotFoundException; 206import java.io.FileOutputStream; 207import java.io.IOException; 208import java.io.InputStreamReader; 209import java.io.PrintWriter; 210import java.io.StringWriter; 211import java.lang.ref.WeakReference; 212import java.util.ArrayList; 213import java.util.Arrays; 214import java.util.Collections; 215import java.util.Comparator; 216import java.util.HashMap; 217import java.util.HashSet; 218import java.util.Iterator; 219import java.util.List; 220import java.util.Locale; 221import java.util.Map; 222import java.util.Set; 223import java.util.concurrent.atomic.AtomicBoolean; 224import java.util.concurrent.atomic.AtomicLong; 225 226public final class ActivityManagerService extends ActivityManagerNative 227 implements Watchdog.Monitor, BatteryStatsImpl.BatteryCallback { 228 229 private static final String USER_DATA_DIR = "/data/user/"; 230 // File that stores last updated system version and called preboot receivers 231 static final String CALLED_PRE_BOOTS_FILENAME = "called_pre_boots.dat"; 232 233 static final String TAG = "ActivityManager"; 234 static final String TAG_MU = "ActivityManagerServiceMU"; 235 static final boolean DEBUG = false; 236 static final boolean localLOGV = DEBUG; 237 static final boolean DEBUG_BACKUP = localLOGV || false; 238 static final boolean DEBUG_BROADCAST = localLOGV || false; 239 static final boolean DEBUG_BROADCAST_LIGHT = DEBUG_BROADCAST || false; 240 static final boolean DEBUG_BACKGROUND_BROADCAST = DEBUG_BROADCAST || false; 241 static final boolean DEBUG_CLEANUP = localLOGV || false; 242 static final boolean DEBUG_CONFIGURATION = localLOGV || false; 243 static final boolean DEBUG_FOCUS = false; 244 static final boolean DEBUG_IMMERSIVE = localLOGV || false; 245 static final boolean DEBUG_MU = localLOGV || false; 246 static final boolean DEBUG_OOM_ADJ = localLOGV || false; 247 static final boolean DEBUG_LRU = localLOGV || false; 248 static final boolean DEBUG_PAUSE = localLOGV || false; 249 static final boolean DEBUG_POWER = localLOGV || false; 250 static final boolean DEBUG_POWER_QUICK = DEBUG_POWER || false; 251 static final boolean DEBUG_PROCESS_OBSERVERS = localLOGV || false; 252 static final boolean DEBUG_PROCESSES = localLOGV || false; 253 static final boolean DEBUG_PROVIDER = localLOGV || false; 254 static final boolean DEBUG_RESULTS = localLOGV || false; 255 static final boolean DEBUG_SERVICE = localLOGV || false; 256 static final boolean DEBUG_SERVICE_EXECUTING = localLOGV || false; 257 static final boolean DEBUG_STACK = localLOGV || false; 258 static final boolean DEBUG_SWITCH = localLOGV || false; 259 static final boolean DEBUG_TASKS = localLOGV || false; 260 static final boolean DEBUG_THUMBNAILS = localLOGV || false; 261 static final boolean DEBUG_TRANSITION = localLOGV || false; 262 static final boolean DEBUG_URI_PERMISSION = localLOGV || false; 263 static final boolean DEBUG_USER_LEAVING = localLOGV || false; 264 static final boolean DEBUG_VISBILITY = localLOGV || false; 265 static final boolean DEBUG_PSS = localLOGV || false; 266 static final boolean DEBUG_LOCKSCREEN = localLOGV || false; 267 static final boolean DEBUG_RECENTS = localLOGV || false; 268 static final boolean VALIDATE_TOKENS = false; 269 static final boolean SHOW_ACTIVITY_START_TIME = true; 270 271 // Control over CPU and battery monitoring. 272 static final long BATTERY_STATS_TIME = 30*60*1000; // write battery stats every 30 minutes. 273 static final boolean MONITOR_CPU_USAGE = true; 274 static final long MONITOR_CPU_MIN_TIME = 5*1000; // don't sample cpu less than every 5 seconds. 275 static final long MONITOR_CPU_MAX_TIME = 0x0fffffff; // wait possibly forever for next cpu sample. 276 static final boolean MONITOR_THREAD_CPU_USAGE = false; 277 278 // The flags that are set for all calls we make to the package manager. 279 static final int STOCK_PM_FLAGS = PackageManager.GET_SHARED_LIBRARY_FILES; 280 281 private static final String SYSTEM_DEBUGGABLE = "ro.debuggable"; 282 283 static final boolean IS_USER_BUILD = "user".equals(Build.TYPE); 284 285 // Maximum number of recent tasks that we can remember. 286 static final int MAX_RECENT_TASKS = ActivityManager.isLowRamDeviceStatic() ? 100 : 200; 287 288 // Maximum number recent bitmaps to keep in memory. 289 static final int MAX_RECENT_BITMAPS = 5; 290 291 // Amount of time after a call to stopAppSwitches() during which we will 292 // prevent further untrusted switches from happening. 293 static final long APP_SWITCH_DELAY_TIME = 5*1000; 294 295 // How long we wait for a launched process to attach to the activity manager 296 // before we decide it's never going to come up for real. 297 static final int PROC_START_TIMEOUT = 10*1000; 298 299 // How long we wait for a launched process to attach to the activity manager 300 // before we decide it's never going to come up for real, when the process was 301 // started with a wrapper for instrumentation (such as Valgrind) because it 302 // could take much longer than usual. 303 static final int PROC_START_TIMEOUT_WITH_WRAPPER = 1200*1000; 304 305 // How long to wait after going idle before forcing apps to GC. 306 static final int GC_TIMEOUT = 5*1000; 307 308 // The minimum amount of time between successive GC requests for a process. 309 static final int GC_MIN_INTERVAL = 60*1000; 310 311 // The minimum amount of time between successive PSS requests for a process. 312 static final int FULL_PSS_MIN_INTERVAL = 10*60*1000; 313 314 // The minimum amount of time between successive PSS requests for a process 315 // when the request is due to the memory state being lowered. 316 static final int FULL_PSS_LOWERED_INTERVAL = 2*60*1000; 317 318 // The rate at which we check for apps using excessive power -- 15 mins. 319 static final int POWER_CHECK_DELAY = (DEBUG_POWER_QUICK ? 2 : 15) * 60*1000; 320 321 // The minimum sample duration we will allow before deciding we have 322 // enough data on wake locks to start killing things. 323 static final int WAKE_LOCK_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 324 325 // The minimum sample duration we will allow before deciding we have 326 // enough data on CPU usage to start killing things. 327 static final int CPU_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 328 329 // How long we allow a receiver to run before giving up on it. 330 static final int BROADCAST_FG_TIMEOUT = 10*1000; 331 static final int BROADCAST_BG_TIMEOUT = 60*1000; 332 333 // How long we wait until we timeout on key dispatching. 334 static final int KEY_DISPATCHING_TIMEOUT = 5*1000; 335 336 // How long we wait until we timeout on key dispatching during instrumentation. 337 static final int INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT = 60*1000; 338 339 // Amount of time we wait for observers to handle a user switch before 340 // giving up on them and unfreezing the screen. 341 static final int USER_SWITCH_TIMEOUT = 2*1000; 342 343 // Maximum number of users we allow to be running at a time. 344 static final int MAX_RUNNING_USERS = 3; 345 346 // How long to wait in getAssistContextExtras for the activity and foreground services 347 // to respond with the result. 348 static final int PENDING_ASSIST_EXTRAS_TIMEOUT = 500; 349 350 // Maximum number of persisted Uri grants a package is allowed 351 static final int MAX_PERSISTED_URI_GRANTS = 128; 352 353 static final int MY_PID = Process.myPid(); 354 355 static final String[] EMPTY_STRING_ARRAY = new String[0]; 356 357 // How many bytes to write into the dropbox log before truncating 358 static final int DROPBOX_MAX_SIZE = 256 * 1024; 359 360 // Access modes for handleIncomingUser. 361 static final int ALLOW_NON_FULL = 0; 362 static final int ALLOW_NON_FULL_IN_PROFILE = 1; 363 static final int ALLOW_FULL_ONLY = 2; 364 365 static final int LAST_PREBOOT_DELIVERED_FILE_VERSION = 10000; 366 367 /** All system services */ 368 SystemServiceManager mSystemServiceManager; 369 370 /** Run all ActivityStacks through this */ 371 ActivityStackSupervisor mStackSupervisor; 372 373 public IntentFirewall mIntentFirewall; 374 375 // Whether we should show our dialogs (ANR, crash, etc) or just perform their 376 // default actuion automatically. Important for devices without direct input 377 // devices. 378 private boolean mShowDialogs = true; 379 380 BroadcastQueue mFgBroadcastQueue; 381 BroadcastQueue mBgBroadcastQueue; 382 // Convenient for easy iteration over the queues. Foreground is first 383 // so that dispatch of foreground broadcasts gets precedence. 384 final BroadcastQueue[] mBroadcastQueues = new BroadcastQueue[2]; 385 386 BroadcastQueue broadcastQueueForIntent(Intent intent) { 387 final boolean isFg = (intent.getFlags() & Intent.FLAG_RECEIVER_FOREGROUND) != 0; 388 if (DEBUG_BACKGROUND_BROADCAST) { 389 Slog.i(TAG, "Broadcast intent " + intent + " on " 390 + (isFg ? "foreground" : "background") 391 + " queue"); 392 } 393 return (isFg) ? mFgBroadcastQueue : mBgBroadcastQueue; 394 } 395 396 BroadcastRecord broadcastRecordForReceiverLocked(IBinder receiver) { 397 for (BroadcastQueue queue : mBroadcastQueues) { 398 BroadcastRecord r = queue.getMatchingOrderedReceiver(receiver); 399 if (r != null) { 400 return r; 401 } 402 } 403 return null; 404 } 405 406 /** 407 * Activity we have told the window manager to have key focus. 408 */ 409 ActivityRecord mFocusedActivity = null; 410 411 /** 412 * List of intents that were used to start the most recent tasks. 413 */ 414 ArrayList<TaskRecord> mRecentTasks; 415 ArraySet<TaskRecord> mTmpRecents = new ArraySet<TaskRecord>(); 416 417 /** 418 * For addAppTask: cached of the last activity component that was added. 419 */ 420 ComponentName mLastAddedTaskComponent; 421 422 /** 423 * For addAppTask: cached of the last activity uid that was added. 424 */ 425 int mLastAddedTaskUid; 426 427 /** 428 * For addAppTask: cached of the last ActivityInfo that was added. 429 */ 430 ActivityInfo mLastAddedTaskActivity; 431 432 public class PendingAssistExtras extends Binder implements Runnable { 433 public final ActivityRecord activity; 434 public boolean haveResult = false; 435 public Bundle result = null; 436 public PendingAssistExtras(ActivityRecord _activity) { 437 activity = _activity; 438 } 439 @Override 440 public void run() { 441 Slog.w(TAG, "getAssistContextExtras failed: timeout retrieving from " + activity); 442 synchronized (this) { 443 haveResult = true; 444 notifyAll(); 445 } 446 } 447 } 448 449 final ArrayList<PendingAssistExtras> mPendingAssistExtras 450 = new ArrayList<PendingAssistExtras>(); 451 452 /** 453 * Process management. 454 */ 455 final ProcessList mProcessList = new ProcessList(); 456 457 /** 458 * All of the applications we currently have running organized by name. 459 * The keys are strings of the application package name (as 460 * returned by the package manager), and the keys are ApplicationRecord 461 * objects. 462 */ 463 final ProcessMap<ProcessRecord> mProcessNames = new ProcessMap<ProcessRecord>(); 464 465 /** 466 * Tracking long-term execution of processes to look for abuse and other 467 * bad app behavior. 468 */ 469 final ProcessStatsService mProcessStats; 470 471 /** 472 * The currently running isolated processes. 473 */ 474 final SparseArray<ProcessRecord> mIsolatedProcesses = new SparseArray<ProcessRecord>(); 475 476 /** 477 * Counter for assigning isolated process uids, to avoid frequently reusing the 478 * same ones. 479 */ 480 int mNextIsolatedProcessUid = 0; 481 482 /** 483 * The currently running heavy-weight process, if any. 484 */ 485 ProcessRecord mHeavyWeightProcess = null; 486 487 /** 488 * The last time that various processes have crashed. 489 */ 490 final ProcessMap<Long> mProcessCrashTimes = new ProcessMap<Long>(); 491 492 /** 493 * Information about a process that is currently marked as bad. 494 */ 495 static final class BadProcessInfo { 496 BadProcessInfo(long time, String shortMsg, String longMsg, String stack) { 497 this.time = time; 498 this.shortMsg = shortMsg; 499 this.longMsg = longMsg; 500 this.stack = stack; 501 } 502 503 final long time; 504 final String shortMsg; 505 final String longMsg; 506 final String stack; 507 } 508 509 /** 510 * Set of applications that we consider to be bad, and will reject 511 * incoming broadcasts from (which the user has no control over). 512 * Processes are added to this set when they have crashed twice within 513 * a minimum amount of time; they are removed from it when they are 514 * later restarted (hopefully due to some user action). The value is the 515 * time it was added to the list. 516 */ 517 final ProcessMap<BadProcessInfo> mBadProcesses = new ProcessMap<BadProcessInfo>(); 518 519 /** 520 * All of the processes we currently have running organized by pid. 521 * The keys are the pid running the application. 522 * 523 * <p>NOTE: This object is protected by its own lock, NOT the global 524 * activity manager lock! 525 */ 526 final SparseArray<ProcessRecord> mPidsSelfLocked = new SparseArray<ProcessRecord>(); 527 528 /** 529 * All of the processes that have been forced to be foreground. The key 530 * is the pid of the caller who requested it (we hold a death 531 * link on it). 532 */ 533 abstract class ForegroundToken implements IBinder.DeathRecipient { 534 int pid; 535 IBinder token; 536 } 537 final SparseArray<ForegroundToken> mForegroundProcesses = new SparseArray<ForegroundToken>(); 538 539 /** 540 * List of records for processes that someone had tried to start before the 541 * system was ready. We don't start them at that point, but ensure they 542 * are started by the time booting is complete. 543 */ 544 final ArrayList<ProcessRecord> mProcessesOnHold = new ArrayList<ProcessRecord>(); 545 546 /** 547 * List of persistent applications that are in the process 548 * of being started. 549 */ 550 final ArrayList<ProcessRecord> mPersistentStartingProcesses = new ArrayList<ProcessRecord>(); 551 552 /** 553 * Processes that are being forcibly torn down. 554 */ 555 final ArrayList<ProcessRecord> mRemovedProcesses = new ArrayList<ProcessRecord>(); 556 557 /** 558 * List of running applications, sorted by recent usage. 559 * The first entry in the list is the least recently used. 560 */ 561 final ArrayList<ProcessRecord> mLruProcesses = new ArrayList<ProcessRecord>(); 562 563 /** 564 * Where in mLruProcesses that the processes hosting activities start. 565 */ 566 int mLruProcessActivityStart = 0; 567 568 /** 569 * Where in mLruProcesses that the processes hosting services start. 570 * This is after (lower index) than mLruProcessesActivityStart. 571 */ 572 int mLruProcessServiceStart = 0; 573 574 /** 575 * List of processes that should gc as soon as things are idle. 576 */ 577 final ArrayList<ProcessRecord> mProcessesToGc = new ArrayList<ProcessRecord>(); 578 579 /** 580 * Processes we want to collect PSS data from. 581 */ 582 final ArrayList<ProcessRecord> mPendingPssProcesses = new ArrayList<ProcessRecord>(); 583 584 /** 585 * Last time we requested PSS data of all processes. 586 */ 587 long mLastFullPssTime = SystemClock.uptimeMillis(); 588 589 /** 590 * If set, the next time we collect PSS data we should do a full collection 591 * with data from native processes and the kernel. 592 */ 593 boolean mFullPssPending = false; 594 595 /** 596 * This is the process holding what we currently consider to be 597 * the "home" activity. 598 */ 599 ProcessRecord mHomeProcess; 600 601 /** 602 * This is the process holding the activity the user last visited that 603 * is in a different process from the one they are currently in. 604 */ 605 ProcessRecord mPreviousProcess; 606 607 /** 608 * The time at which the previous process was last visible. 609 */ 610 long mPreviousProcessVisibleTime; 611 612 /** 613 * Which uses have been started, so are allowed to run code. 614 */ 615 final SparseArray<UserStartedState> mStartedUsers = new SparseArray<UserStartedState>(); 616 617 /** 618 * LRU list of history of current users. Most recently current is at the end. 619 */ 620 final ArrayList<Integer> mUserLru = new ArrayList<Integer>(); 621 622 /** 623 * Constant array of the users that are currently started. 624 */ 625 int[] mStartedUserArray = new int[] { 0 }; 626 627 /** 628 * Registered observers of the user switching mechanics. 629 */ 630 final RemoteCallbackList<IUserSwitchObserver> mUserSwitchObservers 631 = new RemoteCallbackList<IUserSwitchObserver>(); 632 633 /** 634 * Currently active user switch. 635 */ 636 Object mCurUserSwitchCallback; 637 638 /** 639 * Packages that the user has asked to have run in screen size 640 * compatibility mode instead of filling the screen. 641 */ 642 final CompatModePackages mCompatModePackages; 643 644 /** 645 * Set of IntentSenderRecord objects that are currently active. 646 */ 647 final HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>> mIntentSenderRecords 648 = new HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>>(); 649 650 /** 651 * Fingerprints (hashCode()) of stack traces that we've 652 * already logged DropBox entries for. Guarded by itself. If 653 * something (rogue user app) forces this over 654 * MAX_DUP_SUPPRESSED_STACKS entries, the contents are cleared. 655 */ 656 private final HashSet<Integer> mAlreadyLoggedViolatedStacks = new HashSet<Integer>(); 657 private static final int MAX_DUP_SUPPRESSED_STACKS = 5000; 658 659 /** 660 * Strict Mode background batched logging state. 661 * 662 * The string buffer is guarded by itself, and its lock is also 663 * used to determine if another batched write is already 664 * in-flight. 665 */ 666 private final StringBuilder mStrictModeBuffer = new StringBuilder(); 667 668 /** 669 * Keeps track of all IIntentReceivers that have been registered for 670 * broadcasts. Hash keys are the receiver IBinder, hash value is 671 * a ReceiverList. 672 */ 673 final HashMap<IBinder, ReceiverList> mRegisteredReceivers = 674 new HashMap<IBinder, ReceiverList>(); 675 676 /** 677 * Resolver for broadcast intents to registered receivers. 678 * Holds BroadcastFilter (subclass of IntentFilter). 679 */ 680 final IntentResolver<BroadcastFilter, BroadcastFilter> mReceiverResolver 681 = new IntentResolver<BroadcastFilter, BroadcastFilter>() { 682 @Override 683 protected boolean allowFilterResult( 684 BroadcastFilter filter, List<BroadcastFilter> dest) { 685 IBinder target = filter.receiverList.receiver.asBinder(); 686 for (int i=dest.size()-1; i>=0; i--) { 687 if (dest.get(i).receiverList.receiver.asBinder() == target) { 688 return false; 689 } 690 } 691 return true; 692 } 693 694 @Override 695 protected BroadcastFilter newResult(BroadcastFilter filter, int match, int userId) { 696 if (userId == UserHandle.USER_ALL || filter.owningUserId == UserHandle.USER_ALL 697 || userId == filter.owningUserId) { 698 return super.newResult(filter, match, userId); 699 } 700 return null; 701 } 702 703 @Override 704 protected BroadcastFilter[] newArray(int size) { 705 return new BroadcastFilter[size]; 706 } 707 708 @Override 709 protected boolean isPackageForFilter(String packageName, BroadcastFilter filter) { 710 return packageName.equals(filter.packageName); 711 } 712 }; 713 714 /** 715 * State of all active sticky broadcasts per user. Keys are the action of the 716 * sticky Intent, values are an ArrayList of all broadcasted intents with 717 * that action (which should usually be one). The SparseArray is keyed 718 * by the user ID the sticky is for, and can include UserHandle.USER_ALL 719 * for stickies that are sent to all users. 720 */ 721 final SparseArray<ArrayMap<String, ArrayList<Intent>>> mStickyBroadcasts = 722 new SparseArray<ArrayMap<String, ArrayList<Intent>>>(); 723 724 final ActiveServices mServices; 725 726 /** 727 * Backup/restore process management 728 */ 729 String mBackupAppName = null; 730 BackupRecord mBackupTarget = null; 731 732 final ProviderMap mProviderMap; 733 734 /** 735 * List of content providers who have clients waiting for them. The 736 * application is currently being launched and the provider will be 737 * removed from this list once it is published. 738 */ 739 final ArrayList<ContentProviderRecord> mLaunchingProviders 740 = new ArrayList<ContentProviderRecord>(); 741 742 /** 743 * File storing persisted {@link #mGrantedUriPermissions}. 744 */ 745 private final AtomicFile mGrantFile; 746 747 /** XML constants used in {@link #mGrantFile} */ 748 private static final String TAG_URI_GRANTS = "uri-grants"; 749 private static final String TAG_URI_GRANT = "uri-grant"; 750 private static final String ATTR_USER_HANDLE = "userHandle"; 751 private static final String ATTR_SOURCE_USER_ID = "sourceUserId"; 752 private static final String ATTR_TARGET_USER_ID = "targetUserId"; 753 private static final String ATTR_SOURCE_PKG = "sourcePkg"; 754 private static final String ATTR_TARGET_PKG = "targetPkg"; 755 private static final String ATTR_URI = "uri"; 756 private static final String ATTR_MODE_FLAGS = "modeFlags"; 757 private static final String ATTR_CREATED_TIME = "createdTime"; 758 private static final String ATTR_PREFIX = "prefix"; 759 760 /** 761 * Global set of specific {@link Uri} permissions that have been granted. 762 * This optimized lookup structure maps from {@link UriPermission#targetUid} 763 * to {@link UriPermission#uri} to {@link UriPermission}. 764 */ 765 @GuardedBy("this") 766 private final SparseArray<ArrayMap<GrantUri, UriPermission>> 767 mGrantedUriPermissions = new SparseArray<ArrayMap<GrantUri, UriPermission>>(); 768 769 public static class GrantUri { 770 public final int sourceUserId; 771 public final Uri uri; 772 public boolean prefix; 773 774 public GrantUri(int sourceUserId, Uri uri, boolean prefix) { 775 this.sourceUserId = sourceUserId; 776 this.uri = uri; 777 this.prefix = prefix; 778 } 779 780 @Override 781 public int hashCode() { 782 return toString().hashCode(); 783 } 784 785 @Override 786 public boolean equals(Object o) { 787 if (o instanceof GrantUri) { 788 GrantUri other = (GrantUri) o; 789 return uri.equals(other.uri) && (sourceUserId == other.sourceUserId) 790 && prefix == other.prefix; 791 } 792 return false; 793 } 794 795 @Override 796 public String toString() { 797 String result = Integer.toString(sourceUserId) + " @ " + uri.toString(); 798 if (prefix) result += " [prefix]"; 799 return result; 800 } 801 802 public String toSafeString() { 803 String result = Integer.toString(sourceUserId) + " @ " + uri.toSafeString(); 804 if (prefix) result += " [prefix]"; 805 return result; 806 } 807 808 public static GrantUri resolve(int defaultSourceUserHandle, Uri uri) { 809 return new GrantUri(ContentProvider.getUserIdFromUri(uri, defaultSourceUserHandle), 810 ContentProvider.getUriWithoutUserId(uri), false); 811 } 812 } 813 814 CoreSettingsObserver mCoreSettingsObserver; 815 816 /** 817 * Thread-local storage used to carry caller permissions over through 818 * indirect content-provider access. 819 */ 820 private class Identity { 821 public int pid; 822 public int uid; 823 824 Identity(int _pid, int _uid) { 825 pid = _pid; 826 uid = _uid; 827 } 828 } 829 830 private static final ThreadLocal<Identity> sCallerIdentity = new ThreadLocal<Identity>(); 831 832 /** 833 * All information we have collected about the runtime performance of 834 * any user id that can impact battery performance. 835 */ 836 final BatteryStatsService mBatteryStatsService; 837 838 /** 839 * Information about component usage 840 */ 841 UsageStatsManagerInternal mUsageStatsService; 842 843 /** 844 * Information about and control over application operations 845 */ 846 final AppOpsService mAppOpsService; 847 848 /** 849 * Save recent tasks information across reboots. 850 */ 851 final TaskPersister mTaskPersister; 852 853 /** 854 * Current configuration information. HistoryRecord objects are given 855 * a reference to this object to indicate which configuration they are 856 * currently running in, so this object must be kept immutable. 857 */ 858 Configuration mConfiguration = new Configuration(); 859 860 /** 861 * Current sequencing integer of the configuration, for skipping old 862 * configurations. 863 */ 864 int mConfigurationSeq = 0; 865 866 /** 867 * Hardware-reported OpenGLES version. 868 */ 869 final int GL_ES_VERSION; 870 871 /** 872 * List of initialization arguments to pass to all processes when binding applications to them. 873 * For example, references to the commonly used services. 874 */ 875 HashMap<String, IBinder> mAppBindArgs; 876 877 /** 878 * Temporary to avoid allocations. Protected by main lock. 879 */ 880 final StringBuilder mStringBuilder = new StringBuilder(256); 881 882 /** 883 * Used to control how we initialize the service. 884 */ 885 ComponentName mTopComponent; 886 String mTopAction = Intent.ACTION_MAIN; 887 String mTopData; 888 boolean mProcessesReady = false; 889 boolean mSystemReady = false; 890 boolean mBooting = false; 891 boolean mWaitingUpdate = false; 892 boolean mDidUpdate = false; 893 boolean mOnBattery = false; 894 boolean mLaunchWarningShown = false; 895 896 Context mContext; 897 898 int mFactoryTest; 899 900 boolean mCheckedForSetup; 901 902 /** 903 * The time at which we will allow normal application switches again, 904 * after a call to {@link #stopAppSwitches()}. 905 */ 906 long mAppSwitchesAllowedTime; 907 908 /** 909 * This is set to true after the first switch after mAppSwitchesAllowedTime 910 * is set; any switches after that will clear the time. 911 */ 912 boolean mDidAppSwitch; 913 914 /** 915 * Last time (in realtime) at which we checked for power usage. 916 */ 917 long mLastPowerCheckRealtime; 918 919 /** 920 * Last time (in uptime) at which we checked for power usage. 921 */ 922 long mLastPowerCheckUptime; 923 924 /** 925 * Set while we are wanting to sleep, to prevent any 926 * activities from being started/resumed. 927 */ 928 private boolean mSleeping = false; 929 930 /** 931 * Set while we are running a voice interaction. This overrides 932 * sleeping while it is active. 933 */ 934 private boolean mRunningVoice = false; 935 936 /** 937 * State of external calls telling us if the device is asleep. 938 */ 939 private boolean mWentToSleep = false; 940 941 /** 942 * State of external call telling us if the lock screen is shown. 943 */ 944 private boolean mLockScreenShown = false; 945 946 /** 947 * Set if we are shutting down the system, similar to sleeping. 948 */ 949 boolean mShuttingDown = false; 950 951 /** 952 * Current sequence id for oom_adj computation traversal. 953 */ 954 int mAdjSeq = 0; 955 956 /** 957 * Current sequence id for process LRU updating. 958 */ 959 int mLruSeq = 0; 960 961 /** 962 * Keep track of the non-cached/empty process we last found, to help 963 * determine how to distribute cached/empty processes next time. 964 */ 965 int mNumNonCachedProcs = 0; 966 967 /** 968 * Keep track of the number of cached hidden procs, to balance oom adj 969 * distribution between those and empty procs. 970 */ 971 int mNumCachedHiddenProcs = 0; 972 973 /** 974 * Keep track of the number of service processes we last found, to 975 * determine on the next iteration which should be B services. 976 */ 977 int mNumServiceProcs = 0; 978 int mNewNumAServiceProcs = 0; 979 int mNewNumServiceProcs = 0; 980 981 /** 982 * Allow the current computed overall memory level of the system to go down? 983 * This is set to false when we are killing processes for reasons other than 984 * memory management, so that the now smaller process list will not be taken as 985 * an indication that memory is tighter. 986 */ 987 boolean mAllowLowerMemLevel = false; 988 989 /** 990 * The last computed memory level, for holding when we are in a state that 991 * processes are going away for other reasons. 992 */ 993 int mLastMemoryLevel = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 994 995 /** 996 * The last total number of process we have, to determine if changes actually look 997 * like a shrinking number of process due to lower RAM. 998 */ 999 int mLastNumProcesses; 1000 1001 /** 1002 * The uptime of the last time we performed idle maintenance. 1003 */ 1004 long mLastIdleTime = SystemClock.uptimeMillis(); 1005 1006 /** 1007 * Total time spent with RAM that has been added in the past since the last idle time. 1008 */ 1009 long mLowRamTimeSinceLastIdle = 0; 1010 1011 /** 1012 * If RAM is currently low, when that horrible situation started. 1013 */ 1014 long mLowRamStartTime = 0; 1015 1016 /** 1017 * For reporting to battery stats the current top application. 1018 */ 1019 private String mCurResumedPackage = null; 1020 private int mCurResumedUid = -1; 1021 1022 /** 1023 * For reporting to battery stats the apps currently running foreground 1024 * service. The ProcessMap is package/uid tuples; each of these contain 1025 * an array of the currently foreground processes. 1026 */ 1027 final ProcessMap<ArrayList<ProcessRecord>> mForegroundPackages 1028 = new ProcessMap<ArrayList<ProcessRecord>>(); 1029 1030 /** 1031 * This is set if we had to do a delayed dexopt of an app before launching 1032 * it, to increase the ANR timeouts in that case. 1033 */ 1034 boolean mDidDexOpt; 1035 1036 /** 1037 * Set if the systemServer made a call to enterSafeMode. 1038 */ 1039 boolean mSafeMode; 1040 1041 String mDebugApp = null; 1042 boolean mWaitForDebugger = false; 1043 boolean mDebugTransient = false; 1044 String mOrigDebugApp = null; 1045 boolean mOrigWaitForDebugger = false; 1046 boolean mAlwaysFinishActivities = false; 1047 IActivityController mController = null; 1048 String mProfileApp = null; 1049 ProcessRecord mProfileProc = null; 1050 String mProfileFile; 1051 ParcelFileDescriptor mProfileFd; 1052 int mProfileType = 0; 1053 boolean mAutoStopProfiler = false; 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 final boolean mHasRecents; 1203 1204 final int mThumbnailWidth; 1205 final int mThumbnailHeight; 1206 1207 final ServiceThread mHandlerThread; 1208 final MainHandler mHandler; 1209 1210 final class MainHandler extends Handler { 1211 public MainHandler(Looper looper) { 1212 super(looper, null, true); 1213 } 1214 1215 @Override 1216 public void handleMessage(Message msg) { 1217 switch (msg.what) { 1218 case SHOW_ERROR_MSG: { 1219 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1220 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 1221 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 1222 synchronized (ActivityManagerService.this) { 1223 ProcessRecord proc = (ProcessRecord)data.get("app"); 1224 AppErrorResult res = (AppErrorResult) data.get("result"); 1225 if (proc != null && proc.crashDialog != null) { 1226 Slog.e(TAG, "App already has crash dialog: " + proc); 1227 if (res != null) { 1228 res.set(0); 1229 } 1230 return; 1231 } 1232 boolean isBackground = (UserHandle.getAppId(proc.uid) 1233 >= Process.FIRST_APPLICATION_UID 1234 && proc.pid != MY_PID); 1235 for (int userId : mCurrentProfileIds) { 1236 isBackground &= (proc.userId != userId); 1237 } 1238 if (isBackground && !showBackground) { 1239 Slog.w(TAG, "Skipping crash dialog of " + proc + ": background"); 1240 if (res != null) { 1241 res.set(0); 1242 } 1243 return; 1244 } 1245 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1246 Dialog d = new AppErrorDialog(mContext, 1247 ActivityManagerService.this, res, proc); 1248 d.show(); 1249 proc.crashDialog = d; 1250 } else { 1251 // The device is asleep, so just pretend that the user 1252 // saw a crash dialog and hit "force quit". 1253 if (res != null) { 1254 res.set(0); 1255 } 1256 } 1257 } 1258 1259 ensureBootCompleted(); 1260 } break; 1261 case SHOW_NOT_RESPONDING_MSG: { 1262 synchronized (ActivityManagerService.this) { 1263 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1264 ProcessRecord proc = (ProcessRecord)data.get("app"); 1265 if (proc != null && proc.anrDialog != null) { 1266 Slog.e(TAG, "App already has anr dialog: " + proc); 1267 return; 1268 } 1269 1270 Intent intent = new Intent("android.intent.action.ANR"); 1271 if (!mProcessesReady) { 1272 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 1273 | Intent.FLAG_RECEIVER_FOREGROUND); 1274 } 1275 broadcastIntentLocked(null, null, intent, 1276 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 1277 false, false, MY_PID, Process.SYSTEM_UID, 0 /* TODO: Verify */); 1278 1279 if (mShowDialogs) { 1280 Dialog d = new AppNotRespondingDialog(ActivityManagerService.this, 1281 mContext, proc, (ActivityRecord)data.get("activity"), 1282 msg.arg1 != 0); 1283 d.show(); 1284 proc.anrDialog = d; 1285 } else { 1286 // Just kill the app if there is no dialog to be shown. 1287 killAppAtUsersRequest(proc, null); 1288 } 1289 } 1290 1291 ensureBootCompleted(); 1292 } break; 1293 case SHOW_STRICT_MODE_VIOLATION_MSG: { 1294 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1295 synchronized (ActivityManagerService.this) { 1296 ProcessRecord proc = (ProcessRecord) data.get("app"); 1297 if (proc == null) { 1298 Slog.e(TAG, "App not found when showing strict mode dialog."); 1299 break; 1300 } 1301 if (proc.crashDialog != null) { 1302 Slog.e(TAG, "App already has strict mode dialog: " + proc); 1303 return; 1304 } 1305 AppErrorResult res = (AppErrorResult) data.get("result"); 1306 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1307 Dialog d = new StrictModeViolationDialog(mContext, 1308 ActivityManagerService.this, res, proc); 1309 d.show(); 1310 proc.crashDialog = d; 1311 } else { 1312 // The device is asleep, so just pretend that the user 1313 // saw a crash dialog and hit "force quit". 1314 res.set(0); 1315 } 1316 } 1317 ensureBootCompleted(); 1318 } break; 1319 case SHOW_FACTORY_ERROR_MSG: { 1320 Dialog d = new FactoryErrorDialog( 1321 mContext, msg.getData().getCharSequence("msg")); 1322 d.show(); 1323 ensureBootCompleted(); 1324 } break; 1325 case UPDATE_CONFIGURATION_MSG: { 1326 final ContentResolver resolver = mContext.getContentResolver(); 1327 Settings.System.putConfiguration(resolver, (Configuration)msg.obj); 1328 } break; 1329 case GC_BACKGROUND_PROCESSES_MSG: { 1330 synchronized (ActivityManagerService.this) { 1331 performAppGcsIfAppropriateLocked(); 1332 } 1333 } break; 1334 case WAIT_FOR_DEBUGGER_MSG: { 1335 synchronized (ActivityManagerService.this) { 1336 ProcessRecord app = (ProcessRecord)msg.obj; 1337 if (msg.arg1 != 0) { 1338 if (!app.waitedForDebugger) { 1339 Dialog d = new AppWaitingForDebuggerDialog( 1340 ActivityManagerService.this, 1341 mContext, app); 1342 app.waitDialog = d; 1343 app.waitedForDebugger = true; 1344 d.show(); 1345 } 1346 } else { 1347 if (app.waitDialog != null) { 1348 app.waitDialog.dismiss(); 1349 app.waitDialog = null; 1350 } 1351 } 1352 } 1353 } break; 1354 case SERVICE_TIMEOUT_MSG: { 1355 if (mDidDexOpt) { 1356 mDidDexOpt = false; 1357 Message nmsg = mHandler.obtainMessage(SERVICE_TIMEOUT_MSG); 1358 nmsg.obj = msg.obj; 1359 mHandler.sendMessageDelayed(nmsg, ActiveServices.SERVICE_TIMEOUT); 1360 return; 1361 } 1362 mServices.serviceTimeout((ProcessRecord)msg.obj); 1363 } break; 1364 case UPDATE_TIME_ZONE: { 1365 synchronized (ActivityManagerService.this) { 1366 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1367 ProcessRecord r = mLruProcesses.get(i); 1368 if (r.thread != null) { 1369 try { 1370 r.thread.updateTimeZone(); 1371 } catch (RemoteException ex) { 1372 Slog.w(TAG, "Failed to update time zone for: " + r.info.processName); 1373 } 1374 } 1375 } 1376 } 1377 } break; 1378 case CLEAR_DNS_CACHE_MSG: { 1379 synchronized (ActivityManagerService.this) { 1380 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1381 ProcessRecord r = mLruProcesses.get(i); 1382 if (r.thread != null) { 1383 try { 1384 r.thread.clearDnsCache(); 1385 } catch (RemoteException ex) { 1386 Slog.w(TAG, "Failed to clear dns cache for: " + r.info.processName); 1387 } 1388 } 1389 } 1390 } 1391 } break; 1392 case UPDATE_HTTP_PROXY_MSG: { 1393 ProxyInfo proxy = (ProxyInfo)msg.obj; 1394 String host = ""; 1395 String port = ""; 1396 String exclList = ""; 1397 Uri pacFileUrl = Uri.EMPTY; 1398 if (proxy != null) { 1399 host = proxy.getHost(); 1400 port = Integer.toString(proxy.getPort()); 1401 exclList = proxy.getExclusionListAsString(); 1402 pacFileUrl = proxy.getPacFileUrl(); 1403 } 1404 synchronized (ActivityManagerService.this) { 1405 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1406 ProcessRecord r = mLruProcesses.get(i); 1407 if (r.thread != null) { 1408 try { 1409 r.thread.setHttpProxy(host, port, exclList, pacFileUrl); 1410 } catch (RemoteException ex) { 1411 Slog.w(TAG, "Failed to update http proxy for: " + 1412 r.info.processName); 1413 } 1414 } 1415 } 1416 } 1417 } break; 1418 case SHOW_UID_ERROR_MSG: { 1419 String title = "System UIDs Inconsistent"; 1420 String text = "UIDs on the system are inconsistent, you need to wipe your" 1421 + " data partition or your device will be unstable."; 1422 Log.e(TAG, title + ": " + text); 1423 if (mShowDialogs) { 1424 // XXX This is a temporary dialog, no need to localize. 1425 AlertDialog d = new BaseErrorDialog(mContext); 1426 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 1427 d.setCancelable(false); 1428 d.setTitle(title); 1429 d.setMessage(text); 1430 d.setButton(DialogInterface.BUTTON_POSITIVE, "I'm Feeling Lucky", 1431 mHandler.obtainMessage(IM_FEELING_LUCKY_MSG)); 1432 mUidAlert = d; 1433 d.show(); 1434 } 1435 } break; 1436 case IM_FEELING_LUCKY_MSG: { 1437 if (mUidAlert != null) { 1438 mUidAlert.dismiss(); 1439 mUidAlert = null; 1440 } 1441 } break; 1442 case PROC_START_TIMEOUT_MSG: { 1443 if (mDidDexOpt) { 1444 mDidDexOpt = false; 1445 Message nmsg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 1446 nmsg.obj = msg.obj; 1447 mHandler.sendMessageDelayed(nmsg, PROC_START_TIMEOUT); 1448 return; 1449 } 1450 ProcessRecord app = (ProcessRecord)msg.obj; 1451 synchronized (ActivityManagerService.this) { 1452 processStartTimedOutLocked(app); 1453 } 1454 } break; 1455 case DO_PENDING_ACTIVITY_LAUNCHES_MSG: { 1456 synchronized (ActivityManagerService.this) { 1457 mStackSupervisor.doPendingActivityLaunchesLocked(true); 1458 } 1459 } break; 1460 case KILL_APPLICATION_MSG: { 1461 synchronized (ActivityManagerService.this) { 1462 int appid = msg.arg1; 1463 boolean restart = (msg.arg2 == 1); 1464 Bundle bundle = (Bundle)msg.obj; 1465 String pkg = bundle.getString("pkg"); 1466 String reason = bundle.getString("reason"); 1467 forceStopPackageLocked(pkg, appid, restart, false, true, false, 1468 false, UserHandle.USER_ALL, reason); 1469 } 1470 } break; 1471 case FINALIZE_PENDING_INTENT_MSG: { 1472 ((PendingIntentRecord)msg.obj).completeFinalize(); 1473 } break; 1474 case POST_HEAVY_NOTIFICATION_MSG: { 1475 INotificationManager inm = NotificationManager.getService(); 1476 if (inm == null) { 1477 return; 1478 } 1479 1480 ActivityRecord root = (ActivityRecord)msg.obj; 1481 ProcessRecord process = root.app; 1482 if (process == null) { 1483 return; 1484 } 1485 1486 try { 1487 Context context = mContext.createPackageContext(process.info.packageName, 0); 1488 String text = mContext.getString(R.string.heavy_weight_notification, 1489 context.getApplicationInfo().loadLabel(context.getPackageManager())); 1490 Notification notification = new Notification(); 1491 notification.icon = com.android.internal.R.drawable.stat_sys_adb; //context.getApplicationInfo().icon; 1492 notification.when = 0; 1493 notification.flags = Notification.FLAG_ONGOING_EVENT; 1494 notification.tickerText = text; 1495 notification.defaults = 0; // please be quiet 1496 notification.sound = null; 1497 notification.vibrate = null; 1498 notification.color = mContext.getResources().getColor( 1499 com.android.internal.R.color.system_notification_accent_color); 1500 notification.setLatestEventInfo(context, text, 1501 mContext.getText(R.string.heavy_weight_notification_detail), 1502 PendingIntent.getActivityAsUser(mContext, 0, root.intent, 1503 PendingIntent.FLAG_CANCEL_CURRENT, null, 1504 new UserHandle(root.userId))); 1505 1506 try { 1507 int[] outId = new int[1]; 1508 inm.enqueueNotificationWithTag("android", "android", null, 1509 R.string.heavy_weight_notification, 1510 notification, outId, root.userId); 1511 } catch (RuntimeException e) { 1512 Slog.w(ActivityManagerService.TAG, 1513 "Error showing notification for heavy-weight app", e); 1514 } catch (RemoteException e) { 1515 } 1516 } catch (NameNotFoundException e) { 1517 Slog.w(TAG, "Unable to create context for heavy notification", e); 1518 } 1519 } break; 1520 case CANCEL_HEAVY_NOTIFICATION_MSG: { 1521 INotificationManager inm = NotificationManager.getService(); 1522 if (inm == null) { 1523 return; 1524 } 1525 try { 1526 inm.cancelNotificationWithTag("android", null, 1527 R.string.heavy_weight_notification, msg.arg1); 1528 } catch (RuntimeException e) { 1529 Slog.w(ActivityManagerService.TAG, 1530 "Error canceling notification for service", e); 1531 } catch (RemoteException e) { 1532 } 1533 } break; 1534 case CHECK_EXCESSIVE_WAKE_LOCKS_MSG: { 1535 synchronized (ActivityManagerService.this) { 1536 checkExcessivePowerUsageLocked(true); 1537 removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1538 Message nmsg = obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1539 sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 1540 } 1541 } break; 1542 case SHOW_COMPAT_MODE_DIALOG_MSG: { 1543 synchronized (ActivityManagerService.this) { 1544 ActivityRecord ar = (ActivityRecord)msg.obj; 1545 if (mCompatModeDialog != null) { 1546 if (mCompatModeDialog.mAppInfo.packageName.equals( 1547 ar.info.applicationInfo.packageName)) { 1548 return; 1549 } 1550 mCompatModeDialog.dismiss(); 1551 mCompatModeDialog = null; 1552 } 1553 if (ar != null && false) { 1554 if (mCompatModePackages.getPackageAskCompatModeLocked( 1555 ar.packageName)) { 1556 int mode = mCompatModePackages.computeCompatModeLocked( 1557 ar.info.applicationInfo); 1558 if (mode == ActivityManager.COMPAT_MODE_DISABLED 1559 || mode == ActivityManager.COMPAT_MODE_ENABLED) { 1560 mCompatModeDialog = new CompatModeDialog( 1561 ActivityManagerService.this, mContext, 1562 ar.info.applicationInfo); 1563 mCompatModeDialog.show(); 1564 } 1565 } 1566 } 1567 } 1568 break; 1569 } 1570 case DISPATCH_PROCESSES_CHANGED: { 1571 dispatchProcessesChanged(); 1572 break; 1573 } 1574 case DISPATCH_PROCESS_DIED: { 1575 final int pid = msg.arg1; 1576 final int uid = msg.arg2; 1577 dispatchProcessDied(pid, uid); 1578 break; 1579 } 1580 case REPORT_MEM_USAGE_MSG: { 1581 final ArrayList<ProcessMemInfo> memInfos = (ArrayList<ProcessMemInfo>)msg.obj; 1582 Thread thread = new Thread() { 1583 @Override public void run() { 1584 final SparseArray<ProcessMemInfo> infoMap 1585 = new SparseArray<ProcessMemInfo>(memInfos.size()); 1586 for (int i=0, N=memInfos.size(); i<N; i++) { 1587 ProcessMemInfo mi = memInfos.get(i); 1588 infoMap.put(mi.pid, mi); 1589 } 1590 updateCpuStatsNow(); 1591 synchronized (mProcessCpuThread) { 1592 final int N = mProcessCpuTracker.countStats(); 1593 for (int i=0; i<N; i++) { 1594 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 1595 if (st.vsize > 0) { 1596 long pss = Debug.getPss(st.pid, null); 1597 if (pss > 0) { 1598 if (infoMap.indexOfKey(st.pid) < 0) { 1599 ProcessMemInfo mi = new ProcessMemInfo(st.name, st.pid, 1600 ProcessList.NATIVE_ADJ, -1, "native", null); 1601 mi.pss = pss; 1602 memInfos.add(mi); 1603 } 1604 } 1605 } 1606 } 1607 } 1608 1609 long totalPss = 0; 1610 for (int i=0, N=memInfos.size(); i<N; i++) { 1611 ProcessMemInfo mi = memInfos.get(i); 1612 if (mi.pss == 0) { 1613 mi.pss = Debug.getPss(mi.pid, null); 1614 } 1615 totalPss += mi.pss; 1616 } 1617 Collections.sort(memInfos, new Comparator<ProcessMemInfo>() { 1618 @Override public int compare(ProcessMemInfo lhs, ProcessMemInfo rhs) { 1619 if (lhs.oomAdj != rhs.oomAdj) { 1620 return lhs.oomAdj < rhs.oomAdj ? -1 : 1; 1621 } 1622 if (lhs.pss != rhs.pss) { 1623 return lhs.pss < rhs.pss ? 1 : -1; 1624 } 1625 return 0; 1626 } 1627 }); 1628 1629 StringBuilder tag = new StringBuilder(128); 1630 StringBuilder stack = new StringBuilder(128); 1631 tag.append("Low on memory -- "); 1632 appendMemBucket(tag, totalPss, "total", false); 1633 appendMemBucket(stack, totalPss, "total", true); 1634 1635 StringBuilder logBuilder = new StringBuilder(1024); 1636 logBuilder.append("Low on memory:\n"); 1637 1638 boolean firstLine = true; 1639 int lastOomAdj = Integer.MIN_VALUE; 1640 for (int i=0, N=memInfos.size(); i<N; i++) { 1641 ProcessMemInfo mi = memInfos.get(i); 1642 1643 if (mi.oomAdj != ProcessList.NATIVE_ADJ 1644 && (mi.oomAdj < ProcessList.SERVICE_ADJ 1645 || mi.oomAdj == ProcessList.HOME_APP_ADJ 1646 || mi.oomAdj == ProcessList.PREVIOUS_APP_ADJ)) { 1647 if (lastOomAdj != mi.oomAdj) { 1648 lastOomAdj = mi.oomAdj; 1649 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1650 tag.append(" / "); 1651 } 1652 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ) { 1653 if (firstLine) { 1654 stack.append(":"); 1655 firstLine = false; 1656 } 1657 stack.append("\n\t at "); 1658 } else { 1659 stack.append("$"); 1660 } 1661 } else { 1662 tag.append(" "); 1663 stack.append("$"); 1664 } 1665 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1666 appendMemBucket(tag, mi.pss, mi.name, false); 1667 } 1668 appendMemBucket(stack, mi.pss, mi.name, true); 1669 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ 1670 && ((i+1) >= N || memInfos.get(i+1).oomAdj != lastOomAdj)) { 1671 stack.append("("); 1672 for (int k=0; k<DUMP_MEM_OOM_ADJ.length; k++) { 1673 if (DUMP_MEM_OOM_ADJ[k] == mi.oomAdj) { 1674 stack.append(DUMP_MEM_OOM_LABEL[k]); 1675 stack.append(":"); 1676 stack.append(DUMP_MEM_OOM_ADJ[k]); 1677 } 1678 } 1679 stack.append(")"); 1680 } 1681 } 1682 1683 logBuilder.append(" "); 1684 logBuilder.append(ProcessList.makeOomAdjString(mi.oomAdj)); 1685 logBuilder.append(' '); 1686 logBuilder.append(ProcessList.makeProcStateString(mi.procState)); 1687 logBuilder.append(' '); 1688 ProcessList.appendRamKb(logBuilder, mi.pss); 1689 logBuilder.append(" kB: "); 1690 logBuilder.append(mi.name); 1691 logBuilder.append(" ("); 1692 logBuilder.append(mi.pid); 1693 logBuilder.append(") "); 1694 logBuilder.append(mi.adjType); 1695 logBuilder.append('\n'); 1696 if (mi.adjReason != null) { 1697 logBuilder.append(" "); 1698 logBuilder.append(mi.adjReason); 1699 logBuilder.append('\n'); 1700 } 1701 } 1702 1703 logBuilder.append(" "); 1704 ProcessList.appendRamKb(logBuilder, totalPss); 1705 logBuilder.append(" kB: TOTAL\n"); 1706 1707 long[] infos = new long[Debug.MEMINFO_COUNT]; 1708 Debug.getMemInfo(infos); 1709 logBuilder.append(" MemInfo: "); 1710 logBuilder.append(infos[Debug.MEMINFO_SLAB]).append(" kB slab, "); 1711 logBuilder.append(infos[Debug.MEMINFO_SHMEM]).append(" kB shmem, "); 1712 logBuilder.append(infos[Debug.MEMINFO_BUFFERS]).append(" kB buffers, "); 1713 logBuilder.append(infos[Debug.MEMINFO_CACHED]).append(" kB cached, "); 1714 logBuilder.append(infos[Debug.MEMINFO_FREE]).append(" kB free\n"); 1715 if (infos[Debug.MEMINFO_ZRAM_TOTAL] != 0) { 1716 logBuilder.append(" ZRAM: "); 1717 logBuilder.append(infos[Debug.MEMINFO_ZRAM_TOTAL]); 1718 logBuilder.append(" kB RAM, "); 1719 logBuilder.append(infos[Debug.MEMINFO_SWAP_TOTAL]); 1720 logBuilder.append(" kB swap total, "); 1721 logBuilder.append(infos[Debug.MEMINFO_SWAP_FREE]); 1722 logBuilder.append(" kB swap free\n"); 1723 } 1724 Slog.i(TAG, logBuilder.toString()); 1725 1726 StringBuilder dropBuilder = new StringBuilder(1024); 1727 /* 1728 StringWriter oomSw = new StringWriter(); 1729 PrintWriter oomPw = new FastPrintWriter(oomSw, false, 256); 1730 StringWriter catSw = new StringWriter(); 1731 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1732 String[] emptyArgs = new String[] { }; 1733 dumpApplicationMemoryUsage(null, oomPw, " ", emptyArgs, true, catPw); 1734 oomPw.flush(); 1735 String oomString = oomSw.toString(); 1736 */ 1737 dropBuilder.append(stack); 1738 dropBuilder.append('\n'); 1739 dropBuilder.append('\n'); 1740 dropBuilder.append(logBuilder); 1741 dropBuilder.append('\n'); 1742 /* 1743 dropBuilder.append(oomString); 1744 dropBuilder.append('\n'); 1745 */ 1746 StringWriter catSw = new StringWriter(); 1747 synchronized (ActivityManagerService.this) { 1748 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1749 String[] emptyArgs = new String[] { }; 1750 catPw.println(); 1751 dumpProcessesLocked(null, catPw, emptyArgs, 0, false, null); 1752 catPw.println(); 1753 mServices.dumpServicesLocked(null, catPw, emptyArgs, 0, 1754 false, false, null); 1755 catPw.println(); 1756 dumpActivitiesLocked(null, catPw, emptyArgs, 0, false, false, null); 1757 catPw.flush(); 1758 } 1759 dropBuilder.append(catSw.toString()); 1760 addErrorToDropBox("lowmem", null, "system_server", null, 1761 null, tag.toString(), dropBuilder.toString(), null, null); 1762 //Slog.i(TAG, "Sent to dropbox:"); 1763 //Slog.i(TAG, dropBuilder.toString()); 1764 synchronized (ActivityManagerService.this) { 1765 long now = SystemClock.uptimeMillis(); 1766 if (mLastMemUsageReportTime < now) { 1767 mLastMemUsageReportTime = now; 1768 } 1769 } 1770 } 1771 }; 1772 thread.start(); 1773 break; 1774 } 1775 case START_USER_SWITCH_MSG: { 1776 showUserSwitchDialog(msg.arg1, (String) msg.obj); 1777 break; 1778 } 1779 case REPORT_USER_SWITCH_MSG: { 1780 dispatchUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1781 break; 1782 } 1783 case CONTINUE_USER_SWITCH_MSG: { 1784 continueUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1785 break; 1786 } 1787 case USER_SWITCH_TIMEOUT_MSG: { 1788 timeoutUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1789 break; 1790 } 1791 case IMMERSIVE_MODE_LOCK_MSG: { 1792 final boolean nextState = (msg.arg1 != 0); 1793 if (mUpdateLock.isHeld() != nextState) { 1794 if (DEBUG_IMMERSIVE) { 1795 final ActivityRecord r = (ActivityRecord) msg.obj; 1796 Slog.d(TAG, "Applying new update lock state '" + nextState + "' for " + r); 1797 } 1798 if (nextState) { 1799 mUpdateLock.acquire(); 1800 } else { 1801 mUpdateLock.release(); 1802 } 1803 } 1804 break; 1805 } 1806 case PERSIST_URI_GRANTS_MSG: { 1807 writeGrantedUriPermissions(); 1808 break; 1809 } 1810 case REQUEST_ALL_PSS_MSG: { 1811 requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, false); 1812 break; 1813 } 1814 case START_PROFILES_MSG: { 1815 synchronized (ActivityManagerService.this) { 1816 startProfilesLocked(); 1817 } 1818 break; 1819 } 1820 case UPDATE_TIME: { 1821 synchronized (ActivityManagerService.this) { 1822 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1823 ProcessRecord r = mLruProcesses.get(i); 1824 if (r.thread != null) { 1825 try { 1826 r.thread.updateTimePrefs(msg.arg1 == 0 ? false : true); 1827 } catch (RemoteException ex) { 1828 Slog.w(TAG, "Failed to update preferences for: " + r.info.processName); 1829 } 1830 } 1831 } 1832 } 1833 break; 1834 } 1835 case SYSTEM_USER_START_MSG: { 1836 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 1837 Integer.toString(msg.arg1), msg.arg1); 1838 mSystemServiceManager.startUser(msg.arg1); 1839 break; 1840 } 1841 case SYSTEM_USER_CURRENT_MSG: { 1842 mBatteryStatsService.noteEvent( 1843 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_FINISH, 1844 Integer.toString(msg.arg2), msg.arg2); 1845 mBatteryStatsService.noteEvent( 1846 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 1847 Integer.toString(msg.arg1), msg.arg1); 1848 mSystemServiceManager.switchUser(msg.arg1); 1849 mLockToAppRequest.clearPrompt(); 1850 break; 1851 } 1852 case ENTER_ANIMATION_COMPLETE_MSG: { 1853 synchronized (ActivityManagerService.this) { 1854 ActivityRecord r = ActivityRecord.forToken((IBinder) msg.obj); 1855 if (r != null && r.app != null && r.app.thread != null) { 1856 try { 1857 r.app.thread.scheduleEnterAnimationComplete(r.appToken); 1858 } catch (RemoteException e) { 1859 } 1860 } 1861 } 1862 break; 1863 } 1864 case ENABLE_SCREEN_AFTER_BOOT_MSG: { 1865 enableScreenAfterBoot(); 1866 break; 1867 } 1868 } 1869 } 1870 }; 1871 1872 static final int COLLECT_PSS_BG_MSG = 1; 1873 1874 final Handler mBgHandler = new Handler(BackgroundThread.getHandler().getLooper()) { 1875 @Override 1876 public void handleMessage(Message msg) { 1877 switch (msg.what) { 1878 case COLLECT_PSS_BG_MSG: { 1879 long start = SystemClock.uptimeMillis(); 1880 MemInfoReader memInfo = null; 1881 synchronized (ActivityManagerService.this) { 1882 if (mFullPssPending) { 1883 mFullPssPending = false; 1884 memInfo = new MemInfoReader(); 1885 } 1886 } 1887 if (memInfo != null) { 1888 updateCpuStatsNow(); 1889 long nativeTotalPss = 0; 1890 synchronized (mProcessCpuThread) { 1891 final int N = mProcessCpuTracker.countStats(); 1892 for (int j=0; j<N; j++) { 1893 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(j); 1894 if (st.vsize <= 0 || st.uid >= Process.FIRST_APPLICATION_UID) { 1895 // This is definitely an application process; skip it. 1896 continue; 1897 } 1898 synchronized (mPidsSelfLocked) { 1899 if (mPidsSelfLocked.indexOfKey(st.pid) >= 0) { 1900 // This is one of our own processes; skip it. 1901 continue; 1902 } 1903 } 1904 nativeTotalPss += Debug.getPss(st.pid, null); 1905 } 1906 } 1907 memInfo.readMemInfo(); 1908 synchronized (this) { 1909 if (DEBUG_PSS) Slog.d(TAG, "Collected native and kernel memory in " 1910 + (SystemClock.uptimeMillis()-start) + "ms"); 1911 mProcessStats.addSysMemUsageLocked(memInfo.getCachedSizeKb(), 1912 memInfo.getFreeSizeKb(), memInfo.getZramTotalSizeKb(), 1913 memInfo.getBuffersSizeKb()+memInfo.getShmemSizeKb() 1914 +memInfo.getSlabSizeKb(), 1915 nativeTotalPss); 1916 } 1917 } 1918 1919 int i=0, num=0; 1920 long[] tmp = new long[1]; 1921 do { 1922 ProcessRecord proc; 1923 int procState; 1924 int pid; 1925 synchronized (ActivityManagerService.this) { 1926 if (i >= mPendingPssProcesses.size()) { 1927 if (DEBUG_PSS) Slog.d(TAG, "Collected PSS of " + num + " of " + i 1928 + " processes in " + (SystemClock.uptimeMillis()-start) + "ms"); 1929 mPendingPssProcesses.clear(); 1930 return; 1931 } 1932 proc = mPendingPssProcesses.get(i); 1933 procState = proc.pssProcState; 1934 if (proc.thread != null && procState == proc.setProcState) { 1935 pid = proc.pid; 1936 } else { 1937 proc = null; 1938 pid = 0; 1939 } 1940 i++; 1941 } 1942 if (proc != null) { 1943 long pss = Debug.getPss(pid, tmp); 1944 synchronized (ActivityManagerService.this) { 1945 if (proc.thread != null && proc.setProcState == procState 1946 && proc.pid == pid) { 1947 num++; 1948 proc.lastPssTime = SystemClock.uptimeMillis(); 1949 proc.baseProcessTracker.addPss(pss, tmp[0], true, proc.pkgList); 1950 if (DEBUG_PSS) Slog.d(TAG, "PSS of " + proc.toShortString() 1951 + ": " + pss + " lastPss=" + proc.lastPss 1952 + " state=" + ProcessList.makeProcStateString(procState)); 1953 if (proc.initialIdlePss == 0) { 1954 proc.initialIdlePss = pss; 1955 } 1956 proc.lastPss = pss; 1957 if (procState >= ActivityManager.PROCESS_STATE_HOME) { 1958 proc.lastCachedPss = pss; 1959 } 1960 } 1961 } 1962 } 1963 } while (true); 1964 } 1965 } 1966 } 1967 }; 1968 1969 /** 1970 * Monitor for package changes and update our internal state. 1971 */ 1972 private final PackageMonitor mPackageMonitor = new PackageMonitor() { 1973 @Override 1974 public void onPackageRemoved(String packageName, int uid) { 1975 // Remove all tasks with activities in the specified package from the list of recent tasks 1976 synchronized (ActivityManagerService.this) { 1977 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 1978 TaskRecord tr = mRecentTasks.get(i); 1979 ComponentName cn = tr.intent.getComponent(); 1980 if (cn != null && cn.getPackageName().equals(packageName)) { 1981 // If the package name matches, remove the task and kill the process 1982 removeTaskByIdLocked(tr.taskId, ActivityManager.REMOVE_TASK_KILL_PROCESS); 1983 } 1984 } 1985 } 1986 } 1987 1988 @Override 1989 public boolean onPackageChanged(String packageName, int uid, String[] components) { 1990 onPackageModified(packageName); 1991 return true; 1992 } 1993 1994 @Override 1995 public void onPackageModified(String packageName) { 1996 final PackageManager pm = mContext.getPackageManager(); 1997 final ArrayList<Pair<Intent, Integer>> recentTaskIntents = 1998 new ArrayList<Pair<Intent, Integer>>(); 1999 final ArrayList<Integer> tasksToRemove = new ArrayList<Integer>(); 2000 // Copy the list of recent tasks so that we don't hold onto the lock on 2001 // ActivityManagerService for long periods while checking if components exist. 2002 synchronized (ActivityManagerService.this) { 2003 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 2004 TaskRecord tr = mRecentTasks.get(i); 2005 recentTaskIntents.add(new Pair<Intent, Integer>(tr.intent, tr.taskId)); 2006 } 2007 } 2008 // Check the recent tasks and filter out all tasks with components that no longer exist. 2009 Intent tmpI = new Intent(); 2010 for (int i = recentTaskIntents.size() - 1; i >= 0; i--) { 2011 Pair<Intent, Integer> p = recentTaskIntents.get(i); 2012 ComponentName cn = p.first.getComponent(); 2013 if (cn != null && cn.getPackageName().equals(packageName)) { 2014 try { 2015 // Add the task to the list to remove if the component no longer exists 2016 tmpI.setComponent(cn); 2017 if (pm.queryIntentActivities(tmpI, PackageManager.MATCH_DEFAULT_ONLY).isEmpty()) { 2018 tasksToRemove.add(p.second); 2019 } 2020 } catch (Exception e) {} 2021 } 2022 } 2023 // Prune all the tasks with removed components from the list of recent tasks 2024 synchronized (ActivityManagerService.this) { 2025 for (int i = tasksToRemove.size() - 1; i >= 0; i--) { 2026 // Remove the task but don't kill the process (since other components in that 2027 // package may still be running and in the background) 2028 removeTaskByIdLocked(tasksToRemove.get(i), 0); 2029 } 2030 } 2031 } 2032 2033 @Override 2034 public boolean onHandleForceStop(Intent intent, String[] packages, int uid, boolean doit) { 2035 // Force stop the specified packages 2036 if (packages != null) { 2037 for (String pkg : packages) { 2038 synchronized (ActivityManagerService.this) { 2039 if (forceStopPackageLocked(pkg, -1, false, false, false, false, false, 0, 2040 "finished booting")) { 2041 return true; 2042 } 2043 } 2044 } 2045 } 2046 return false; 2047 } 2048 }; 2049 2050 public void setSystemProcess() { 2051 try { 2052 ServiceManager.addService(Context.ACTIVITY_SERVICE, this, true); 2053 ServiceManager.addService(ProcessStats.SERVICE_NAME, mProcessStats); 2054 ServiceManager.addService("meminfo", new MemBinder(this)); 2055 ServiceManager.addService("gfxinfo", new GraphicsBinder(this)); 2056 ServiceManager.addService("dbinfo", new DbBinder(this)); 2057 if (MONITOR_CPU_USAGE) { 2058 ServiceManager.addService("cpuinfo", new CpuBinder(this)); 2059 } 2060 ServiceManager.addService("permission", new PermissionController(this)); 2061 2062 ApplicationInfo info = mContext.getPackageManager().getApplicationInfo( 2063 "android", STOCK_PM_FLAGS); 2064 mSystemThread.installSystemApplicationInfo(info, getClass().getClassLoader()); 2065 2066 synchronized (this) { 2067 ProcessRecord app = newProcessRecordLocked(info, info.processName, false, 0); 2068 app.persistent = true; 2069 app.pid = MY_PID; 2070 app.maxAdj = ProcessList.SYSTEM_ADJ; 2071 app.makeActive(mSystemThread.getApplicationThread(), mProcessStats); 2072 mProcessNames.put(app.processName, app.uid, app); 2073 synchronized (mPidsSelfLocked) { 2074 mPidsSelfLocked.put(app.pid, app); 2075 } 2076 updateLruProcessLocked(app, false, null); 2077 updateOomAdjLocked(); 2078 } 2079 } catch (PackageManager.NameNotFoundException e) { 2080 throw new RuntimeException( 2081 "Unable to find android system package", e); 2082 } 2083 } 2084 2085 public void setWindowManager(WindowManagerService wm) { 2086 mWindowManager = wm; 2087 mStackSupervisor.setWindowManager(wm); 2088 } 2089 2090 public void setUsageStatsManager(UsageStatsManagerInternal usageStatsManager) { 2091 mUsageStatsService = usageStatsManager; 2092 } 2093 2094 public void startObservingNativeCrashes() { 2095 final NativeCrashListener ncl = new NativeCrashListener(this); 2096 ncl.start(); 2097 } 2098 2099 public IAppOpsService getAppOpsService() { 2100 return mAppOpsService; 2101 } 2102 2103 static class MemBinder extends Binder { 2104 ActivityManagerService mActivityManagerService; 2105 MemBinder(ActivityManagerService activityManagerService) { 2106 mActivityManagerService = activityManagerService; 2107 } 2108 2109 @Override 2110 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2111 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2112 != PackageManager.PERMISSION_GRANTED) { 2113 pw.println("Permission Denial: can't dump meminfo from from pid=" 2114 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2115 + " without permission " + android.Manifest.permission.DUMP); 2116 return; 2117 } 2118 2119 mActivityManagerService.dumpApplicationMemoryUsage(fd, pw, " ", args, false, null); 2120 } 2121 } 2122 2123 static class GraphicsBinder extends Binder { 2124 ActivityManagerService mActivityManagerService; 2125 GraphicsBinder(ActivityManagerService activityManagerService) { 2126 mActivityManagerService = activityManagerService; 2127 } 2128 2129 @Override 2130 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2131 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2132 != PackageManager.PERMISSION_GRANTED) { 2133 pw.println("Permission Denial: can't dump gfxinfo from from pid=" 2134 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2135 + " without permission " + android.Manifest.permission.DUMP); 2136 return; 2137 } 2138 2139 mActivityManagerService.dumpGraphicsHardwareUsage(fd, pw, args); 2140 } 2141 } 2142 2143 static class DbBinder extends Binder { 2144 ActivityManagerService mActivityManagerService; 2145 DbBinder(ActivityManagerService activityManagerService) { 2146 mActivityManagerService = activityManagerService; 2147 } 2148 2149 @Override 2150 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2151 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2152 != PackageManager.PERMISSION_GRANTED) { 2153 pw.println("Permission Denial: can't dump dbinfo from from pid=" 2154 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2155 + " without permission " + android.Manifest.permission.DUMP); 2156 return; 2157 } 2158 2159 mActivityManagerService.dumpDbInfo(fd, pw, args); 2160 } 2161 } 2162 2163 static class CpuBinder extends Binder { 2164 ActivityManagerService mActivityManagerService; 2165 CpuBinder(ActivityManagerService activityManagerService) { 2166 mActivityManagerService = activityManagerService; 2167 } 2168 2169 @Override 2170 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2171 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2172 != PackageManager.PERMISSION_GRANTED) { 2173 pw.println("Permission Denial: can't dump cpuinfo from from pid=" 2174 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2175 + " without permission " + android.Manifest.permission.DUMP); 2176 return; 2177 } 2178 2179 synchronized (mActivityManagerService.mProcessCpuThread) { 2180 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentLoad()); 2181 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentState( 2182 SystemClock.uptimeMillis())); 2183 } 2184 } 2185 } 2186 2187 public static final class Lifecycle extends SystemService { 2188 private final ActivityManagerService mService; 2189 2190 public Lifecycle(Context context) { 2191 super(context); 2192 mService = new ActivityManagerService(context); 2193 } 2194 2195 @Override 2196 public void onStart() { 2197 mService.start(); 2198 } 2199 2200 public ActivityManagerService getService() { 2201 return mService; 2202 } 2203 } 2204 2205 // Note: This method is invoked on the main thread but may need to attach various 2206 // handlers to other threads. So take care to be explicit about the looper. 2207 public ActivityManagerService(Context systemContext) { 2208 mContext = systemContext; 2209 mFactoryTest = FactoryTest.getMode(); 2210 mSystemThread = ActivityThread.currentActivityThread(); 2211 2212 Slog.i(TAG, "Memory class: " + ActivityManager.staticGetMemoryClass()); 2213 2214 mHandlerThread = new ServiceThread(TAG, 2215 android.os.Process.THREAD_PRIORITY_FOREGROUND, false /*allowIo*/); 2216 mHandlerThread.start(); 2217 mHandler = new MainHandler(mHandlerThread.getLooper()); 2218 2219 mFgBroadcastQueue = new BroadcastQueue(this, mHandler, 2220 "foreground", BROADCAST_FG_TIMEOUT, false); 2221 mBgBroadcastQueue = new BroadcastQueue(this, mHandler, 2222 "background", BROADCAST_BG_TIMEOUT, true); 2223 mBroadcastQueues[0] = mFgBroadcastQueue; 2224 mBroadcastQueues[1] = mBgBroadcastQueue; 2225 2226 mServices = new ActiveServices(this); 2227 mProviderMap = new ProviderMap(this); 2228 2229 // TODO: Move creation of battery stats service outside of activity manager service. 2230 File dataDir = Environment.getDataDirectory(); 2231 File systemDir = new File(dataDir, "system"); 2232 systemDir.mkdirs(); 2233 mBatteryStatsService = new BatteryStatsService(systemDir, mHandler); 2234 mBatteryStatsService.getActiveStatistics().readLocked(); 2235 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2236 mOnBattery = DEBUG_POWER ? true 2237 : mBatteryStatsService.getActiveStatistics().getIsOnBattery(); 2238 mBatteryStatsService.getActiveStatistics().setCallback(this); 2239 2240 mProcessStats = new ProcessStatsService(this, new File(systemDir, "procstats")); 2241 2242 mAppOpsService = new AppOpsService(new File(systemDir, "appops.xml"), mHandler); 2243 2244 mGrantFile = new AtomicFile(new File(systemDir, "urigrants.xml")); 2245 2246 // User 0 is the first and only user that runs at boot. 2247 mStartedUsers.put(0, new UserStartedState(new UserHandle(0), true)); 2248 mUserLru.add(Integer.valueOf(0)); 2249 updateStartedUserArrayLocked(); 2250 2251 GL_ES_VERSION = SystemProperties.getInt("ro.opengles.version", 2252 ConfigurationInfo.GL_ES_VERSION_UNDEFINED); 2253 2254 mConfiguration.setToDefaults(); 2255 mConfiguration.setLocale(Locale.getDefault()); 2256 2257 mConfigurationSeq = mConfiguration.seq = 1; 2258 mProcessCpuTracker.init(); 2259 2260 final Resources res = mContext.getResources(); 2261 mHasRecents = res.getBoolean(com.android.internal.R.bool.config_hasRecents); 2262 mThumbnailWidth = res.getDimensionPixelSize(com.android.internal.R.dimen.thumbnail_width); 2263 mThumbnailHeight = res.getDimensionPixelSize(com.android.internal.R.dimen.thumbnail_height); 2264 2265 mCompatModePackages = new CompatModePackages(this, systemDir, mHandler); 2266 mIntentFirewall = new IntentFirewall(new IntentFirewallInterface(), mHandler); 2267 mStackSupervisor = new ActivityStackSupervisor(this); 2268 mTaskPersister = new TaskPersister(systemDir, mStackSupervisor); 2269 2270 mProcessCpuThread = new Thread("CpuTracker") { 2271 @Override 2272 public void run() { 2273 while (true) { 2274 try { 2275 try { 2276 synchronized(this) { 2277 final long now = SystemClock.uptimeMillis(); 2278 long nextCpuDelay = (mLastCpuTime.get()+MONITOR_CPU_MAX_TIME)-now; 2279 long nextWriteDelay = (mLastWriteTime+BATTERY_STATS_TIME)-now; 2280 //Slog.i(TAG, "Cpu delay=" + nextCpuDelay 2281 // + ", write delay=" + nextWriteDelay); 2282 if (nextWriteDelay < nextCpuDelay) { 2283 nextCpuDelay = nextWriteDelay; 2284 } 2285 if (nextCpuDelay > 0) { 2286 mProcessCpuMutexFree.set(true); 2287 this.wait(nextCpuDelay); 2288 } 2289 } 2290 } catch (InterruptedException e) { 2291 } 2292 updateCpuStatsNow(); 2293 } catch (Exception e) { 2294 Slog.e(TAG, "Unexpected exception collecting process stats", e); 2295 } 2296 } 2297 } 2298 }; 2299 2300 mLockToAppRequest = new LockToAppRequestDialog(mContext, this); 2301 2302 Watchdog.getInstance().addMonitor(this); 2303 Watchdog.getInstance().addThread(mHandler); 2304 } 2305 2306 public void setSystemServiceManager(SystemServiceManager mgr) { 2307 mSystemServiceManager = mgr; 2308 } 2309 2310 private void start() { 2311 Process.removeAllProcessGroups(); 2312 mProcessCpuThread.start(); 2313 2314 mBatteryStatsService.publish(mContext); 2315 mAppOpsService.publish(mContext); 2316 Slog.d("AppOps", "AppOpsService published"); 2317 LocalServices.addService(ActivityManagerInternal.class, new LocalService()); 2318 } 2319 2320 public void initPowerManagement() { 2321 mStackSupervisor.initPowerManagement(); 2322 mBatteryStatsService.initPowerManagement(); 2323 } 2324 2325 @Override 2326 public boolean onTransact(int code, Parcel data, Parcel reply, int flags) 2327 throws RemoteException { 2328 if (code == SYSPROPS_TRANSACTION) { 2329 // We need to tell all apps about the system property change. 2330 ArrayList<IBinder> procs = new ArrayList<IBinder>(); 2331 synchronized(this) { 2332 final int NP = mProcessNames.getMap().size(); 2333 for (int ip=0; ip<NP; ip++) { 2334 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 2335 final int NA = apps.size(); 2336 for (int ia=0; ia<NA; ia++) { 2337 ProcessRecord app = apps.valueAt(ia); 2338 if (app.thread != null) { 2339 procs.add(app.thread.asBinder()); 2340 } 2341 } 2342 } 2343 } 2344 2345 int N = procs.size(); 2346 for (int i=0; i<N; i++) { 2347 Parcel data2 = Parcel.obtain(); 2348 try { 2349 procs.get(i).transact(IBinder.SYSPROPS_TRANSACTION, data2, null, 0); 2350 } catch (RemoteException e) { 2351 } 2352 data2.recycle(); 2353 } 2354 } 2355 try { 2356 return super.onTransact(code, data, reply, flags); 2357 } catch (RuntimeException e) { 2358 // The activity manager only throws security exceptions, so let's 2359 // log all others. 2360 if (!(e instanceof SecurityException)) { 2361 Slog.wtf(TAG, "Activity Manager Crash", e); 2362 } 2363 throw e; 2364 } 2365 } 2366 2367 void updateCpuStats() { 2368 final long now = SystemClock.uptimeMillis(); 2369 if (mLastCpuTime.get() >= now - MONITOR_CPU_MIN_TIME) { 2370 return; 2371 } 2372 if (mProcessCpuMutexFree.compareAndSet(true, false)) { 2373 synchronized (mProcessCpuThread) { 2374 mProcessCpuThread.notify(); 2375 } 2376 } 2377 } 2378 2379 void updateCpuStatsNow() { 2380 synchronized (mProcessCpuThread) { 2381 mProcessCpuMutexFree.set(false); 2382 final long now = SystemClock.uptimeMillis(); 2383 boolean haveNewCpuStats = false; 2384 2385 if (MONITOR_CPU_USAGE && 2386 mLastCpuTime.get() < (now-MONITOR_CPU_MIN_TIME)) { 2387 mLastCpuTime.set(now); 2388 haveNewCpuStats = true; 2389 mProcessCpuTracker.update(); 2390 //Slog.i(TAG, mProcessCpu.printCurrentState()); 2391 //Slog.i(TAG, "Total CPU usage: " 2392 // + mProcessCpu.getTotalCpuPercent() + "%"); 2393 2394 // Slog the cpu usage if the property is set. 2395 if ("true".equals(SystemProperties.get("events.cpu"))) { 2396 int user = mProcessCpuTracker.getLastUserTime(); 2397 int system = mProcessCpuTracker.getLastSystemTime(); 2398 int iowait = mProcessCpuTracker.getLastIoWaitTime(); 2399 int irq = mProcessCpuTracker.getLastIrqTime(); 2400 int softIrq = mProcessCpuTracker.getLastSoftIrqTime(); 2401 int idle = mProcessCpuTracker.getLastIdleTime(); 2402 2403 int total = user + system + iowait + irq + softIrq + idle; 2404 if (total == 0) total = 1; 2405 2406 EventLog.writeEvent(EventLogTags.CPU, 2407 ((user+system+iowait+irq+softIrq) * 100) / total, 2408 (user * 100) / total, 2409 (system * 100) / total, 2410 (iowait * 100) / total, 2411 (irq * 100) / total, 2412 (softIrq * 100) / total); 2413 } 2414 } 2415 2416 long[] cpuSpeedTimes = mProcessCpuTracker.getLastCpuSpeedTimes(); 2417 final BatteryStatsImpl bstats = mBatteryStatsService.getActiveStatistics(); 2418 synchronized(bstats) { 2419 synchronized(mPidsSelfLocked) { 2420 if (haveNewCpuStats) { 2421 if (mOnBattery) { 2422 int perc = bstats.startAddingCpuLocked(); 2423 int totalUTime = 0; 2424 int totalSTime = 0; 2425 final int N = mProcessCpuTracker.countStats(); 2426 for (int i=0; i<N; i++) { 2427 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 2428 if (!st.working) { 2429 continue; 2430 } 2431 ProcessRecord pr = mPidsSelfLocked.get(st.pid); 2432 int otherUTime = (st.rel_utime*perc)/100; 2433 int otherSTime = (st.rel_stime*perc)/100; 2434 totalUTime += otherUTime; 2435 totalSTime += otherSTime; 2436 if (pr != null) { 2437 BatteryStatsImpl.Uid.Proc ps = pr.curProcBatteryStats; 2438 if (ps == null || !ps.isActive()) { 2439 pr.curProcBatteryStats = ps = bstats.getProcessStatsLocked( 2440 pr.info.uid, pr.processName); 2441 } 2442 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2443 st.rel_stime-otherSTime); 2444 ps.addSpeedStepTimes(cpuSpeedTimes); 2445 pr.curCpuTime += (st.rel_utime+st.rel_stime) * 10; 2446 } else { 2447 BatteryStatsImpl.Uid.Proc ps = st.batteryStats; 2448 if (ps == null || !ps.isActive()) { 2449 st.batteryStats = ps = bstats.getProcessStatsLocked( 2450 bstats.mapUid(st.uid), st.name); 2451 } 2452 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2453 st.rel_stime-otherSTime); 2454 ps.addSpeedStepTimes(cpuSpeedTimes); 2455 } 2456 } 2457 bstats.finishAddingCpuLocked(perc, totalUTime, 2458 totalSTime, cpuSpeedTimes); 2459 } 2460 } 2461 } 2462 2463 if (mLastWriteTime < (now-BATTERY_STATS_TIME)) { 2464 mLastWriteTime = now; 2465 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2466 } 2467 } 2468 } 2469 } 2470 2471 @Override 2472 public void batteryNeedsCpuUpdate() { 2473 updateCpuStatsNow(); 2474 } 2475 2476 @Override 2477 public void batteryPowerChanged(boolean onBattery) { 2478 // When plugging in, update the CPU stats first before changing 2479 // the plug state. 2480 updateCpuStatsNow(); 2481 synchronized (this) { 2482 synchronized(mPidsSelfLocked) { 2483 mOnBattery = DEBUG_POWER ? true : onBattery; 2484 } 2485 } 2486 } 2487 2488 /** 2489 * Initialize the application bind args. These are passed to each 2490 * process when the bindApplication() IPC is sent to the process. They're 2491 * lazily setup to make sure the services are running when they're asked for. 2492 */ 2493 private HashMap<String, IBinder> getCommonServicesLocked() { 2494 if (mAppBindArgs == null) { 2495 mAppBindArgs = new HashMap<String, IBinder>(); 2496 2497 // Setup the application init args 2498 mAppBindArgs.put("package", ServiceManager.getService("package")); 2499 mAppBindArgs.put("window", ServiceManager.getService("window")); 2500 mAppBindArgs.put(Context.ALARM_SERVICE, 2501 ServiceManager.getService(Context.ALARM_SERVICE)); 2502 } 2503 return mAppBindArgs; 2504 } 2505 2506 final void setFocusedActivityLocked(ActivityRecord r) { 2507 if (mFocusedActivity != r) { 2508 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedActivityLocked: r=" + r); 2509 mFocusedActivity = r; 2510 if (r.task != null && r.task.voiceInteractor != null) { 2511 startRunningVoiceLocked(); 2512 } else { 2513 finishRunningVoiceLocked(); 2514 } 2515 mStackSupervisor.setFocusedStack(r); 2516 if (r != null) { 2517 mWindowManager.setFocusedApp(r.appToken, true); 2518 } 2519 applyUpdateLockStateLocked(r); 2520 } 2521 } 2522 2523 final void clearFocusedActivity(ActivityRecord r) { 2524 if (mFocusedActivity == r) { 2525 mFocusedActivity = null; 2526 } 2527 } 2528 2529 @Override 2530 public void setFocusedStack(int stackId) { 2531 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedStack: stackId=" + stackId); 2532 synchronized (ActivityManagerService.this) { 2533 ActivityStack stack = mStackSupervisor.getStack(stackId); 2534 if (stack != null) { 2535 ActivityRecord r = stack.topRunningActivityLocked(null); 2536 if (r != null) { 2537 setFocusedActivityLocked(r); 2538 } 2539 } 2540 } 2541 } 2542 2543 @Override 2544 public void notifyActivityDrawn(IBinder token) { 2545 if (DEBUG_VISBILITY) Slog.d(TAG, "notifyActivityDrawn: token=" + token); 2546 synchronized (this) { 2547 ActivityRecord r= mStackSupervisor.isInAnyStackLocked(token); 2548 if (r != null) { 2549 r.task.stack.notifyActivityDrawnLocked(r); 2550 } 2551 } 2552 } 2553 2554 final void applyUpdateLockStateLocked(ActivityRecord r) { 2555 // Modifications to the UpdateLock state are done on our handler, outside 2556 // the activity manager's locks. The new state is determined based on the 2557 // state *now* of the relevant activity record. The object is passed to 2558 // the handler solely for logging detail, not to be consulted/modified. 2559 final boolean nextState = r != null && r.immersive; 2560 mHandler.sendMessage( 2561 mHandler.obtainMessage(IMMERSIVE_MODE_LOCK_MSG, (nextState) ? 1 : 0, 0, r)); 2562 } 2563 2564 final void showAskCompatModeDialogLocked(ActivityRecord r) { 2565 Message msg = Message.obtain(); 2566 msg.what = SHOW_COMPAT_MODE_DIALOG_MSG; 2567 msg.obj = r.task.askedCompatMode ? null : r; 2568 mHandler.sendMessage(msg); 2569 } 2570 2571 private final int updateLruProcessInternalLocked(ProcessRecord app, long now, int index, 2572 String what, Object obj, ProcessRecord srcApp) { 2573 app.lastActivityTime = now; 2574 2575 if (app.activities.size() > 0) { 2576 // Don't want to touch dependent processes that are hosting activities. 2577 return index; 2578 } 2579 2580 int lrui = mLruProcesses.lastIndexOf(app); 2581 if (lrui < 0) { 2582 Slog.wtf(TAG, "Adding dependent process " + app + " not on LRU list: " 2583 + what + " " + obj + " from " + srcApp); 2584 return index; 2585 } 2586 2587 if (lrui >= index) { 2588 // Don't want to cause this to move dependent processes *back* in the 2589 // list as if they were less frequently used. 2590 return index; 2591 } 2592 2593 if (lrui >= mLruProcessActivityStart) { 2594 // Don't want to touch dependent processes that are hosting activities. 2595 return index; 2596 } 2597 2598 mLruProcesses.remove(lrui); 2599 if (index > 0) { 2600 index--; 2601 } 2602 if (DEBUG_LRU) Slog.d(TAG, "Moving dep from " + lrui + " to " + index 2603 + " in LRU list: " + app); 2604 mLruProcesses.add(index, app); 2605 return index; 2606 } 2607 2608 final void removeLruProcessLocked(ProcessRecord app) { 2609 int lrui = mLruProcesses.lastIndexOf(app); 2610 if (lrui >= 0) { 2611 if (lrui <= mLruProcessActivityStart) { 2612 mLruProcessActivityStart--; 2613 } 2614 if (lrui <= mLruProcessServiceStart) { 2615 mLruProcessServiceStart--; 2616 } 2617 mLruProcesses.remove(lrui); 2618 } 2619 } 2620 2621 final void updateLruProcessLocked(ProcessRecord app, boolean activityChange, 2622 ProcessRecord client) { 2623 final boolean hasActivity = app.activities.size() > 0 || app.hasClientActivities 2624 || app.treatLikeActivity; 2625 final boolean hasService = false; // not impl yet. app.services.size() > 0; 2626 if (!activityChange && hasActivity) { 2627 // The process has activities, so we are only allowing activity-based adjustments 2628 // to move it. It should be kept in the front of the list with other 2629 // processes that have activities, and we don't want those to change their 2630 // order except due to activity operations. 2631 return; 2632 } 2633 2634 mLruSeq++; 2635 final long now = SystemClock.uptimeMillis(); 2636 app.lastActivityTime = now; 2637 2638 // First a quick reject: if the app is already at the position we will 2639 // put it, then there is nothing to do. 2640 if (hasActivity) { 2641 final int N = mLruProcesses.size(); 2642 if (N > 0 && mLruProcesses.get(N-1) == app) { 2643 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top activity: " + app); 2644 return; 2645 } 2646 } else { 2647 if (mLruProcessServiceStart > 0 2648 && mLruProcesses.get(mLruProcessServiceStart-1) == app) { 2649 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top other: " + app); 2650 return; 2651 } 2652 } 2653 2654 int lrui = mLruProcesses.lastIndexOf(app); 2655 2656 if (app.persistent && lrui >= 0) { 2657 // We don't care about the position of persistent processes, as long as 2658 // they are in the list. 2659 if (DEBUG_LRU) Slog.d(TAG, "Not moving, persistent: " + app); 2660 return; 2661 } 2662 2663 /* In progress: compute new position first, so we can avoid doing work 2664 if the process is not actually going to move. Not yet working. 2665 int addIndex; 2666 int nextIndex; 2667 boolean inActivity = false, inService = false; 2668 if (hasActivity) { 2669 // Process has activities, put it at the very tipsy-top. 2670 addIndex = mLruProcesses.size(); 2671 nextIndex = mLruProcessServiceStart; 2672 inActivity = true; 2673 } else if (hasService) { 2674 // Process has services, put it at the top of the service list. 2675 addIndex = mLruProcessActivityStart; 2676 nextIndex = mLruProcessServiceStart; 2677 inActivity = true; 2678 inService = true; 2679 } else { 2680 // Process not otherwise of interest, it goes to the top of the non-service area. 2681 addIndex = mLruProcessServiceStart; 2682 if (client != null) { 2683 int clientIndex = mLruProcesses.lastIndexOf(client); 2684 if (clientIndex < 0) Slog.d(TAG, "Unknown client " + client + " when updating " 2685 + app); 2686 if (clientIndex >= 0 && addIndex > clientIndex) { 2687 addIndex = clientIndex; 2688 } 2689 } 2690 nextIndex = addIndex > 0 ? addIndex-1 : addIndex; 2691 } 2692 2693 Slog.d(TAG, "Update LRU at " + lrui + " to " + addIndex + " (act=" 2694 + mLruProcessActivityStart + "): " + app); 2695 */ 2696 2697 if (lrui >= 0) { 2698 if (lrui < mLruProcessActivityStart) { 2699 mLruProcessActivityStart--; 2700 } 2701 if (lrui < mLruProcessServiceStart) { 2702 mLruProcessServiceStart--; 2703 } 2704 /* 2705 if (addIndex > lrui) { 2706 addIndex--; 2707 } 2708 if (nextIndex > lrui) { 2709 nextIndex--; 2710 } 2711 */ 2712 mLruProcesses.remove(lrui); 2713 } 2714 2715 /* 2716 mLruProcesses.add(addIndex, app); 2717 if (inActivity) { 2718 mLruProcessActivityStart++; 2719 } 2720 if (inService) { 2721 mLruProcessActivityStart++; 2722 } 2723 */ 2724 2725 int nextIndex; 2726 if (hasActivity) { 2727 final int N = mLruProcesses.size(); 2728 if (app.activities.size() == 0 && mLruProcessActivityStart < (N-1)) { 2729 // Process doesn't have activities, but has clients with 2730 // activities... move it up, but one below the top (the top 2731 // should always have a real activity). 2732 if (DEBUG_LRU) Slog.d(TAG, "Adding to second-top of LRU activity list: " + app); 2733 mLruProcesses.add(N-1, app); 2734 // To keep it from spamming the LRU list (by making a bunch of clients), 2735 // we will push down any other entries owned by the app. 2736 final int uid = app.info.uid; 2737 for (int i=N-2; i>mLruProcessActivityStart; i--) { 2738 ProcessRecord subProc = mLruProcesses.get(i); 2739 if (subProc.info.uid == uid) { 2740 // We want to push this one down the list. If the process after 2741 // it is for the same uid, however, don't do so, because we don't 2742 // want them internally to be re-ordered. 2743 if (mLruProcesses.get(i-1).info.uid != uid) { 2744 if (DEBUG_LRU) Slog.d(TAG, "Pushing uid " + uid + " swapping at " + i 2745 + ": " + mLruProcesses.get(i) + " : " + mLruProcesses.get(i-1)); 2746 ProcessRecord tmp = mLruProcesses.get(i); 2747 mLruProcesses.set(i, mLruProcesses.get(i-1)); 2748 mLruProcesses.set(i-1, tmp); 2749 i--; 2750 } 2751 } else { 2752 // A gap, we can stop here. 2753 break; 2754 } 2755 } 2756 } else { 2757 // Process has activities, put it at the very tipsy-top. 2758 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU activity list: " + app); 2759 mLruProcesses.add(app); 2760 } 2761 nextIndex = mLruProcessServiceStart; 2762 } else if (hasService) { 2763 // Process has services, put it at the top of the service list. 2764 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU service list: " + app); 2765 mLruProcesses.add(mLruProcessActivityStart, app); 2766 nextIndex = mLruProcessServiceStart; 2767 mLruProcessActivityStart++; 2768 } else { 2769 // Process not otherwise of interest, it goes to the top of the non-service area. 2770 int index = mLruProcessServiceStart; 2771 if (client != null) { 2772 // If there is a client, don't allow the process to be moved up higher 2773 // in the list than that client. 2774 int clientIndex = mLruProcesses.lastIndexOf(client); 2775 if (DEBUG_LRU && clientIndex < 0) Slog.d(TAG, "Unknown client " + client 2776 + " when updating " + app); 2777 if (clientIndex <= lrui) { 2778 // Don't allow the client index restriction to push it down farther in the 2779 // list than it already is. 2780 clientIndex = lrui; 2781 } 2782 if (clientIndex >= 0 && index > clientIndex) { 2783 index = clientIndex; 2784 } 2785 } 2786 if (DEBUG_LRU) Slog.d(TAG, "Adding at " + index + " of LRU list: " + app); 2787 mLruProcesses.add(index, app); 2788 nextIndex = index-1; 2789 mLruProcessActivityStart++; 2790 mLruProcessServiceStart++; 2791 } 2792 2793 // If the app is currently using a content provider or service, 2794 // bump those processes as well. 2795 for (int j=app.connections.size()-1; j>=0; j--) { 2796 ConnectionRecord cr = app.connections.valueAt(j); 2797 if (cr.binding != null && !cr.serviceDead && cr.binding.service != null 2798 && cr.binding.service.app != null 2799 && cr.binding.service.app.lruSeq != mLruSeq 2800 && !cr.binding.service.app.persistent) { 2801 nextIndex = updateLruProcessInternalLocked(cr.binding.service.app, now, nextIndex, 2802 "service connection", cr, app); 2803 } 2804 } 2805 for (int j=app.conProviders.size()-1; j>=0; j--) { 2806 ContentProviderRecord cpr = app.conProviders.get(j).provider; 2807 if (cpr.proc != null && cpr.proc.lruSeq != mLruSeq && !cpr.proc.persistent) { 2808 nextIndex = updateLruProcessInternalLocked(cpr.proc, now, nextIndex, 2809 "provider reference", cpr, app); 2810 } 2811 } 2812 } 2813 2814 final ProcessRecord getProcessRecordLocked(String processName, int uid, boolean keepIfLarge) { 2815 if (uid == Process.SYSTEM_UID) { 2816 // The system gets to run in any process. If there are multiple 2817 // processes with the same uid, just pick the first (this 2818 // should never happen). 2819 SparseArray<ProcessRecord> procs = mProcessNames.getMap().get(processName); 2820 if (procs == null) return null; 2821 final int N = procs.size(); 2822 for (int i = 0; i < N; i++) { 2823 if (UserHandle.isSameUser(procs.keyAt(i), uid)) return procs.valueAt(i); 2824 } 2825 } 2826 ProcessRecord proc = mProcessNames.get(processName, uid); 2827 if (false && proc != null && !keepIfLarge 2828 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY 2829 && proc.lastCachedPss >= 4000) { 2830 // Turn this condition on to cause killing to happen regularly, for testing. 2831 if (proc.baseProcessTracker != null) { 2832 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2833 } 2834 killUnneededProcessLocked(proc, Long.toString(proc.lastCachedPss) 2835 + "k from cached"); 2836 } else if (proc != null && !keepIfLarge 2837 && mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 2838 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 2839 if (DEBUG_PSS) Slog.d(TAG, "May not keep " + proc + ": pss=" + proc.lastCachedPss); 2840 if (proc.lastCachedPss >= mProcessList.getCachedRestoreThresholdKb()) { 2841 if (proc.baseProcessTracker != null) { 2842 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2843 } 2844 killUnneededProcessLocked(proc, Long.toString(proc.lastCachedPss) 2845 + "k from cached"); 2846 } 2847 } 2848 return proc; 2849 } 2850 2851 void ensurePackageDexOpt(String packageName) { 2852 IPackageManager pm = AppGlobals.getPackageManager(); 2853 try { 2854 if (pm.performDexOptIfNeeded(packageName, null /* instruction set */)) { 2855 mDidDexOpt = true; 2856 } 2857 } catch (RemoteException e) { 2858 } 2859 } 2860 2861 boolean isNextTransitionForward() { 2862 int transit = mWindowManager.getPendingAppTransition(); 2863 return transit == AppTransition.TRANSIT_ACTIVITY_OPEN 2864 || transit == AppTransition.TRANSIT_TASK_OPEN 2865 || transit == AppTransition.TRANSIT_TASK_TO_FRONT; 2866 } 2867 2868 int startIsolatedProcess(String entryPoint, String[] entryPointArgs, 2869 String processName, String abiOverride, int uid, Runnable crashHandler) { 2870 synchronized(this) { 2871 ApplicationInfo info = new ApplicationInfo(); 2872 // In general the ApplicationInfo.uid isn't neccesarily equal to ProcessRecord.uid. 2873 // For isolated processes, the former contains the parent's uid and the latter the 2874 // actual uid of the isolated process. 2875 // In the special case introduced by this method (which is, starting an isolated 2876 // process directly from the SystemServer without an actual parent app process) the 2877 // closest thing to a parent's uid is SYSTEM_UID. 2878 // The only important thing here is to keep AI.uid != PR.uid, in order to trigger 2879 // the |isolated| logic in the ProcessRecord constructor. 2880 info.uid = Process.SYSTEM_UID; 2881 info.processName = processName; 2882 info.className = entryPoint; 2883 info.packageName = "android"; 2884 ProcessRecord proc = startProcessLocked(processName, info /* info */, 2885 false /* knownToBeDead */, 0 /* intentFlags */, "" /* hostingType */, 2886 null /* hostingName */, true /* allowWhileBooting */, true /* isolated */, 2887 uid, true /* keepIfLarge */, abiOverride, entryPoint, entryPointArgs, 2888 crashHandler); 2889 return proc != null ? proc.pid : 0; 2890 } 2891 } 2892 2893 final ProcessRecord startProcessLocked(String processName, 2894 ApplicationInfo info, boolean knownToBeDead, int intentFlags, 2895 String hostingType, ComponentName hostingName, boolean allowWhileBooting, 2896 boolean isolated, boolean keepIfLarge) { 2897 return startProcessLocked(processName, info, knownToBeDead, intentFlags, hostingType, 2898 hostingName, allowWhileBooting, isolated, 0 /* isolatedUid */, keepIfLarge, 2899 null /* ABI override */, null /* entryPoint */, null /* entryPointArgs */, 2900 null /* crashHandler */); 2901 } 2902 2903 final ProcessRecord startProcessLocked(String processName, ApplicationInfo info, 2904 boolean knownToBeDead, int intentFlags, String hostingType, ComponentName hostingName, 2905 boolean allowWhileBooting, boolean isolated, int isolatedUid, boolean keepIfLarge, 2906 String abiOverride, String entryPoint, String[] entryPointArgs, Runnable crashHandler) { 2907 ProcessRecord app; 2908 if (!isolated) { 2909 app = getProcessRecordLocked(processName, info.uid, keepIfLarge); 2910 } else { 2911 // If this is an isolated process, it can't re-use an existing process. 2912 app = null; 2913 } 2914 // We don't have to do anything more if: 2915 // (1) There is an existing application record; and 2916 // (2) The caller doesn't think it is dead, OR there is no thread 2917 // object attached to it so we know it couldn't have crashed; and 2918 // (3) There is a pid assigned to it, so it is either starting or 2919 // already running. 2920 if (DEBUG_PROCESSES) Slog.v(TAG, "startProcess: name=" + processName 2921 + " app=" + app + " knownToBeDead=" + knownToBeDead 2922 + " thread=" + (app != null ? app.thread : null) 2923 + " pid=" + (app != null ? app.pid : -1)); 2924 if (app != null && app.pid > 0) { 2925 if (!knownToBeDead || app.thread == null) { 2926 // We already have the app running, or are waiting for it to 2927 // come up (we have a pid but not yet its thread), so keep it. 2928 if (DEBUG_PROCESSES) Slog.v(TAG, "App already running: " + app); 2929 // If this is a new package in the process, add the package to the list 2930 app.addPackage(info.packageName, info.versionCode, mProcessStats); 2931 return app; 2932 } 2933 2934 // An application record is attached to a previous process, 2935 // clean it up now. 2936 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, "App died: " + app); 2937 Process.killProcessGroup(app.info.uid, app.pid); 2938 handleAppDiedLocked(app, true, true); 2939 } 2940 2941 String hostingNameStr = hostingName != null 2942 ? hostingName.flattenToShortString() : null; 2943 2944 if (!isolated) { 2945 if ((intentFlags&Intent.FLAG_FROM_BACKGROUND) != 0) { 2946 // If we are in the background, then check to see if this process 2947 // is bad. If so, we will just silently fail. 2948 if (mBadProcesses.get(info.processName, info.uid) != null) { 2949 if (DEBUG_PROCESSES) Slog.v(TAG, "Bad process: " + info.uid 2950 + "/" + info.processName); 2951 return null; 2952 } 2953 } else { 2954 // When the user is explicitly starting a process, then clear its 2955 // crash count so that we won't make it bad until they see at 2956 // least one crash dialog again, and make the process good again 2957 // if it had been bad. 2958 if (DEBUG_PROCESSES) Slog.v(TAG, "Clearing bad process: " + info.uid 2959 + "/" + info.processName); 2960 mProcessCrashTimes.remove(info.processName, info.uid); 2961 if (mBadProcesses.get(info.processName, info.uid) != null) { 2962 EventLog.writeEvent(EventLogTags.AM_PROC_GOOD, 2963 UserHandle.getUserId(info.uid), info.uid, 2964 info.processName); 2965 mBadProcesses.remove(info.processName, info.uid); 2966 if (app != null) { 2967 app.bad = false; 2968 } 2969 } 2970 } 2971 } 2972 2973 if (app == null) { 2974 app = newProcessRecordLocked(info, processName, isolated, isolatedUid); 2975 app.crashHandler = crashHandler; 2976 if (app == null) { 2977 Slog.w(TAG, "Failed making new process record for " 2978 + processName + "/" + info.uid + " isolated=" + isolated); 2979 return null; 2980 } 2981 mProcessNames.put(processName, app.uid, app); 2982 if (isolated) { 2983 mIsolatedProcesses.put(app.uid, app); 2984 } 2985 } else { 2986 // If this is a new package in the process, add the package to the list 2987 app.addPackage(info.packageName, info.versionCode, mProcessStats); 2988 } 2989 2990 // If the system is not ready yet, then hold off on starting this 2991 // process until it is. 2992 if (!mProcessesReady 2993 && !isAllowedWhileBooting(info) 2994 && !allowWhileBooting) { 2995 if (!mProcessesOnHold.contains(app)) { 2996 mProcessesOnHold.add(app); 2997 } 2998 if (DEBUG_PROCESSES) Slog.v(TAG, "System not ready, putting on hold: " + app); 2999 return app; 3000 } 3001 3002 startProcessLocked( 3003 app, hostingType, hostingNameStr, abiOverride, entryPoint, entryPointArgs); 3004 return (app.pid != 0) ? app : null; 3005 } 3006 3007 boolean isAllowedWhileBooting(ApplicationInfo ai) { 3008 return (ai.flags&ApplicationInfo.FLAG_PERSISTENT) != 0; 3009 } 3010 3011 private final void startProcessLocked(ProcessRecord app, 3012 String hostingType, String hostingNameStr) { 3013 startProcessLocked(app, hostingType, hostingNameStr, null /* abiOverride */, 3014 null /* entryPoint */, null /* entryPointArgs */); 3015 } 3016 3017 private final void startProcessLocked(ProcessRecord app, String hostingType, 3018 String hostingNameStr, String abiOverride, String entryPoint, String[] entryPointArgs) { 3019 if (app.pid > 0 && app.pid != MY_PID) { 3020 synchronized (mPidsSelfLocked) { 3021 mPidsSelfLocked.remove(app.pid); 3022 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 3023 } 3024 app.setPid(0); 3025 } 3026 3027 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 3028 "startProcessLocked removing on hold: " + app); 3029 mProcessesOnHold.remove(app); 3030 3031 updateCpuStats(); 3032 3033 try { 3034 int uid = app.uid; 3035 3036 int[] gids = null; 3037 int mountExternal = Zygote.MOUNT_EXTERNAL_NONE; 3038 if (!app.isolated) { 3039 int[] permGids = null; 3040 try { 3041 final PackageManager pm = mContext.getPackageManager(); 3042 permGids = pm.getPackageGids(app.info.packageName); 3043 3044 if (Environment.isExternalStorageEmulated()) { 3045 if (pm.checkPermission( 3046 android.Manifest.permission.ACCESS_ALL_EXTERNAL_STORAGE, 3047 app.info.packageName) == PERMISSION_GRANTED) { 3048 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER_ALL; 3049 } else { 3050 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER; 3051 } 3052 } 3053 } catch (PackageManager.NameNotFoundException e) { 3054 Slog.w(TAG, "Unable to retrieve gids", e); 3055 } 3056 3057 /* 3058 * Add shared application and profile GIDs so applications can share some 3059 * resources like shared libraries and access user-wide resources 3060 */ 3061 if (permGids == null) { 3062 gids = new int[2]; 3063 } else { 3064 gids = new int[permGids.length + 2]; 3065 System.arraycopy(permGids, 0, gids, 2, permGids.length); 3066 } 3067 gids[0] = UserHandle.getSharedAppGid(UserHandle.getAppId(uid)); 3068 gids[1] = UserHandle.getUserGid(UserHandle.getUserId(uid)); 3069 } 3070 if (mFactoryTest != FactoryTest.FACTORY_TEST_OFF) { 3071 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3072 && mTopComponent != null 3073 && app.processName.equals(mTopComponent.getPackageName())) { 3074 uid = 0; 3075 } 3076 if (mFactoryTest == FactoryTest.FACTORY_TEST_HIGH_LEVEL 3077 && (app.info.flags&ApplicationInfo.FLAG_FACTORY_TEST) != 0) { 3078 uid = 0; 3079 } 3080 } 3081 int debugFlags = 0; 3082 if ((app.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 3083 debugFlags |= Zygote.DEBUG_ENABLE_DEBUGGER; 3084 // Also turn on CheckJNI for debuggable apps. It's quite 3085 // awkward to turn on otherwise. 3086 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 3087 } 3088 // Run the app in safe mode if its manifest requests so or the 3089 // system is booted in safe mode. 3090 if ((app.info.flags & ApplicationInfo.FLAG_VM_SAFE_MODE) != 0 || 3091 mSafeMode == true) { 3092 debugFlags |= Zygote.DEBUG_ENABLE_SAFEMODE; 3093 } 3094 if ("1".equals(SystemProperties.get("debug.checkjni"))) { 3095 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 3096 } 3097 if ("1".equals(SystemProperties.get("debug.jni.logging"))) { 3098 debugFlags |= Zygote.DEBUG_ENABLE_JNI_LOGGING; 3099 } 3100 if ("1".equals(SystemProperties.get("debug.assert"))) { 3101 debugFlags |= Zygote.DEBUG_ENABLE_ASSERT; 3102 } 3103 3104 String requiredAbi = (abiOverride != null) ? abiOverride : app.info.primaryCpuAbi; 3105 if (requiredAbi == null) { 3106 requiredAbi = Build.SUPPORTED_ABIS[0]; 3107 } 3108 3109 // Start the process. It will either succeed and return a result containing 3110 // the PID of the new process, or else throw a RuntimeException. 3111 boolean isActivityProcess = (entryPoint == null); 3112 if (entryPoint == null) entryPoint = "android.app.ActivityThread"; 3113 Process.ProcessStartResult startResult = Process.start(entryPoint, 3114 app.processName, uid, uid, gids, debugFlags, mountExternal, 3115 app.info.targetSdkVersion, app.info.seinfo, requiredAbi, entryPointArgs); 3116 3117 if (app.isolated) { 3118 mBatteryStatsService.addIsolatedUid(app.uid, app.info.uid); 3119 } 3120 mBatteryStatsService.noteProcessStart(app.processName, app.info.uid); 3121 3122 EventLog.writeEvent(EventLogTags.AM_PROC_START, 3123 UserHandle.getUserId(uid), startResult.pid, uid, 3124 app.processName, hostingType, 3125 hostingNameStr != null ? hostingNameStr : ""); 3126 3127 if (app.persistent) { 3128 Watchdog.getInstance().processStarted(app.processName, startResult.pid); 3129 } 3130 3131 StringBuilder buf = mStringBuilder; 3132 buf.setLength(0); 3133 buf.append("Start proc "); 3134 buf.append(app.processName); 3135 if (!isActivityProcess) { 3136 buf.append(" ["); 3137 buf.append(entryPoint); 3138 buf.append("]"); 3139 } 3140 buf.append(" for "); 3141 buf.append(hostingType); 3142 if (hostingNameStr != null) { 3143 buf.append(" "); 3144 buf.append(hostingNameStr); 3145 } 3146 buf.append(": pid="); 3147 buf.append(startResult.pid); 3148 buf.append(" uid="); 3149 buf.append(uid); 3150 buf.append(" gids={"); 3151 if (gids != null) { 3152 for (int gi=0; gi<gids.length; gi++) { 3153 if (gi != 0) buf.append(", "); 3154 buf.append(gids[gi]); 3155 3156 } 3157 } 3158 buf.append("}"); 3159 if (requiredAbi != null) { 3160 buf.append(" abi="); 3161 buf.append(requiredAbi); 3162 } 3163 Slog.i(TAG, buf.toString()); 3164 app.setPid(startResult.pid); 3165 app.usingWrapper = startResult.usingWrapper; 3166 app.removed = false; 3167 app.killedByAm = false; 3168 synchronized (mPidsSelfLocked) { 3169 this.mPidsSelfLocked.put(startResult.pid, app); 3170 if (isActivityProcess) { 3171 Message msg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 3172 msg.obj = app; 3173 mHandler.sendMessageDelayed(msg, startResult.usingWrapper 3174 ? PROC_START_TIMEOUT_WITH_WRAPPER : PROC_START_TIMEOUT); 3175 } 3176 } 3177 } catch (RuntimeException e) { 3178 // XXX do better error recovery. 3179 app.setPid(0); 3180 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 3181 if (app.isolated) { 3182 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 3183 } 3184 Slog.e(TAG, "Failure starting process " + app.processName, e); 3185 } 3186 } 3187 3188 void updateUsageStats(ActivityRecord component, boolean resumed) { 3189 if (DEBUG_SWITCH) Slog.d(TAG, "updateUsageStats: comp=" + component + "res=" + resumed); 3190 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 3191 if (resumed) { 3192 if (mUsageStatsService != null) { 3193 mUsageStatsService.reportEvent(component.realActivity, component.userId, 3194 System.currentTimeMillis(), 3195 UsageEvents.Event.MOVE_TO_FOREGROUND); 3196 } 3197 synchronized (stats) { 3198 stats.noteActivityResumedLocked(component.app.uid); 3199 } 3200 } else { 3201 if (mUsageStatsService != null) { 3202 mUsageStatsService.reportEvent(component.realActivity, component.userId, 3203 System.currentTimeMillis(), 3204 UsageEvents.Event.MOVE_TO_BACKGROUND); 3205 } 3206 synchronized (stats) { 3207 stats.noteActivityPausedLocked(component.app.uid); 3208 } 3209 } 3210 } 3211 3212 Intent getHomeIntent() { 3213 Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null); 3214 intent.setComponent(mTopComponent); 3215 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 3216 intent.addCategory(Intent.CATEGORY_HOME); 3217 } 3218 return intent; 3219 } 3220 3221 boolean startHomeActivityLocked(int userId) { 3222 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3223 && mTopAction == null) { 3224 // We are running in factory test mode, but unable to find 3225 // the factory test app, so just sit around displaying the 3226 // error message and don't try to start anything. 3227 return false; 3228 } 3229 Intent intent = getHomeIntent(); 3230 ActivityInfo aInfo = 3231 resolveActivityInfo(intent, STOCK_PM_FLAGS, userId); 3232 if (aInfo != null) { 3233 intent.setComponent(new ComponentName( 3234 aInfo.applicationInfo.packageName, aInfo.name)); 3235 // Don't do this if the home app is currently being 3236 // instrumented. 3237 aInfo = new ActivityInfo(aInfo); 3238 aInfo.applicationInfo = getAppInfoForUser(aInfo.applicationInfo, userId); 3239 ProcessRecord app = getProcessRecordLocked(aInfo.processName, 3240 aInfo.applicationInfo.uid, true); 3241 if (app == null || app.instrumentationClass == null) { 3242 intent.setFlags(intent.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK); 3243 mStackSupervisor.startHomeActivity(intent, aInfo); 3244 } 3245 } 3246 3247 return true; 3248 } 3249 3250 private ActivityInfo resolveActivityInfo(Intent intent, int flags, int userId) { 3251 ActivityInfo ai = null; 3252 ComponentName comp = intent.getComponent(); 3253 try { 3254 if (comp != null) { 3255 ai = AppGlobals.getPackageManager().getActivityInfo(comp, flags, userId); 3256 } else { 3257 ResolveInfo info = AppGlobals.getPackageManager().resolveIntent( 3258 intent, 3259 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 3260 flags, userId); 3261 3262 if (info != null) { 3263 ai = info.activityInfo; 3264 } 3265 } 3266 } catch (RemoteException e) { 3267 // ignore 3268 } 3269 3270 return ai; 3271 } 3272 3273 /** 3274 * Starts the "new version setup screen" if appropriate. 3275 */ 3276 void startSetupActivityLocked() { 3277 // Only do this once per boot. 3278 if (mCheckedForSetup) { 3279 return; 3280 } 3281 3282 // We will show this screen if the current one is a different 3283 // version than the last one shown, and we are not running in 3284 // low-level factory test mode. 3285 final ContentResolver resolver = mContext.getContentResolver(); 3286 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL && 3287 Settings.Global.getInt(resolver, 3288 Settings.Global.DEVICE_PROVISIONED, 0) != 0) { 3289 mCheckedForSetup = true; 3290 3291 // See if we should be showing the platform update setup UI. 3292 Intent intent = new Intent(Intent.ACTION_UPGRADE_SETUP); 3293 List<ResolveInfo> ris = mContext.getPackageManager() 3294 .queryIntentActivities(intent, PackageManager.GET_META_DATA); 3295 3296 // We don't allow third party apps to replace this. 3297 ResolveInfo ri = null; 3298 for (int i=0; ris != null && i<ris.size(); i++) { 3299 if ((ris.get(i).activityInfo.applicationInfo.flags 3300 & ApplicationInfo.FLAG_SYSTEM) != 0) { 3301 ri = ris.get(i); 3302 break; 3303 } 3304 } 3305 3306 if (ri != null) { 3307 String vers = ri.activityInfo.metaData != null 3308 ? ri.activityInfo.metaData.getString(Intent.METADATA_SETUP_VERSION) 3309 : null; 3310 if (vers == null && ri.activityInfo.applicationInfo.metaData != null) { 3311 vers = ri.activityInfo.applicationInfo.metaData.getString( 3312 Intent.METADATA_SETUP_VERSION); 3313 } 3314 String lastVers = Settings.Secure.getString( 3315 resolver, Settings.Secure.LAST_SETUP_SHOWN); 3316 if (vers != null && !vers.equals(lastVers)) { 3317 intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 3318 intent.setComponent(new ComponentName( 3319 ri.activityInfo.packageName, ri.activityInfo.name)); 3320 mStackSupervisor.startActivityLocked(null, intent, null, ri.activityInfo, 3321 null, null, null, null, 0, 0, 0, null, 0, null, false, null, null); 3322 } 3323 } 3324 } 3325 } 3326 3327 CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) { 3328 return mCompatModePackages.compatibilityInfoForPackageLocked(ai); 3329 } 3330 3331 void enforceNotIsolatedCaller(String caller) { 3332 if (UserHandle.isIsolated(Binder.getCallingUid())) { 3333 throw new SecurityException("Isolated process not allowed to call " + caller); 3334 } 3335 } 3336 3337 @Override 3338 public int getFrontActivityScreenCompatMode() { 3339 enforceNotIsolatedCaller("getFrontActivityScreenCompatMode"); 3340 synchronized (this) { 3341 return mCompatModePackages.getFrontActivityScreenCompatModeLocked(); 3342 } 3343 } 3344 3345 @Override 3346 public void setFrontActivityScreenCompatMode(int mode) { 3347 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3348 "setFrontActivityScreenCompatMode"); 3349 synchronized (this) { 3350 mCompatModePackages.setFrontActivityScreenCompatModeLocked(mode); 3351 } 3352 } 3353 3354 @Override 3355 public int getPackageScreenCompatMode(String packageName) { 3356 enforceNotIsolatedCaller("getPackageScreenCompatMode"); 3357 synchronized (this) { 3358 return mCompatModePackages.getPackageScreenCompatModeLocked(packageName); 3359 } 3360 } 3361 3362 @Override 3363 public void setPackageScreenCompatMode(String packageName, int mode) { 3364 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3365 "setPackageScreenCompatMode"); 3366 synchronized (this) { 3367 mCompatModePackages.setPackageScreenCompatModeLocked(packageName, mode); 3368 } 3369 } 3370 3371 @Override 3372 public boolean getPackageAskScreenCompat(String packageName) { 3373 enforceNotIsolatedCaller("getPackageAskScreenCompat"); 3374 synchronized (this) { 3375 return mCompatModePackages.getPackageAskCompatModeLocked(packageName); 3376 } 3377 } 3378 3379 @Override 3380 public void setPackageAskScreenCompat(String packageName, boolean ask) { 3381 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3382 "setPackageAskScreenCompat"); 3383 synchronized (this) { 3384 mCompatModePackages.setPackageAskCompatModeLocked(packageName, ask); 3385 } 3386 } 3387 3388 private void dispatchProcessesChanged() { 3389 int N; 3390 synchronized (this) { 3391 N = mPendingProcessChanges.size(); 3392 if (mActiveProcessChanges.length < N) { 3393 mActiveProcessChanges = new ProcessChangeItem[N]; 3394 } 3395 mPendingProcessChanges.toArray(mActiveProcessChanges); 3396 mAvailProcessChanges.addAll(mPendingProcessChanges); 3397 mPendingProcessChanges.clear(); 3398 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "*** Delivering " + N + " process changes"); 3399 } 3400 3401 int i = mProcessObservers.beginBroadcast(); 3402 while (i > 0) { 3403 i--; 3404 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3405 if (observer != null) { 3406 try { 3407 for (int j=0; j<N; j++) { 3408 ProcessChangeItem item = mActiveProcessChanges[j]; 3409 if ((item.changes&ProcessChangeItem.CHANGE_ACTIVITIES) != 0) { 3410 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "ACTIVITIES CHANGED pid=" 3411 + item.pid + " uid=" + item.uid + ": " 3412 + item.foregroundActivities); 3413 observer.onForegroundActivitiesChanged(item.pid, item.uid, 3414 item.foregroundActivities); 3415 } 3416 if ((item.changes&ProcessChangeItem.CHANGE_PROCESS_STATE) != 0) { 3417 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "PROCSTATE CHANGED pid=" 3418 + item.pid + " uid=" + item.uid + ": " + item.processState); 3419 observer.onProcessStateChanged(item.pid, item.uid, item.processState); 3420 } 3421 } 3422 } catch (RemoteException e) { 3423 } 3424 } 3425 } 3426 mProcessObservers.finishBroadcast(); 3427 } 3428 3429 private void dispatchProcessDied(int pid, int uid) { 3430 int i = mProcessObservers.beginBroadcast(); 3431 while (i > 0) { 3432 i--; 3433 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3434 if (observer != null) { 3435 try { 3436 observer.onProcessDied(pid, uid); 3437 } catch (RemoteException e) { 3438 } 3439 } 3440 } 3441 mProcessObservers.finishBroadcast(); 3442 } 3443 3444 @Override 3445 public final int startActivity(IApplicationThread caller, String callingPackage, 3446 Intent intent, String resolvedType, IBinder resultTo, 3447 String resultWho, int requestCode, int startFlags, 3448 String profileFile, ParcelFileDescriptor profileFd, Bundle options) { 3449 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo, 3450 resultWho, requestCode, 3451 startFlags, profileFile, profileFd, options, UserHandle.getCallingUserId()); 3452 } 3453 3454 @Override 3455 public final int startActivityAsUser(IApplicationThread caller, String callingPackage, 3456 Intent intent, String resolvedType, IBinder resultTo, 3457 String resultWho, int requestCode, int startFlags, 3458 String profileFile, ParcelFileDescriptor profileFd, Bundle options, int userId) { 3459 enforceNotIsolatedCaller("startActivity"); 3460 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3461 false, ALLOW_FULL_ONLY, "startActivity", null); 3462 // TODO: Switch to user app stacks here. 3463 return mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 3464 null, null, resultTo, resultWho, requestCode, startFlags, profileFile, profileFd, 3465 null, null, options, userId, null); 3466 } 3467 3468 @Override 3469 public final int startActivityAsCaller(IApplicationThread caller, String callingPackage, 3470 Intent intent, String resolvedType, IBinder resultTo, 3471 String resultWho, int requestCode, int startFlags, 3472 String profileFile, ParcelFileDescriptor profileFd, Bundle options) { 3473 3474 // This is very dangerous -- it allows you to perform a start activity (including 3475 // permission grants) as any app that may launch one of your own activities. So 3476 // we will only allow this to be done from activities that are part of the core framework, 3477 // and then only when they are running as the system. 3478 final ActivityRecord sourceRecord; 3479 final int targetUid; 3480 final String targetPackage; 3481 synchronized (this) { 3482 if (resultTo == null) { 3483 throw new SecurityException("Must be called from an activity"); 3484 } 3485 sourceRecord = mStackSupervisor.isInAnyStackLocked(resultTo); 3486 if (sourceRecord == null) { 3487 throw new SecurityException("Called with bad activity token: " + resultTo); 3488 } 3489 if (!sourceRecord.info.packageName.equals("android")) { 3490 throw new SecurityException( 3491 "Must be called from an activity that is declared in the android package"); 3492 } 3493 if (sourceRecord.app == null) { 3494 throw new SecurityException("Called without a process attached to activity"); 3495 } 3496 if (UserHandle.getAppId(sourceRecord.app.uid) != Process.SYSTEM_UID) { 3497 // This is still okay, as long as this activity is running under the 3498 // uid of the original calling activity. 3499 if (sourceRecord.app.uid != sourceRecord.launchedFromUid) { 3500 throw new SecurityException( 3501 "Calling activity in uid " + sourceRecord.app.uid 3502 + " must be system uid or original calling uid " 3503 + sourceRecord.launchedFromUid); 3504 } 3505 } 3506 targetUid = sourceRecord.launchedFromUid; 3507 targetPackage = sourceRecord.launchedFromPackage; 3508 } 3509 3510 // TODO: Switch to user app stacks here. 3511 try { 3512 int ret = mStackSupervisor.startActivityMayWait(null, targetUid, targetPackage, intent, 3513 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3514 null, null, null, null, options, UserHandle.getUserId(sourceRecord.app.uid), 3515 null); 3516 return ret; 3517 } catch (SecurityException e) { 3518 // XXX need to figure out how to propagate to original app. 3519 // A SecurityException here is generally actually a fault of the original 3520 // calling activity (such as a fairly granting permissions), so propagate it 3521 // back to them. 3522 /* 3523 StringBuilder msg = new StringBuilder(); 3524 msg.append("While launching"); 3525 msg.append(intent.toString()); 3526 msg.append(": "); 3527 msg.append(e.getMessage()); 3528 */ 3529 throw e; 3530 } 3531 } 3532 3533 @Override 3534 public final WaitResult startActivityAndWait(IApplicationThread caller, String callingPackage, 3535 Intent intent, String resolvedType, IBinder resultTo, 3536 String resultWho, int requestCode, int startFlags, String profileFile, 3537 ParcelFileDescriptor profileFd, Bundle options, int userId) { 3538 enforceNotIsolatedCaller("startActivityAndWait"); 3539 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3540 false, ALLOW_FULL_ONLY, "startActivityAndWait", null); 3541 WaitResult res = new WaitResult(); 3542 // TODO: Switch to user app stacks here. 3543 mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 3544 null, null, resultTo, resultWho, requestCode, startFlags, profileFile, profileFd, 3545 res, null, options, userId, null); 3546 return res; 3547 } 3548 3549 @Override 3550 public final int startActivityWithConfig(IApplicationThread caller, String callingPackage, 3551 Intent intent, String resolvedType, IBinder resultTo, 3552 String resultWho, int requestCode, int startFlags, Configuration config, 3553 Bundle options, int userId) { 3554 enforceNotIsolatedCaller("startActivityWithConfig"); 3555 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3556 false, ALLOW_FULL_ONLY, "startActivityWithConfig", null); 3557 // TODO: Switch to user app stacks here. 3558 int ret = mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, 3559 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3560 null, null, null, config, options, userId, null); 3561 return ret; 3562 } 3563 3564 @Override 3565 public int startActivityIntentSender(IApplicationThread caller, 3566 IntentSender intent, Intent fillInIntent, String resolvedType, 3567 IBinder resultTo, String resultWho, int requestCode, 3568 int flagsMask, int flagsValues, Bundle options) { 3569 enforceNotIsolatedCaller("startActivityIntentSender"); 3570 // Refuse possible leaked file descriptors 3571 if (fillInIntent != null && fillInIntent.hasFileDescriptors()) { 3572 throw new IllegalArgumentException("File descriptors passed in Intent"); 3573 } 3574 3575 IIntentSender sender = intent.getTarget(); 3576 if (!(sender instanceof PendingIntentRecord)) { 3577 throw new IllegalArgumentException("Bad PendingIntent object"); 3578 } 3579 3580 PendingIntentRecord pir = (PendingIntentRecord)sender; 3581 3582 synchronized (this) { 3583 // If this is coming from the currently resumed activity, it is 3584 // effectively saying that app switches are allowed at this point. 3585 final ActivityStack stack = getFocusedStack(); 3586 if (stack.mResumedActivity != null && 3587 stack.mResumedActivity.info.applicationInfo.uid == Binder.getCallingUid()) { 3588 mAppSwitchesAllowedTime = 0; 3589 } 3590 } 3591 int ret = pir.sendInner(0, fillInIntent, resolvedType, null, null, 3592 resultTo, resultWho, requestCode, flagsMask, flagsValues, options, null); 3593 return ret; 3594 } 3595 3596 @Override 3597 public int startVoiceActivity(String callingPackage, int callingPid, int callingUid, 3598 Intent intent, String resolvedType, IVoiceInteractionSession session, 3599 IVoiceInteractor interactor, int startFlags, String profileFile, 3600 ParcelFileDescriptor profileFd, Bundle options, int userId) { 3601 if (checkCallingPermission(Manifest.permission.BIND_VOICE_INTERACTION) 3602 != PackageManager.PERMISSION_GRANTED) { 3603 String msg = "Permission Denial: startVoiceActivity() from pid=" 3604 + Binder.getCallingPid() 3605 + ", uid=" + Binder.getCallingUid() 3606 + " requires " + android.Manifest.permission.BIND_VOICE_INTERACTION; 3607 Slog.w(TAG, msg); 3608 throw new SecurityException(msg); 3609 } 3610 if (session == null || interactor == null) { 3611 throw new NullPointerException("null session or interactor"); 3612 } 3613 userId = handleIncomingUser(callingPid, callingUid, userId, 3614 false, ALLOW_FULL_ONLY, "startVoiceActivity", null); 3615 // TODO: Switch to user app stacks here. 3616 return mStackSupervisor.startActivityMayWait(null, callingUid, callingPackage, intent, 3617 resolvedType, session, interactor, null, null, 0, startFlags, 3618 profileFile, profileFd, null, null, options, userId, null); 3619 } 3620 3621 @Override 3622 public boolean startNextMatchingActivity(IBinder callingActivity, 3623 Intent intent, Bundle options) { 3624 // Refuse possible leaked file descriptors 3625 if (intent != null && intent.hasFileDescriptors() == true) { 3626 throw new IllegalArgumentException("File descriptors passed in Intent"); 3627 } 3628 3629 synchronized (this) { 3630 final ActivityRecord r = ActivityRecord.isInStackLocked(callingActivity); 3631 if (r == null) { 3632 ActivityOptions.abort(options); 3633 return false; 3634 } 3635 if (r.app == null || r.app.thread == null) { 3636 // The caller is not running... d'oh! 3637 ActivityOptions.abort(options); 3638 return false; 3639 } 3640 intent = new Intent(intent); 3641 // The caller is not allowed to change the data. 3642 intent.setDataAndType(r.intent.getData(), r.intent.getType()); 3643 // And we are resetting to find the next component... 3644 intent.setComponent(null); 3645 3646 final boolean debug = ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0); 3647 3648 ActivityInfo aInfo = null; 3649 try { 3650 List<ResolveInfo> resolves = 3651 AppGlobals.getPackageManager().queryIntentActivities( 3652 intent, r.resolvedType, 3653 PackageManager.MATCH_DEFAULT_ONLY | STOCK_PM_FLAGS, 3654 UserHandle.getCallingUserId()); 3655 3656 // Look for the original activity in the list... 3657 final int N = resolves != null ? resolves.size() : 0; 3658 for (int i=0; i<N; i++) { 3659 ResolveInfo rInfo = resolves.get(i); 3660 if (rInfo.activityInfo.packageName.equals(r.packageName) 3661 && rInfo.activityInfo.name.equals(r.info.name)) { 3662 // We found the current one... the next matching is 3663 // after it. 3664 i++; 3665 if (i<N) { 3666 aInfo = resolves.get(i).activityInfo; 3667 } 3668 if (debug) { 3669 Slog.v(TAG, "Next matching activity: found current " + r.packageName 3670 + "/" + r.info.name); 3671 Slog.v(TAG, "Next matching activity: next is " + aInfo.packageName 3672 + "/" + aInfo.name); 3673 } 3674 break; 3675 } 3676 } 3677 } catch (RemoteException e) { 3678 } 3679 3680 if (aInfo == null) { 3681 // Nobody who is next! 3682 ActivityOptions.abort(options); 3683 if (debug) Slog.d(TAG, "Next matching activity: nothing found"); 3684 return false; 3685 } 3686 3687 intent.setComponent(new ComponentName( 3688 aInfo.applicationInfo.packageName, aInfo.name)); 3689 intent.setFlags(intent.getFlags()&~( 3690 Intent.FLAG_ACTIVITY_FORWARD_RESULT| 3691 Intent.FLAG_ACTIVITY_CLEAR_TOP| 3692 Intent.FLAG_ACTIVITY_MULTIPLE_TASK| 3693 Intent.FLAG_ACTIVITY_NEW_TASK)); 3694 3695 // Okay now we need to start the new activity, replacing the 3696 // currently running activity. This is a little tricky because 3697 // we want to start the new one as if the current one is finished, 3698 // but not finish the current one first so that there is no flicker. 3699 // And thus... 3700 final boolean wasFinishing = r.finishing; 3701 r.finishing = true; 3702 3703 // Propagate reply information over to the new activity. 3704 final ActivityRecord resultTo = r.resultTo; 3705 final String resultWho = r.resultWho; 3706 final int requestCode = r.requestCode; 3707 r.resultTo = null; 3708 if (resultTo != null) { 3709 resultTo.removeResultsLocked(r, resultWho, requestCode); 3710 } 3711 3712 final long origId = Binder.clearCallingIdentity(); 3713 int res = mStackSupervisor.startActivityLocked(r.app.thread, intent, 3714 r.resolvedType, aInfo, null, null, resultTo != null ? resultTo.appToken : null, 3715 resultWho, requestCode, -1, r.launchedFromUid, r.launchedFromPackage, 0, 3716 options, false, null, null); 3717 Binder.restoreCallingIdentity(origId); 3718 3719 r.finishing = wasFinishing; 3720 if (res != ActivityManager.START_SUCCESS) { 3721 return false; 3722 } 3723 return true; 3724 } 3725 } 3726 3727 @Override 3728 public final int startActivityFromRecents(int taskId, Bundle options) { 3729 if (checkCallingPermission(START_TASKS_FROM_RECENTS) != PackageManager.PERMISSION_GRANTED) { 3730 String msg = "Permission Denial: startActivityFromRecents called without " + 3731 START_TASKS_FROM_RECENTS; 3732 Slog.w(TAG, msg); 3733 throw new SecurityException(msg); 3734 } 3735 final int callingUid; 3736 final String callingPackage; 3737 final Intent intent; 3738 final int userId; 3739 synchronized (this) { 3740 final TaskRecord task = recentTaskForIdLocked(taskId); 3741 if (task == null) { 3742 throw new ActivityNotFoundException("Task " + taskId + " not found."); 3743 } 3744 callingUid = task.mCallingUid; 3745 callingPackage = task.mCallingPackage; 3746 intent = task.intent; 3747 userId = task.userId; 3748 } 3749 return startActivityInPackage(callingUid, callingPackage, intent, null, null, null, 0, 0, 3750 options, userId, null); 3751 } 3752 3753 final int startActivityInPackage(int uid, String callingPackage, 3754 Intent intent, String resolvedType, IBinder resultTo, 3755 String resultWho, int requestCode, int startFlags, Bundle options, int userId, 3756 IActivityContainer container) { 3757 3758 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3759 false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 3760 3761 // TODO: Switch to user app stacks here. 3762 int ret = mStackSupervisor.startActivityMayWait(null, uid, callingPackage, intent, resolvedType, 3763 null, null, resultTo, resultWho, requestCode, startFlags, 3764 null, null, null, null, options, userId, container); 3765 return ret; 3766 } 3767 3768 @Override 3769 public final int startActivities(IApplicationThread caller, String callingPackage, 3770 Intent[] intents, String[] resolvedTypes, IBinder resultTo, Bundle options, 3771 int userId) { 3772 enforceNotIsolatedCaller("startActivities"); 3773 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3774 false, ALLOW_FULL_ONLY, "startActivity", null); 3775 // TODO: Switch to user app stacks here. 3776 int ret = mStackSupervisor.startActivities(caller, -1, callingPackage, intents, 3777 resolvedTypes, resultTo, options, userId); 3778 return ret; 3779 } 3780 3781 final int startActivitiesInPackage(int uid, String callingPackage, 3782 Intent[] intents, String[] resolvedTypes, IBinder resultTo, 3783 Bundle options, int userId) { 3784 3785 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3786 false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 3787 // TODO: Switch to user app stacks here. 3788 int ret = mStackSupervisor.startActivities(null, uid, callingPackage, intents, resolvedTypes, 3789 resultTo, options, userId); 3790 return ret; 3791 } 3792 3793 //explicitly remove thd old information in mRecentTasks when removing existing user. 3794 private void removeRecentTasksForUserLocked(int userId) { 3795 if(userId <= 0) { 3796 Slog.i(TAG, "Can't remove recent task on user " + userId); 3797 return; 3798 } 3799 3800 for (int i = mRecentTasks.size() - 1; i >= 0; --i) { 3801 TaskRecord tr = mRecentTasks.get(i); 3802 if (tr.userId == userId) { 3803 if(DEBUG_TASKS) Slog.i(TAG, "remove RecentTask " + tr 3804 + " when finishing user" + userId); 3805 tr.disposeThumbnail(); 3806 mRecentTasks.remove(i); 3807 } 3808 } 3809 3810 // Remove tasks from persistent storage. 3811 mTaskPersister.wakeup(null, true); 3812 } 3813 3814 final void addRecentTaskLocked(TaskRecord task) { 3815 final int N = mRecentTasks.size(); 3816 // Quick case: check if the top-most recent task is the same. 3817 if (N > 0 && mRecentTasks.get(0) == task) { 3818 return; 3819 } 3820 // Another quick case: never add voice sessions. 3821 if (task.voiceSession != null) { 3822 return; 3823 } 3824 3825 trimRecentsForTask(task, true); 3826 3827 if (N >= MAX_RECENT_TASKS) { 3828 final TaskRecord tr = mRecentTasks.remove(N - 1); 3829 tr.disposeThumbnail(); 3830 tr.closeRecentsChain(); 3831 } 3832 mRecentTasks.add(0, task); 3833 } 3834 3835 /** 3836 * If needed, remove oldest existing entries in recents that are for the same kind 3837 * of task as the given one. 3838 */ 3839 int trimRecentsForTask(TaskRecord task, boolean doTrim) { 3840 int N = mRecentTasks.size(); 3841 final Intent intent = task.intent; 3842 final boolean document = intent != null && intent.isDocument(); 3843 3844 int maxRecents = task.maxRecents - 1; 3845 for (int i=0; i<N; i++) { 3846 final TaskRecord tr = mRecentTasks.get(i); 3847 if (task != tr) { 3848 if (task.userId != tr.userId) { 3849 continue; 3850 } 3851 if (i > MAX_RECENT_BITMAPS) { 3852 tr.freeLastThumbnail(); 3853 } 3854 final Intent trIntent = tr.intent; 3855 if ((task.affinity == null || !task.affinity.equals(tr.affinity)) && 3856 (intent == null || !intent.filterEquals(trIntent))) { 3857 continue; 3858 } 3859 final boolean trIsDocument = trIntent != null && trIntent.isDocument(); 3860 if (document && trIsDocument) { 3861 // These are the same document activity (not necessarily the same doc). 3862 if (maxRecents > 0) { 3863 --maxRecents; 3864 continue; 3865 } 3866 // Hit the maximum number of documents for this task. Fall through 3867 // and remove this document from recents. 3868 } else if (document || trIsDocument) { 3869 // Only one of these is a document. Not the droid we're looking for. 3870 continue; 3871 } 3872 } 3873 3874 if (!doTrim) { 3875 // If the caller is not actually asking for a trim, just tell them we reached 3876 // a point where the trim would happen. 3877 return i; 3878 } 3879 3880 // Either task and tr are the same or, their affinities match or their intents match 3881 // and neither of them is a document, or they are documents using the same activity 3882 // and their maxRecents has been reached. 3883 tr.disposeThumbnail(); 3884 mRecentTasks.remove(i); 3885 if (task != tr) { 3886 tr.closeRecentsChain(); 3887 } 3888 i--; 3889 N--; 3890 if (task.intent == null) { 3891 // If the new recent task we are adding is not fully 3892 // specified, then replace it with the existing recent task. 3893 task = tr; 3894 } 3895 notifyTaskPersisterLocked(tr, false); 3896 } 3897 3898 return -1; 3899 } 3900 3901 @Override 3902 public void reportActivityFullyDrawn(IBinder token) { 3903 synchronized (this) { 3904 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3905 if (r == null) { 3906 return; 3907 } 3908 r.reportFullyDrawnLocked(); 3909 } 3910 } 3911 3912 @Override 3913 public void setRequestedOrientation(IBinder token, int requestedOrientation) { 3914 synchronized (this) { 3915 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3916 if (r == null) { 3917 return; 3918 } 3919 final long origId = Binder.clearCallingIdentity(); 3920 mWindowManager.setAppOrientation(r.appToken, requestedOrientation); 3921 Configuration config = mWindowManager.updateOrientationFromAppTokens( 3922 mConfiguration, r.mayFreezeScreenLocked(r.app) ? r.appToken : null); 3923 if (config != null) { 3924 r.frozenBeforeDestroy = true; 3925 if (!updateConfigurationLocked(config, r, false, false)) { 3926 mStackSupervisor.resumeTopActivitiesLocked(); 3927 } 3928 } 3929 Binder.restoreCallingIdentity(origId); 3930 } 3931 } 3932 3933 @Override 3934 public int getRequestedOrientation(IBinder token) { 3935 synchronized (this) { 3936 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3937 if (r == null) { 3938 return ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED; 3939 } 3940 return mWindowManager.getAppOrientation(r.appToken); 3941 } 3942 } 3943 3944 /** 3945 * This is the internal entry point for handling Activity.finish(). 3946 * 3947 * @param token The Binder token referencing the Activity we want to finish. 3948 * @param resultCode Result code, if any, from this Activity. 3949 * @param resultData Result data (Intent), if any, from this Activity. 3950 * @param finishTask Whether to finish the task associated with this Activity. Only applies to 3951 * the root Activity in the task. 3952 * 3953 * @return Returns true if the activity successfully finished, or false if it is still running. 3954 */ 3955 @Override 3956 public final boolean finishActivity(IBinder token, int resultCode, Intent resultData, 3957 boolean finishTask) { 3958 // Refuse possible leaked file descriptors 3959 if (resultData != null && resultData.hasFileDescriptors() == true) { 3960 throw new IllegalArgumentException("File descriptors passed in Intent"); 3961 } 3962 3963 synchronized(this) { 3964 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3965 if (r == null) { 3966 return true; 3967 } 3968 // Keep track of the root activity of the task before we finish it 3969 TaskRecord tr = r.task; 3970 ActivityRecord rootR = tr.getRootActivity(); 3971 // Do not allow task to finish in Lock Task mode. 3972 if (tr == mStackSupervisor.mLockTaskModeTask) { 3973 if (rootR == r) { 3974 mStackSupervisor.showLockTaskToast(); 3975 return false; 3976 } 3977 } 3978 if (mController != null) { 3979 // Find the first activity that is not finishing. 3980 ActivityRecord next = r.task.stack.topRunningActivityLocked(token, 0); 3981 if (next != null) { 3982 // ask watcher if this is allowed 3983 boolean resumeOK = true; 3984 try { 3985 resumeOK = mController.activityResuming(next.packageName); 3986 } catch (RemoteException e) { 3987 mController = null; 3988 Watchdog.getInstance().setActivityController(null); 3989 } 3990 3991 if (!resumeOK) { 3992 return false; 3993 } 3994 } 3995 } 3996 final long origId = Binder.clearCallingIdentity(); 3997 try { 3998 boolean res; 3999 if (finishTask && r == rootR) { 4000 // If requested, remove the task that is associated to this activity only if it 4001 // was the root activity in the task. The result code and data is ignored because 4002 // we don't support returning them across task boundaries. 4003 res = removeTaskByIdLocked(tr.taskId, 0); 4004 } else { 4005 res = tr.stack.requestFinishActivityLocked(token, resultCode, 4006 resultData, "app-request", true); 4007 } 4008 return res; 4009 } finally { 4010 Binder.restoreCallingIdentity(origId); 4011 } 4012 } 4013 } 4014 4015 @Override 4016 public final void finishHeavyWeightApp() { 4017 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4018 != PackageManager.PERMISSION_GRANTED) { 4019 String msg = "Permission Denial: finishHeavyWeightApp() from pid=" 4020 + Binder.getCallingPid() 4021 + ", uid=" + Binder.getCallingUid() 4022 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4023 Slog.w(TAG, msg); 4024 throw new SecurityException(msg); 4025 } 4026 4027 synchronized(this) { 4028 if (mHeavyWeightProcess == null) { 4029 return; 4030 } 4031 4032 ArrayList<ActivityRecord> activities = new ArrayList<ActivityRecord>( 4033 mHeavyWeightProcess.activities); 4034 for (int i=0; i<activities.size(); i++) { 4035 ActivityRecord r = activities.get(i); 4036 if (!r.finishing) { 4037 r.task.stack.finishActivityLocked(r, Activity.RESULT_CANCELED, 4038 null, "finish-heavy", true); 4039 } 4040 } 4041 4042 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 4043 mHeavyWeightProcess.userId, 0)); 4044 mHeavyWeightProcess = null; 4045 } 4046 } 4047 4048 @Override 4049 public void crashApplication(int uid, int initialPid, String packageName, 4050 String message) { 4051 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4052 != PackageManager.PERMISSION_GRANTED) { 4053 String msg = "Permission Denial: crashApplication() from pid=" 4054 + Binder.getCallingPid() 4055 + ", uid=" + Binder.getCallingUid() 4056 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4057 Slog.w(TAG, msg); 4058 throw new SecurityException(msg); 4059 } 4060 4061 synchronized(this) { 4062 ProcessRecord proc = null; 4063 4064 // Figure out which process to kill. We don't trust that initialPid 4065 // still has any relation to current pids, so must scan through the 4066 // list. 4067 synchronized (mPidsSelfLocked) { 4068 for (int i=0; i<mPidsSelfLocked.size(); i++) { 4069 ProcessRecord p = mPidsSelfLocked.valueAt(i); 4070 if (p.uid != uid) { 4071 continue; 4072 } 4073 if (p.pid == initialPid) { 4074 proc = p; 4075 break; 4076 } 4077 if (p.pkgList.containsKey(packageName)) { 4078 proc = p; 4079 } 4080 } 4081 } 4082 4083 if (proc == null) { 4084 Slog.w(TAG, "crashApplication: nothing for uid=" + uid 4085 + " initialPid=" + initialPid 4086 + " packageName=" + packageName); 4087 return; 4088 } 4089 4090 if (proc.thread != null) { 4091 if (proc.pid == Process.myPid()) { 4092 Log.w(TAG, "crashApplication: trying to crash self!"); 4093 return; 4094 } 4095 long ident = Binder.clearCallingIdentity(); 4096 try { 4097 proc.thread.scheduleCrash(message); 4098 } catch (RemoteException e) { 4099 } 4100 Binder.restoreCallingIdentity(ident); 4101 } 4102 } 4103 } 4104 4105 @Override 4106 public final void finishSubActivity(IBinder token, String resultWho, 4107 int requestCode) { 4108 synchronized(this) { 4109 final long origId = Binder.clearCallingIdentity(); 4110 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4111 if (r != null) { 4112 r.task.stack.finishSubActivityLocked(r, resultWho, requestCode); 4113 } 4114 Binder.restoreCallingIdentity(origId); 4115 } 4116 } 4117 4118 @Override 4119 public boolean finishActivityAffinity(IBinder token) { 4120 synchronized(this) { 4121 final long origId = Binder.clearCallingIdentity(); 4122 try { 4123 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4124 4125 ActivityRecord rootR = r.task.getRootActivity(); 4126 // Do not allow task to finish in Lock Task mode. 4127 if (r.task == mStackSupervisor.mLockTaskModeTask) { 4128 if (rootR == r) { 4129 mStackSupervisor.showLockTaskToast(); 4130 return false; 4131 } 4132 } 4133 boolean res = false; 4134 if (r != null) { 4135 res = r.task.stack.finishActivityAffinityLocked(r); 4136 } 4137 return res; 4138 } finally { 4139 Binder.restoreCallingIdentity(origId); 4140 } 4141 } 4142 } 4143 4144 @Override 4145 public void finishVoiceTask(IVoiceInteractionSession session) { 4146 synchronized(this) { 4147 final long origId = Binder.clearCallingIdentity(); 4148 try { 4149 mStackSupervisor.finishVoiceTask(session); 4150 } finally { 4151 Binder.restoreCallingIdentity(origId); 4152 } 4153 } 4154 4155 } 4156 4157 @Override 4158 public boolean willActivityBeVisible(IBinder token) { 4159 synchronized(this) { 4160 ActivityStack stack = ActivityRecord.getStackLocked(token); 4161 if (stack != null) { 4162 return stack.willActivityBeVisibleLocked(token); 4163 } 4164 return false; 4165 } 4166 } 4167 4168 @Override 4169 public void overridePendingTransition(IBinder token, String packageName, 4170 int enterAnim, int exitAnim) { 4171 synchronized(this) { 4172 ActivityRecord self = ActivityRecord.isInStackLocked(token); 4173 if (self == null) { 4174 return; 4175 } 4176 4177 final long origId = Binder.clearCallingIdentity(); 4178 4179 if (self.state == ActivityState.RESUMED 4180 || self.state == ActivityState.PAUSING) { 4181 mWindowManager.overridePendingAppTransition(packageName, 4182 enterAnim, exitAnim, null); 4183 } 4184 4185 Binder.restoreCallingIdentity(origId); 4186 } 4187 } 4188 4189 /** 4190 * Main function for removing an existing process from the activity manager 4191 * as a result of that process going away. Clears out all connections 4192 * to the process. 4193 */ 4194 private final void handleAppDiedLocked(ProcessRecord app, 4195 boolean restarting, boolean allowRestart) { 4196 int pid = app.pid; 4197 cleanUpApplicationRecordLocked(app, restarting, allowRestart, -1); 4198 if (!restarting) { 4199 removeLruProcessLocked(app); 4200 if (pid > 0) { 4201 ProcessList.remove(pid); 4202 } 4203 } 4204 4205 if (mProfileProc == app) { 4206 clearProfilerLocked(); 4207 } 4208 4209 // Remove this application's activities from active lists. 4210 boolean hasVisibleActivities = mStackSupervisor.handleAppDiedLocked(app); 4211 4212 app.activities.clear(); 4213 4214 if (app.instrumentationClass != null) { 4215 Slog.w(TAG, "Crash of app " + app.processName 4216 + " running instrumentation " + app.instrumentationClass); 4217 Bundle info = new Bundle(); 4218 info.putString("shortMsg", "Process crashed."); 4219 finishInstrumentationLocked(app, Activity.RESULT_CANCELED, info); 4220 } 4221 4222 if (!restarting) { 4223 if (!mStackSupervisor.resumeTopActivitiesLocked()) { 4224 // If there was nothing to resume, and we are not already 4225 // restarting this process, but there is a visible activity that 4226 // is hosted by the process... then make sure all visible 4227 // activities are running, taking care of restarting this 4228 // process. 4229 if (hasVisibleActivities) { 4230 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 4231 } 4232 } 4233 } 4234 } 4235 4236 private final int getLRURecordIndexForAppLocked(IApplicationThread thread) { 4237 IBinder threadBinder = thread.asBinder(); 4238 // Find the application record. 4239 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4240 ProcessRecord rec = mLruProcesses.get(i); 4241 if (rec.thread != null && rec.thread.asBinder() == threadBinder) { 4242 return i; 4243 } 4244 } 4245 return -1; 4246 } 4247 4248 final ProcessRecord getRecordForAppLocked( 4249 IApplicationThread thread) { 4250 if (thread == null) { 4251 return null; 4252 } 4253 4254 int appIndex = getLRURecordIndexForAppLocked(thread); 4255 return appIndex >= 0 ? mLruProcesses.get(appIndex) : null; 4256 } 4257 4258 final void doLowMemReportIfNeededLocked(ProcessRecord dyingProc) { 4259 // If there are no longer any background processes running, 4260 // and the app that died was not running instrumentation, 4261 // then tell everyone we are now low on memory. 4262 boolean haveBg = false; 4263 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4264 ProcessRecord rec = mLruProcesses.get(i); 4265 if (rec.thread != null 4266 && rec.setProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 4267 haveBg = true; 4268 break; 4269 } 4270 } 4271 4272 if (!haveBg) { 4273 boolean doReport = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 4274 if (doReport) { 4275 long now = SystemClock.uptimeMillis(); 4276 if (now < (mLastMemUsageReportTime+5*60*1000)) { 4277 doReport = false; 4278 } else { 4279 mLastMemUsageReportTime = now; 4280 } 4281 } 4282 final ArrayList<ProcessMemInfo> memInfos 4283 = doReport ? new ArrayList<ProcessMemInfo>(mLruProcesses.size()) : null; 4284 EventLog.writeEvent(EventLogTags.AM_LOW_MEMORY, mLruProcesses.size()); 4285 long now = SystemClock.uptimeMillis(); 4286 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4287 ProcessRecord rec = mLruProcesses.get(i); 4288 if (rec == dyingProc || rec.thread == null) { 4289 continue; 4290 } 4291 if (doReport) { 4292 memInfos.add(new ProcessMemInfo(rec.processName, rec.pid, rec.setAdj, 4293 rec.setProcState, rec.adjType, rec.makeAdjReason())); 4294 } 4295 if ((rec.lastLowMemory+GC_MIN_INTERVAL) <= now) { 4296 // The low memory report is overriding any current 4297 // state for a GC request. Make sure to do 4298 // heavy/important/visible/foreground processes first. 4299 if (rec.setAdj <= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 4300 rec.lastRequestedGc = 0; 4301 } else { 4302 rec.lastRequestedGc = rec.lastLowMemory; 4303 } 4304 rec.reportLowMemory = true; 4305 rec.lastLowMemory = now; 4306 mProcessesToGc.remove(rec); 4307 addProcessToGcListLocked(rec); 4308 } 4309 } 4310 if (doReport) { 4311 Message msg = mHandler.obtainMessage(REPORT_MEM_USAGE_MSG, memInfos); 4312 mHandler.sendMessage(msg); 4313 } 4314 scheduleAppGcsLocked(); 4315 } 4316 } 4317 4318 final void appDiedLocked(ProcessRecord app) { 4319 appDiedLocked(app, app.pid, app.thread); 4320 } 4321 4322 final void appDiedLocked(ProcessRecord app, int pid, 4323 IApplicationThread thread) { 4324 4325 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 4326 synchronized (stats) { 4327 stats.noteProcessDiedLocked(app.info.uid, pid); 4328 } 4329 4330 Process.killProcessGroup(app.info.uid, pid); 4331 4332 // Clean up already done if the process has been re-started. 4333 if (app.pid == pid && app.thread != null && 4334 app.thread.asBinder() == thread.asBinder()) { 4335 boolean doLowMem = app.instrumentationClass == null; 4336 boolean doOomAdj = doLowMem; 4337 if (!app.killedByAm) { 4338 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4339 + ") has died."); 4340 mAllowLowerMemLevel = true; 4341 } else { 4342 // Note that we always want to do oom adj to update our state with the 4343 // new number of procs. 4344 mAllowLowerMemLevel = false; 4345 doLowMem = false; 4346 } 4347 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4348 if (DEBUG_CLEANUP) Slog.v( 4349 TAG, "Dying app: " + app + ", pid: " + pid 4350 + ", thread: " + thread.asBinder()); 4351 handleAppDiedLocked(app, false, true); 4352 4353 if (doOomAdj) { 4354 updateOomAdjLocked(); 4355 } 4356 if (doLowMem) { 4357 doLowMemReportIfNeededLocked(app); 4358 } 4359 } else if (app.pid != pid) { 4360 // A new process has already been started. 4361 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4362 + ") has died and restarted (pid " + app.pid + ")."); 4363 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4364 } else if (DEBUG_PROCESSES) { 4365 Slog.d(TAG, "Received spurious death notification for thread " 4366 + thread.asBinder()); 4367 } 4368 } 4369 4370 /** 4371 * If a stack trace dump file is configured, dump process stack traces. 4372 * @param clearTraces causes the dump file to be erased prior to the new 4373 * traces being written, if true; when false, the new traces will be 4374 * appended to any existing file content. 4375 * @param firstPids of dalvik VM processes to dump stack traces for first 4376 * @param lastPids of dalvik VM processes to dump stack traces for last 4377 * @param nativeProcs optional list of native process names to dump stack crawls 4378 * @return file containing stack traces, or null if no dump file is configured 4379 */ 4380 public static File dumpStackTraces(boolean clearTraces, ArrayList<Integer> firstPids, 4381 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4382 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4383 if (tracesPath == null || tracesPath.length() == 0) { 4384 return null; 4385 } 4386 4387 File tracesFile = new File(tracesPath); 4388 try { 4389 File tracesDir = tracesFile.getParentFile(); 4390 if (!tracesDir.exists()) { 4391 tracesFile.mkdirs(); 4392 if (!SELinux.restorecon(tracesDir)) { 4393 return null; 4394 } 4395 } 4396 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4397 4398 if (clearTraces && tracesFile.exists()) tracesFile.delete(); 4399 tracesFile.createNewFile(); 4400 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4401 } catch (IOException e) { 4402 Slog.w(TAG, "Unable to prepare ANR traces file: " + tracesPath, e); 4403 return null; 4404 } 4405 4406 dumpStackTraces(tracesPath, firstPids, processCpuTracker, lastPids, nativeProcs); 4407 return tracesFile; 4408 } 4409 4410 private static void dumpStackTraces(String tracesPath, ArrayList<Integer> firstPids, 4411 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4412 // Use a FileObserver to detect when traces finish writing. 4413 // The order of traces is considered important to maintain for legibility. 4414 FileObserver observer = new FileObserver(tracesPath, FileObserver.CLOSE_WRITE) { 4415 @Override 4416 public synchronized void onEvent(int event, String path) { notify(); } 4417 }; 4418 4419 try { 4420 observer.startWatching(); 4421 4422 // First collect all of the stacks of the most important pids. 4423 if (firstPids != null) { 4424 try { 4425 int num = firstPids.size(); 4426 for (int i = 0; i < num; i++) { 4427 synchronized (observer) { 4428 Process.sendSignal(firstPids.get(i), Process.SIGNAL_QUIT); 4429 observer.wait(200); // Wait for write-close, give up after 200msec 4430 } 4431 } 4432 } catch (InterruptedException e) { 4433 Log.wtf(TAG, e); 4434 } 4435 } 4436 4437 // Next collect the stacks of the native pids 4438 if (nativeProcs != null) { 4439 int[] pids = Process.getPidsForCommands(nativeProcs); 4440 if (pids != null) { 4441 for (int pid : pids) { 4442 Debug.dumpNativeBacktraceToFile(pid, tracesPath); 4443 } 4444 } 4445 } 4446 4447 // Lastly, measure CPU usage. 4448 if (processCpuTracker != null) { 4449 processCpuTracker.init(); 4450 System.gc(); 4451 processCpuTracker.update(); 4452 try { 4453 synchronized (processCpuTracker) { 4454 processCpuTracker.wait(500); // measure over 1/2 second. 4455 } 4456 } catch (InterruptedException e) { 4457 } 4458 processCpuTracker.update(); 4459 4460 // We'll take the stack crawls of just the top apps using CPU. 4461 final int N = processCpuTracker.countWorkingStats(); 4462 int numProcs = 0; 4463 for (int i=0; i<N && numProcs<5; i++) { 4464 ProcessCpuTracker.Stats stats = processCpuTracker.getWorkingStats(i); 4465 if (lastPids.indexOfKey(stats.pid) >= 0) { 4466 numProcs++; 4467 try { 4468 synchronized (observer) { 4469 Process.sendSignal(stats.pid, Process.SIGNAL_QUIT); 4470 observer.wait(200); // Wait for write-close, give up after 200msec 4471 } 4472 } catch (InterruptedException e) { 4473 Log.wtf(TAG, e); 4474 } 4475 4476 } 4477 } 4478 } 4479 } finally { 4480 observer.stopWatching(); 4481 } 4482 } 4483 4484 final void logAppTooSlow(ProcessRecord app, long startTime, String msg) { 4485 if (true || IS_USER_BUILD) { 4486 return; 4487 } 4488 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4489 if (tracesPath == null || tracesPath.length() == 0) { 4490 return; 4491 } 4492 4493 StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads(); 4494 StrictMode.allowThreadDiskWrites(); 4495 try { 4496 final File tracesFile = new File(tracesPath); 4497 final File tracesDir = tracesFile.getParentFile(); 4498 final File tracesTmp = new File(tracesDir, "__tmp__"); 4499 try { 4500 if (!tracesDir.exists()) { 4501 tracesFile.mkdirs(); 4502 if (!SELinux.restorecon(tracesDir.getPath())) { 4503 return; 4504 } 4505 } 4506 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4507 4508 if (tracesFile.exists()) { 4509 tracesTmp.delete(); 4510 tracesFile.renameTo(tracesTmp); 4511 } 4512 StringBuilder sb = new StringBuilder(); 4513 Time tobj = new Time(); 4514 tobj.set(System.currentTimeMillis()); 4515 sb.append(tobj.format("%Y-%m-%d %H:%M:%S")); 4516 sb.append(": "); 4517 TimeUtils.formatDuration(SystemClock.uptimeMillis()-startTime, sb); 4518 sb.append(" since "); 4519 sb.append(msg); 4520 FileOutputStream fos = new FileOutputStream(tracesFile); 4521 fos.write(sb.toString().getBytes()); 4522 if (app == null) { 4523 fos.write("\n*** No application process!".getBytes()); 4524 } 4525 fos.close(); 4526 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4527 } catch (IOException e) { 4528 Slog.w(TAG, "Unable to prepare slow app traces file: " + tracesPath, e); 4529 return; 4530 } 4531 4532 if (app != null) { 4533 ArrayList<Integer> firstPids = new ArrayList<Integer>(); 4534 firstPids.add(app.pid); 4535 dumpStackTraces(tracesPath, firstPids, null, null, null); 4536 } 4537 4538 File lastTracesFile = null; 4539 File curTracesFile = null; 4540 for (int i=9; i>=0; i--) { 4541 String name = String.format(Locale.US, "slow%02d.txt", i); 4542 curTracesFile = new File(tracesDir, name); 4543 if (curTracesFile.exists()) { 4544 if (lastTracesFile != null) { 4545 curTracesFile.renameTo(lastTracesFile); 4546 } else { 4547 curTracesFile.delete(); 4548 } 4549 } 4550 lastTracesFile = curTracesFile; 4551 } 4552 tracesFile.renameTo(curTracesFile); 4553 if (tracesTmp.exists()) { 4554 tracesTmp.renameTo(tracesFile); 4555 } 4556 } finally { 4557 StrictMode.setThreadPolicy(oldPolicy); 4558 } 4559 } 4560 4561 final void appNotResponding(ProcessRecord app, ActivityRecord activity, 4562 ActivityRecord parent, boolean aboveSystem, final String annotation) { 4563 ArrayList<Integer> firstPids = new ArrayList<Integer>(5); 4564 SparseArray<Boolean> lastPids = new SparseArray<Boolean>(20); 4565 4566 if (mController != null) { 4567 try { 4568 // 0 == continue, -1 = kill process immediately 4569 int res = mController.appEarlyNotResponding(app.processName, app.pid, annotation); 4570 if (res < 0 && app.pid != MY_PID) { 4571 Process.killProcess(app.pid); 4572 Process.killProcessGroup(app.info.uid, app.pid); 4573 } 4574 } catch (RemoteException e) { 4575 mController = null; 4576 Watchdog.getInstance().setActivityController(null); 4577 } 4578 } 4579 4580 long anrTime = SystemClock.uptimeMillis(); 4581 if (MONITOR_CPU_USAGE) { 4582 updateCpuStatsNow(); 4583 } 4584 4585 synchronized (this) { 4586 // PowerManager.reboot() can block for a long time, so ignore ANRs while shutting down. 4587 if (mShuttingDown) { 4588 Slog.i(TAG, "During shutdown skipping ANR: " + app + " " + annotation); 4589 return; 4590 } else if (app.notResponding) { 4591 Slog.i(TAG, "Skipping duplicate ANR: " + app + " " + annotation); 4592 return; 4593 } else if (app.crashing) { 4594 Slog.i(TAG, "Crashing app skipping ANR: " + app + " " + annotation); 4595 return; 4596 } 4597 4598 // In case we come through here for the same app before completing 4599 // this one, mark as anring now so we will bail out. 4600 app.notResponding = true; 4601 4602 // Log the ANR to the event log. 4603 EventLog.writeEvent(EventLogTags.AM_ANR, app.userId, app.pid, 4604 app.processName, app.info.flags, annotation); 4605 4606 // Dump thread traces as quickly as we can, starting with "interesting" processes. 4607 firstPids.add(app.pid); 4608 4609 int parentPid = app.pid; 4610 if (parent != null && parent.app != null && parent.app.pid > 0) parentPid = parent.app.pid; 4611 if (parentPid != app.pid) firstPids.add(parentPid); 4612 4613 if (MY_PID != app.pid && MY_PID != parentPid) firstPids.add(MY_PID); 4614 4615 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 4616 ProcessRecord r = mLruProcesses.get(i); 4617 if (r != null && r.thread != null) { 4618 int pid = r.pid; 4619 if (pid > 0 && pid != app.pid && pid != parentPid && pid != MY_PID) { 4620 if (r.persistent) { 4621 firstPids.add(pid); 4622 } else { 4623 lastPids.put(pid, Boolean.TRUE); 4624 } 4625 } 4626 } 4627 } 4628 } 4629 4630 // Log the ANR to the main log. 4631 StringBuilder info = new StringBuilder(); 4632 info.setLength(0); 4633 info.append("ANR in ").append(app.processName); 4634 if (activity != null && activity.shortComponentName != null) { 4635 info.append(" (").append(activity.shortComponentName).append(")"); 4636 } 4637 info.append("\n"); 4638 info.append("PID: ").append(app.pid).append("\n"); 4639 if (annotation != null) { 4640 info.append("Reason: ").append(annotation).append("\n"); 4641 } 4642 if (parent != null && parent != activity) { 4643 info.append("Parent: ").append(parent.shortComponentName).append("\n"); 4644 } 4645 4646 final ProcessCpuTracker processCpuTracker = new ProcessCpuTracker(true); 4647 4648 File tracesFile = dumpStackTraces(true, firstPids, processCpuTracker, lastPids, 4649 NATIVE_STACKS_OF_INTEREST); 4650 4651 String cpuInfo = null; 4652 if (MONITOR_CPU_USAGE) { 4653 updateCpuStatsNow(); 4654 synchronized (mProcessCpuThread) { 4655 cpuInfo = mProcessCpuTracker.printCurrentState(anrTime); 4656 } 4657 info.append(processCpuTracker.printCurrentLoad()); 4658 info.append(cpuInfo); 4659 } 4660 4661 info.append(processCpuTracker.printCurrentState(anrTime)); 4662 4663 Slog.e(TAG, info.toString()); 4664 if (tracesFile == null) { 4665 // There is no trace file, so dump (only) the alleged culprit's threads to the log 4666 Process.sendSignal(app.pid, Process.SIGNAL_QUIT); 4667 } 4668 4669 addErrorToDropBox("anr", app, app.processName, activity, parent, annotation, 4670 cpuInfo, tracesFile, null); 4671 4672 if (mController != null) { 4673 try { 4674 // 0 == show dialog, 1 = keep waiting, -1 = kill process immediately 4675 int res = mController.appNotResponding(app.processName, app.pid, info.toString()); 4676 if (res != 0) { 4677 if (res < 0 && app.pid != MY_PID) { 4678 Process.killProcess(app.pid); 4679 Process.killProcessGroup(app.info.uid, app.pid); 4680 } else { 4681 synchronized (this) { 4682 mServices.scheduleServiceTimeoutLocked(app); 4683 } 4684 } 4685 return; 4686 } 4687 } catch (RemoteException e) { 4688 mController = null; 4689 Watchdog.getInstance().setActivityController(null); 4690 } 4691 } 4692 4693 // Unless configured otherwise, swallow ANRs in background processes & kill the process. 4694 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 4695 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 4696 4697 synchronized (this) { 4698 if (!showBackground && !app.isInterestingToUserLocked() && app.pid != MY_PID) { 4699 killUnneededProcessLocked(app, "background ANR"); 4700 return; 4701 } 4702 4703 // Set the app's notResponding state, and look up the errorReportReceiver 4704 makeAppNotRespondingLocked(app, 4705 activity != null ? activity.shortComponentName : null, 4706 annotation != null ? "ANR " + annotation : "ANR", 4707 info.toString()); 4708 4709 // Bring up the infamous App Not Responding dialog 4710 Message msg = Message.obtain(); 4711 HashMap<String, Object> map = new HashMap<String, Object>(); 4712 msg.what = SHOW_NOT_RESPONDING_MSG; 4713 msg.obj = map; 4714 msg.arg1 = aboveSystem ? 1 : 0; 4715 map.put("app", app); 4716 if (activity != null) { 4717 map.put("activity", activity); 4718 } 4719 4720 mHandler.sendMessage(msg); 4721 } 4722 } 4723 4724 final void showLaunchWarningLocked(final ActivityRecord cur, final ActivityRecord next) { 4725 if (!mLaunchWarningShown) { 4726 mLaunchWarningShown = true; 4727 mHandler.post(new Runnable() { 4728 @Override 4729 public void run() { 4730 synchronized (ActivityManagerService.this) { 4731 final Dialog d = new LaunchWarningWindow(mContext, cur, next); 4732 d.show(); 4733 mHandler.postDelayed(new Runnable() { 4734 @Override 4735 public void run() { 4736 synchronized (ActivityManagerService.this) { 4737 d.dismiss(); 4738 mLaunchWarningShown = false; 4739 } 4740 } 4741 }, 4000); 4742 } 4743 } 4744 }); 4745 } 4746 } 4747 4748 @Override 4749 public boolean clearApplicationUserData(final String packageName, 4750 final IPackageDataObserver observer, int userId) { 4751 enforceNotIsolatedCaller("clearApplicationUserData"); 4752 int uid = Binder.getCallingUid(); 4753 int pid = Binder.getCallingPid(); 4754 userId = handleIncomingUser(pid, uid, 4755 userId, false, ALLOW_FULL_ONLY, "clearApplicationUserData", null); 4756 long callingId = Binder.clearCallingIdentity(); 4757 try { 4758 IPackageManager pm = AppGlobals.getPackageManager(); 4759 int pkgUid = -1; 4760 synchronized(this) { 4761 try { 4762 pkgUid = pm.getPackageUid(packageName, userId); 4763 } catch (RemoteException e) { 4764 } 4765 if (pkgUid == -1) { 4766 Slog.w(TAG, "Invalid packageName: " + packageName); 4767 if (observer != null) { 4768 try { 4769 observer.onRemoveCompleted(packageName, false); 4770 } catch (RemoteException e) { 4771 Slog.i(TAG, "Observer no longer exists."); 4772 } 4773 } 4774 return false; 4775 } 4776 if (uid == pkgUid || checkComponentPermission( 4777 android.Manifest.permission.CLEAR_APP_USER_DATA, 4778 pid, uid, -1, true) 4779 == PackageManager.PERMISSION_GRANTED) { 4780 forceStopPackageLocked(packageName, pkgUid, "clear data"); 4781 } else { 4782 throw new SecurityException("PID " + pid + " does not have permission " 4783 + android.Manifest.permission.CLEAR_APP_USER_DATA + " to clear data" 4784 + " of package " + packageName); 4785 } 4786 4787 // Remove all tasks match the cleared application package and user 4788 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 4789 final TaskRecord tr = mRecentTasks.get(i); 4790 final String taskPackageName = 4791 tr.getBaseIntent().getComponent().getPackageName(); 4792 if (tr.userId != userId) continue; 4793 if (!taskPackageName.equals(packageName)) continue; 4794 removeTaskByIdLocked(tr.taskId, 0); 4795 } 4796 } 4797 4798 try { 4799 // Clear application user data 4800 pm.clearApplicationUserData(packageName, observer, userId); 4801 4802 synchronized(this) { 4803 // Remove all permissions granted from/to this package 4804 removeUriPermissionsForPackageLocked(packageName, userId, true); 4805 } 4806 4807 Intent intent = new Intent(Intent.ACTION_PACKAGE_DATA_CLEARED, 4808 Uri.fromParts("package", packageName, null)); 4809 intent.putExtra(Intent.EXTRA_UID, pkgUid); 4810 broadcastIntentInPackage("android", Process.SYSTEM_UID, intent, 4811 null, null, 0, null, null, null, false, false, userId); 4812 } catch (RemoteException e) { 4813 } 4814 } finally { 4815 Binder.restoreCallingIdentity(callingId); 4816 } 4817 return true; 4818 } 4819 4820 @Override 4821 public void killBackgroundProcesses(final String packageName, int userId) { 4822 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 4823 != PackageManager.PERMISSION_GRANTED && 4824 checkCallingPermission(android.Manifest.permission.RESTART_PACKAGES) 4825 != PackageManager.PERMISSION_GRANTED) { 4826 String msg = "Permission Denial: killBackgroundProcesses() from pid=" 4827 + Binder.getCallingPid() 4828 + ", uid=" + Binder.getCallingUid() 4829 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 4830 Slog.w(TAG, msg); 4831 throw new SecurityException(msg); 4832 } 4833 4834 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4835 userId, true, ALLOW_FULL_ONLY, "killBackgroundProcesses", null); 4836 long callingId = Binder.clearCallingIdentity(); 4837 try { 4838 IPackageManager pm = AppGlobals.getPackageManager(); 4839 synchronized(this) { 4840 int appId = -1; 4841 try { 4842 appId = UserHandle.getAppId(pm.getPackageUid(packageName, 0)); 4843 } catch (RemoteException e) { 4844 } 4845 if (appId == -1) { 4846 Slog.w(TAG, "Invalid packageName: " + packageName); 4847 return; 4848 } 4849 killPackageProcessesLocked(packageName, appId, userId, 4850 ProcessList.SERVICE_ADJ, false, true, true, false, "kill background"); 4851 } 4852 } finally { 4853 Binder.restoreCallingIdentity(callingId); 4854 } 4855 } 4856 4857 @Override 4858 public void killAllBackgroundProcesses() { 4859 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 4860 != PackageManager.PERMISSION_GRANTED) { 4861 String msg = "Permission Denial: killAllBackgroundProcesses() from pid=" 4862 + Binder.getCallingPid() 4863 + ", uid=" + Binder.getCallingUid() 4864 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 4865 Slog.w(TAG, msg); 4866 throw new SecurityException(msg); 4867 } 4868 4869 long callingId = Binder.clearCallingIdentity(); 4870 try { 4871 synchronized(this) { 4872 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 4873 final int NP = mProcessNames.getMap().size(); 4874 for (int ip=0; ip<NP; ip++) { 4875 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 4876 final int NA = apps.size(); 4877 for (int ia=0; ia<NA; ia++) { 4878 ProcessRecord app = apps.valueAt(ia); 4879 if (app.persistent) { 4880 // we don't kill persistent processes 4881 continue; 4882 } 4883 if (app.removed) { 4884 procs.add(app); 4885 } else if (app.setAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 4886 app.removed = true; 4887 procs.add(app); 4888 } 4889 } 4890 } 4891 4892 int N = procs.size(); 4893 for (int i=0; i<N; i++) { 4894 removeProcessLocked(procs.get(i), false, true, "kill all background"); 4895 } 4896 mAllowLowerMemLevel = true; 4897 updateOomAdjLocked(); 4898 doLowMemReportIfNeededLocked(null); 4899 } 4900 } finally { 4901 Binder.restoreCallingIdentity(callingId); 4902 } 4903 } 4904 4905 @Override 4906 public void forceStopPackage(final String packageName, int userId) { 4907 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4908 != PackageManager.PERMISSION_GRANTED) { 4909 String msg = "Permission Denial: forceStopPackage() from pid=" 4910 + Binder.getCallingPid() 4911 + ", uid=" + Binder.getCallingUid() 4912 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4913 Slog.w(TAG, msg); 4914 throw new SecurityException(msg); 4915 } 4916 final int callingPid = Binder.getCallingPid(); 4917 userId = handleIncomingUser(callingPid, Binder.getCallingUid(), 4918 userId, true, ALLOW_FULL_ONLY, "forceStopPackage", null); 4919 long callingId = Binder.clearCallingIdentity(); 4920 try { 4921 IPackageManager pm = AppGlobals.getPackageManager(); 4922 synchronized(this) { 4923 int[] users = userId == UserHandle.USER_ALL 4924 ? getUsersLocked() : new int[] { userId }; 4925 for (int user : users) { 4926 int pkgUid = -1; 4927 try { 4928 pkgUid = pm.getPackageUid(packageName, user); 4929 } catch (RemoteException e) { 4930 } 4931 if (pkgUid == -1) { 4932 Slog.w(TAG, "Invalid packageName: " + packageName); 4933 continue; 4934 } 4935 try { 4936 pm.setPackageStoppedState(packageName, true, user); 4937 } catch (RemoteException e) { 4938 } catch (IllegalArgumentException e) { 4939 Slog.w(TAG, "Failed trying to unstop package " 4940 + packageName + ": " + e); 4941 } 4942 if (isUserRunningLocked(user, false)) { 4943 forceStopPackageLocked(packageName, pkgUid, "from pid " + callingPid); 4944 } 4945 } 4946 } 4947 } finally { 4948 Binder.restoreCallingIdentity(callingId); 4949 } 4950 } 4951 4952 @Override 4953 public void addPackageDependency(String packageName) { 4954 synchronized (this) { 4955 int callingPid = Binder.getCallingPid(); 4956 if (callingPid == Process.myPid()) { 4957 // Yeah, um, no. 4958 Slog.w(TAG, "Can't addPackageDependency on system process"); 4959 return; 4960 } 4961 ProcessRecord proc; 4962 synchronized (mPidsSelfLocked) { 4963 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 4964 } 4965 if (proc != null) { 4966 if (proc.pkgDeps == null) { 4967 proc.pkgDeps = new ArraySet<String>(1); 4968 } 4969 proc.pkgDeps.add(packageName); 4970 } 4971 } 4972 } 4973 4974 /* 4975 * The pkg name and app id have to be specified. 4976 */ 4977 @Override 4978 public void killApplicationWithAppId(String pkg, int appid, String reason) { 4979 if (pkg == null) { 4980 return; 4981 } 4982 // Make sure the uid is valid. 4983 if (appid < 0) { 4984 Slog.w(TAG, "Invalid appid specified for pkg : " + pkg); 4985 return; 4986 } 4987 int callerUid = Binder.getCallingUid(); 4988 // Only the system server can kill an application 4989 if (callerUid == Process.SYSTEM_UID) { 4990 // Post an aysnc message to kill the application 4991 Message msg = mHandler.obtainMessage(KILL_APPLICATION_MSG); 4992 msg.arg1 = appid; 4993 msg.arg2 = 0; 4994 Bundle bundle = new Bundle(); 4995 bundle.putString("pkg", pkg); 4996 bundle.putString("reason", reason); 4997 msg.obj = bundle; 4998 mHandler.sendMessage(msg); 4999 } else { 5000 throw new SecurityException(callerUid + " cannot kill pkg: " + 5001 pkg); 5002 } 5003 } 5004 5005 @Override 5006 public void closeSystemDialogs(String reason) { 5007 enforceNotIsolatedCaller("closeSystemDialogs"); 5008 5009 final int pid = Binder.getCallingPid(); 5010 final int uid = Binder.getCallingUid(); 5011 final long origId = Binder.clearCallingIdentity(); 5012 try { 5013 synchronized (this) { 5014 // Only allow this from foreground processes, so that background 5015 // applications can't abuse it to prevent system UI from being shown. 5016 if (uid >= Process.FIRST_APPLICATION_UID) { 5017 ProcessRecord proc; 5018 synchronized (mPidsSelfLocked) { 5019 proc = mPidsSelfLocked.get(pid); 5020 } 5021 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 5022 Slog.w(TAG, "Ignoring closeSystemDialogs " + reason 5023 + " from background process " + proc); 5024 return; 5025 } 5026 } 5027 closeSystemDialogsLocked(reason); 5028 } 5029 } finally { 5030 Binder.restoreCallingIdentity(origId); 5031 } 5032 } 5033 5034 void closeSystemDialogsLocked(String reason) { 5035 Intent intent = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS); 5036 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5037 | Intent.FLAG_RECEIVER_FOREGROUND); 5038 if (reason != null) { 5039 intent.putExtra("reason", reason); 5040 } 5041 mWindowManager.closeSystemDialogs(reason); 5042 5043 mStackSupervisor.closeSystemDialogsLocked(); 5044 5045 broadcastIntentLocked(null, null, intent, null, 5046 null, 0, null, null, null, AppOpsManager.OP_NONE, false, false, -1, 5047 Process.SYSTEM_UID, UserHandle.USER_ALL); 5048 } 5049 5050 @Override 5051 public Debug.MemoryInfo[] getProcessMemoryInfo(int[] pids) { 5052 enforceNotIsolatedCaller("getProcessMemoryInfo"); 5053 Debug.MemoryInfo[] infos = new Debug.MemoryInfo[pids.length]; 5054 for (int i=pids.length-1; i>=0; i--) { 5055 ProcessRecord proc; 5056 int oomAdj; 5057 synchronized (this) { 5058 synchronized (mPidsSelfLocked) { 5059 proc = mPidsSelfLocked.get(pids[i]); 5060 oomAdj = proc != null ? proc.setAdj : 0; 5061 } 5062 } 5063 infos[i] = new Debug.MemoryInfo(); 5064 Debug.getMemoryInfo(pids[i], infos[i]); 5065 if (proc != null) { 5066 synchronized (this) { 5067 if (proc.thread != null && proc.setAdj == oomAdj) { 5068 // Record this for posterity if the process has been stable. 5069 proc.baseProcessTracker.addPss(infos[i].getTotalPss(), 5070 infos[i].getTotalUss(), false, proc.pkgList); 5071 } 5072 } 5073 } 5074 } 5075 return infos; 5076 } 5077 5078 @Override 5079 public long[] getProcessPss(int[] pids) { 5080 enforceNotIsolatedCaller("getProcessPss"); 5081 long[] pss = new long[pids.length]; 5082 for (int i=pids.length-1; i>=0; i--) { 5083 ProcessRecord proc; 5084 int oomAdj; 5085 synchronized (this) { 5086 synchronized (mPidsSelfLocked) { 5087 proc = mPidsSelfLocked.get(pids[i]); 5088 oomAdj = proc != null ? proc.setAdj : 0; 5089 } 5090 } 5091 long[] tmpUss = new long[1]; 5092 pss[i] = Debug.getPss(pids[i], tmpUss); 5093 if (proc != null) { 5094 synchronized (this) { 5095 if (proc.thread != null && proc.setAdj == oomAdj) { 5096 // Record this for posterity if the process has been stable. 5097 proc.baseProcessTracker.addPss(pss[i], tmpUss[0], false, proc.pkgList); 5098 } 5099 } 5100 } 5101 } 5102 return pss; 5103 } 5104 5105 @Override 5106 public void killApplicationProcess(String processName, int uid) { 5107 if (processName == null) { 5108 return; 5109 } 5110 5111 int callerUid = Binder.getCallingUid(); 5112 // Only the system server can kill an application 5113 if (callerUid == Process.SYSTEM_UID) { 5114 synchronized (this) { 5115 ProcessRecord app = getProcessRecordLocked(processName, uid, true); 5116 if (app != null && app.thread != null) { 5117 try { 5118 app.thread.scheduleSuicide(); 5119 } catch (RemoteException e) { 5120 // If the other end already died, then our work here is done. 5121 } 5122 } else { 5123 Slog.w(TAG, "Process/uid not found attempting kill of " 5124 + processName + " / " + uid); 5125 } 5126 } 5127 } else { 5128 throw new SecurityException(callerUid + " cannot kill app process: " + 5129 processName); 5130 } 5131 } 5132 5133 private void forceStopPackageLocked(final String packageName, int uid, String reason) { 5134 forceStopPackageLocked(packageName, UserHandle.getAppId(uid), false, 5135 false, true, false, false, UserHandle.getUserId(uid), reason); 5136 Intent intent = new Intent(Intent.ACTION_PACKAGE_RESTARTED, 5137 Uri.fromParts("package", packageName, null)); 5138 if (!mProcessesReady) { 5139 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5140 | Intent.FLAG_RECEIVER_FOREGROUND); 5141 } 5142 intent.putExtra(Intent.EXTRA_UID, uid); 5143 intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(uid)); 5144 broadcastIntentLocked(null, null, intent, 5145 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 5146 false, false, 5147 MY_PID, Process.SYSTEM_UID, UserHandle.getUserId(uid)); 5148 } 5149 5150 private void forceStopUserLocked(int userId, String reason) { 5151 forceStopPackageLocked(null, -1, false, false, true, false, false, userId, reason); 5152 Intent intent = new Intent(Intent.ACTION_USER_STOPPED); 5153 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5154 | Intent.FLAG_RECEIVER_FOREGROUND); 5155 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 5156 broadcastIntentLocked(null, null, intent, 5157 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 5158 false, false, 5159 MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 5160 } 5161 5162 private final boolean killPackageProcessesLocked(String packageName, int appId, 5163 int userId, int minOomAdj, boolean callerWillRestart, boolean allowRestart, 5164 boolean doit, boolean evenPersistent, String reason) { 5165 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 5166 5167 // Remove all processes this package may have touched: all with the 5168 // same UID (except for the system or root user), and all whose name 5169 // matches the package name. 5170 final int NP = mProcessNames.getMap().size(); 5171 for (int ip=0; ip<NP; ip++) { 5172 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 5173 final int NA = apps.size(); 5174 for (int ia=0; ia<NA; ia++) { 5175 ProcessRecord app = apps.valueAt(ia); 5176 if (app.persistent && !evenPersistent) { 5177 // we don't kill persistent processes 5178 continue; 5179 } 5180 if (app.removed) { 5181 if (doit) { 5182 procs.add(app); 5183 } 5184 continue; 5185 } 5186 5187 // Skip process if it doesn't meet our oom adj requirement. 5188 if (app.setAdj < minOomAdj) { 5189 continue; 5190 } 5191 5192 // If no package is specified, we call all processes under the 5193 // give user id. 5194 if (packageName == null) { 5195 if (app.userId != userId) { 5196 continue; 5197 } 5198 if (appId >= 0 && UserHandle.getAppId(app.uid) != appId) { 5199 continue; 5200 } 5201 // Package has been specified, we want to hit all processes 5202 // that match it. We need to qualify this by the processes 5203 // that are running under the specified app and user ID. 5204 } else { 5205 final boolean isDep = app.pkgDeps != null 5206 && app.pkgDeps.contains(packageName); 5207 if (!isDep && UserHandle.getAppId(app.uid) != appId) { 5208 continue; 5209 } 5210 if (userId != UserHandle.USER_ALL && app.userId != userId) { 5211 continue; 5212 } 5213 if (!app.pkgList.containsKey(packageName) && !isDep) { 5214 continue; 5215 } 5216 } 5217 5218 // Process has passed all conditions, kill it! 5219 if (!doit) { 5220 return true; 5221 } 5222 app.removed = true; 5223 procs.add(app); 5224 } 5225 } 5226 5227 int N = procs.size(); 5228 for (int i=0; i<N; i++) { 5229 removeProcessLocked(procs.get(i), callerWillRestart, allowRestart, reason); 5230 } 5231 updateOomAdjLocked(); 5232 return N > 0; 5233 } 5234 5235 private final boolean forceStopPackageLocked(String name, int appId, 5236 boolean callerWillRestart, boolean purgeCache, boolean doit, 5237 boolean evenPersistent, boolean uninstalling, int userId, String reason) { 5238 int i; 5239 int N; 5240 5241 if (userId == UserHandle.USER_ALL && name == null) { 5242 Slog.w(TAG, "Can't force stop all processes of all users, that is insane!"); 5243 } 5244 5245 if (appId < 0 && name != null) { 5246 try { 5247 appId = UserHandle.getAppId( 5248 AppGlobals.getPackageManager().getPackageUid(name, 0)); 5249 } catch (RemoteException e) { 5250 } 5251 } 5252 5253 if (doit) { 5254 if (name != null) { 5255 Slog.i(TAG, "Force stopping " + name + " appid=" + appId 5256 + " user=" + userId + ": " + reason); 5257 } else { 5258 Slog.i(TAG, "Force stopping u" + userId + ": " + reason); 5259 } 5260 5261 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 5262 for (int ip=pmap.size()-1; ip>=0; ip--) { 5263 SparseArray<Long> ba = pmap.valueAt(ip); 5264 for (i=ba.size()-1; i>=0; i--) { 5265 boolean remove = false; 5266 final int entUid = ba.keyAt(i); 5267 if (name != null) { 5268 if (userId == UserHandle.USER_ALL) { 5269 if (UserHandle.getAppId(entUid) == appId) { 5270 remove = true; 5271 } 5272 } else { 5273 if (entUid == UserHandle.getUid(userId, appId)) { 5274 remove = true; 5275 } 5276 } 5277 } else if (UserHandle.getUserId(entUid) == userId) { 5278 remove = true; 5279 } 5280 if (remove) { 5281 ba.removeAt(i); 5282 } 5283 } 5284 if (ba.size() == 0) { 5285 pmap.removeAt(ip); 5286 } 5287 } 5288 } 5289 5290 boolean didSomething = killPackageProcessesLocked(name, appId, userId, 5291 -100, callerWillRestart, true, doit, evenPersistent, 5292 name == null ? ("stop user " + userId) : ("stop " + name)); 5293 5294 if (mStackSupervisor.forceStopPackageLocked(name, doit, evenPersistent, userId)) { 5295 if (!doit) { 5296 return true; 5297 } 5298 didSomething = true; 5299 } 5300 5301 if (mServices.forceStopLocked(name, userId, evenPersistent, doit)) { 5302 if (!doit) { 5303 return true; 5304 } 5305 didSomething = true; 5306 } 5307 5308 if (name == null) { 5309 // Remove all sticky broadcasts from this user. 5310 mStickyBroadcasts.remove(userId); 5311 } 5312 5313 ArrayList<ContentProviderRecord> providers = new ArrayList<ContentProviderRecord>(); 5314 if (mProviderMap.collectForceStopProviders(name, appId, doit, evenPersistent, 5315 userId, providers)) { 5316 if (!doit) { 5317 return true; 5318 } 5319 didSomething = true; 5320 } 5321 N = providers.size(); 5322 for (i=0; i<N; i++) { 5323 removeDyingProviderLocked(null, providers.get(i), true); 5324 } 5325 5326 // Remove transient permissions granted from/to this package/user 5327 removeUriPermissionsForPackageLocked(name, userId, false); 5328 5329 if (name == null || uninstalling) { 5330 // Remove pending intents. For now we only do this when force 5331 // stopping users, because we have some problems when doing this 5332 // for packages -- app widgets are not currently cleaned up for 5333 // such packages, so they can be left with bad pending intents. 5334 if (mIntentSenderRecords.size() > 0) { 5335 Iterator<WeakReference<PendingIntentRecord>> it 5336 = mIntentSenderRecords.values().iterator(); 5337 while (it.hasNext()) { 5338 WeakReference<PendingIntentRecord> wpir = it.next(); 5339 if (wpir == null) { 5340 it.remove(); 5341 continue; 5342 } 5343 PendingIntentRecord pir = wpir.get(); 5344 if (pir == null) { 5345 it.remove(); 5346 continue; 5347 } 5348 if (name == null) { 5349 // Stopping user, remove all objects for the user. 5350 if (pir.key.userId != userId) { 5351 // Not the same user, skip it. 5352 continue; 5353 } 5354 } else { 5355 if (UserHandle.getAppId(pir.uid) != appId) { 5356 // Different app id, skip it. 5357 continue; 5358 } 5359 if (userId != UserHandle.USER_ALL && pir.key.userId != userId) { 5360 // Different user, skip it. 5361 continue; 5362 } 5363 if (!pir.key.packageName.equals(name)) { 5364 // Different package, skip it. 5365 continue; 5366 } 5367 } 5368 if (!doit) { 5369 return true; 5370 } 5371 didSomething = true; 5372 it.remove(); 5373 pir.canceled = true; 5374 if (pir.key.activity != null) { 5375 pir.key.activity.pendingResults.remove(pir.ref); 5376 } 5377 } 5378 } 5379 } 5380 5381 if (doit) { 5382 if (purgeCache && name != null) { 5383 AttributeCache ac = AttributeCache.instance(); 5384 if (ac != null) { 5385 ac.removePackage(name); 5386 } 5387 } 5388 if (mBooted) { 5389 mStackSupervisor.resumeTopActivitiesLocked(); 5390 mStackSupervisor.scheduleIdleLocked(); 5391 } 5392 } 5393 5394 return didSomething; 5395 } 5396 5397 private final boolean removeProcessLocked(ProcessRecord app, 5398 boolean callerWillRestart, boolean allowRestart, String reason) { 5399 final String name = app.processName; 5400 final int uid = app.uid; 5401 if (DEBUG_PROCESSES) Slog.d( 5402 TAG, "Force removing proc " + app.toShortString() + " (" + name 5403 + "/" + uid + ")"); 5404 5405 mProcessNames.remove(name, uid); 5406 mIsolatedProcesses.remove(app.uid); 5407 if (mHeavyWeightProcess == app) { 5408 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5409 mHeavyWeightProcess.userId, 0)); 5410 mHeavyWeightProcess = null; 5411 } 5412 boolean needRestart = false; 5413 if (app.pid > 0 && app.pid != MY_PID) { 5414 int pid = app.pid; 5415 synchronized (mPidsSelfLocked) { 5416 mPidsSelfLocked.remove(pid); 5417 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5418 } 5419 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 5420 if (app.isolated) { 5421 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5422 } 5423 killUnneededProcessLocked(app, reason); 5424 Process.killProcessGroup(app.info.uid, app.pid); 5425 handleAppDiedLocked(app, true, allowRestart); 5426 removeLruProcessLocked(app); 5427 5428 if (app.persistent && !app.isolated) { 5429 if (!callerWillRestart) { 5430 addAppLocked(app.info, false, null /* ABI override */); 5431 } else { 5432 needRestart = true; 5433 } 5434 } 5435 } else { 5436 mRemovedProcesses.add(app); 5437 } 5438 5439 return needRestart; 5440 } 5441 5442 private final void processStartTimedOutLocked(ProcessRecord app) { 5443 final int pid = app.pid; 5444 boolean gone = false; 5445 synchronized (mPidsSelfLocked) { 5446 ProcessRecord knownApp = mPidsSelfLocked.get(pid); 5447 if (knownApp != null && knownApp.thread == null) { 5448 mPidsSelfLocked.remove(pid); 5449 gone = true; 5450 } 5451 } 5452 5453 if (gone) { 5454 Slog.w(TAG, "Process " + app + " failed to attach"); 5455 EventLog.writeEvent(EventLogTags.AM_PROCESS_START_TIMEOUT, app.userId, 5456 pid, app.uid, app.processName); 5457 mProcessNames.remove(app.processName, app.uid); 5458 mIsolatedProcesses.remove(app.uid); 5459 if (mHeavyWeightProcess == app) { 5460 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5461 mHeavyWeightProcess.userId, 0)); 5462 mHeavyWeightProcess = null; 5463 } 5464 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 5465 if (app.isolated) { 5466 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5467 } 5468 // Take care of any launching providers waiting for this process. 5469 checkAppInLaunchingProvidersLocked(app, true); 5470 // Take care of any services that are waiting for the process. 5471 mServices.processStartTimedOutLocked(app); 5472 killUnneededProcessLocked(app, "start timeout"); 5473 if (mBackupTarget != null && mBackupTarget.app.pid == pid) { 5474 Slog.w(TAG, "Unattached app died before backup, skipping"); 5475 try { 5476 IBackupManager bm = IBackupManager.Stub.asInterface( 5477 ServiceManager.getService(Context.BACKUP_SERVICE)); 5478 bm.agentDisconnected(app.info.packageName); 5479 } catch (RemoteException e) { 5480 // Can't happen; the backup manager is local 5481 } 5482 } 5483 if (isPendingBroadcastProcessLocked(pid)) { 5484 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 5485 skipPendingBroadcastLocked(pid); 5486 } 5487 } else { 5488 Slog.w(TAG, "Spurious process start timeout - pid not known for " + app); 5489 } 5490 } 5491 5492 private final boolean attachApplicationLocked(IApplicationThread thread, 5493 int pid) { 5494 5495 // Find the application record that is being attached... either via 5496 // the pid if we are running in multiple processes, or just pull the 5497 // next app record if we are emulating process with anonymous threads. 5498 ProcessRecord app; 5499 if (pid != MY_PID && pid >= 0) { 5500 synchronized (mPidsSelfLocked) { 5501 app = mPidsSelfLocked.get(pid); 5502 } 5503 } else { 5504 app = null; 5505 } 5506 5507 if (app == null) { 5508 Slog.w(TAG, "No pending application record for pid " + pid 5509 + " (IApplicationThread " + thread + "); dropping process"); 5510 EventLog.writeEvent(EventLogTags.AM_DROP_PROCESS, pid); 5511 if (pid > 0 && pid != MY_PID) { 5512 Process.killProcessQuiet(pid); 5513 //TODO: Process.killProcessGroup(app.info.uid, pid); 5514 } else { 5515 try { 5516 thread.scheduleExit(); 5517 } catch (Exception e) { 5518 // Ignore exceptions. 5519 } 5520 } 5521 return false; 5522 } 5523 5524 // If this application record is still attached to a previous 5525 // process, clean it up now. 5526 if (app.thread != null) { 5527 handleAppDiedLocked(app, true, true); 5528 } 5529 5530 // Tell the process all about itself. 5531 5532 if (localLOGV) Slog.v( 5533 TAG, "Binding process pid " + pid + " to record " + app); 5534 5535 final String processName = app.processName; 5536 try { 5537 AppDeathRecipient adr = new AppDeathRecipient( 5538 app, pid, thread); 5539 thread.asBinder().linkToDeath(adr, 0); 5540 app.deathRecipient = adr; 5541 } catch (RemoteException e) { 5542 app.resetPackageList(mProcessStats); 5543 startProcessLocked(app, "link fail", processName); 5544 return false; 5545 } 5546 5547 EventLog.writeEvent(EventLogTags.AM_PROC_BOUND, app.userId, app.pid, app.processName); 5548 5549 app.makeActive(thread, mProcessStats); 5550 app.curAdj = app.setAdj = -100; 5551 app.curSchedGroup = app.setSchedGroup = Process.THREAD_GROUP_DEFAULT; 5552 app.forcingToForeground = null; 5553 updateProcessForegroundLocked(app, false, false); 5554 app.hasShownUi = false; 5555 app.debugging = false; 5556 app.cached = false; 5557 5558 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5559 5560 boolean normalMode = mProcessesReady || isAllowedWhileBooting(app.info); 5561 List<ProviderInfo> providers = normalMode ? generateApplicationProvidersLocked(app) : null; 5562 5563 if (!normalMode) { 5564 Slog.i(TAG, "Launching preboot mode app: " + app); 5565 } 5566 5567 if (localLOGV) Slog.v( 5568 TAG, "New app record " + app 5569 + " thread=" + thread.asBinder() + " pid=" + pid); 5570 try { 5571 int testMode = IApplicationThread.DEBUG_OFF; 5572 if (mDebugApp != null && mDebugApp.equals(processName)) { 5573 testMode = mWaitForDebugger 5574 ? IApplicationThread.DEBUG_WAIT 5575 : IApplicationThread.DEBUG_ON; 5576 app.debugging = true; 5577 if (mDebugTransient) { 5578 mDebugApp = mOrigDebugApp; 5579 mWaitForDebugger = mOrigWaitForDebugger; 5580 } 5581 } 5582 String profileFile = app.instrumentationProfileFile; 5583 ParcelFileDescriptor profileFd = null; 5584 boolean profileAutoStop = false; 5585 if (mProfileApp != null && mProfileApp.equals(processName)) { 5586 mProfileProc = app; 5587 profileFile = mProfileFile; 5588 profileFd = mProfileFd; 5589 profileAutoStop = mAutoStopProfiler; 5590 } 5591 boolean enableOpenGlTrace = false; 5592 if (mOpenGlTraceApp != null && mOpenGlTraceApp.equals(processName)) { 5593 enableOpenGlTrace = true; 5594 mOpenGlTraceApp = null; 5595 } 5596 5597 // If the app is being launched for restore or full backup, set it up specially 5598 boolean isRestrictedBackupMode = false; 5599 if (mBackupTarget != null && mBackupAppName.equals(processName)) { 5600 isRestrictedBackupMode = (mBackupTarget.backupMode == BackupRecord.RESTORE) 5601 || (mBackupTarget.backupMode == BackupRecord.RESTORE_FULL) 5602 || (mBackupTarget.backupMode == BackupRecord.BACKUP_FULL); 5603 } 5604 5605 ensurePackageDexOpt(app.instrumentationInfo != null 5606 ? app.instrumentationInfo.packageName 5607 : app.info.packageName); 5608 if (app.instrumentationClass != null) { 5609 ensurePackageDexOpt(app.instrumentationClass.getPackageName()); 5610 } 5611 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Binding proc " 5612 + processName + " with config " + mConfiguration); 5613 ApplicationInfo appInfo = app.instrumentationInfo != null 5614 ? app.instrumentationInfo : app.info; 5615 app.compat = compatibilityInfoForPackageLocked(appInfo); 5616 if (profileFd != null) { 5617 profileFd = profileFd.dup(); 5618 } 5619 thread.bindApplication(processName, appInfo, providers, 5620 app.instrumentationClass, profileFile, profileFd, profileAutoStop, 5621 app.instrumentationArguments, app.instrumentationWatcher, 5622 app.instrumentationUiAutomationConnection, testMode, enableOpenGlTrace, 5623 isRestrictedBackupMode || !normalMode, app.persistent, 5624 new Configuration(mConfiguration), app.compat, getCommonServicesLocked(), 5625 mCoreSettingsObserver.getCoreSettingsLocked()); 5626 updateLruProcessLocked(app, false, null); 5627 app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis(); 5628 } catch (Exception e) { 5629 // todo: Yikes! What should we do? For now we will try to 5630 // start another process, but that could easily get us in 5631 // an infinite loop of restarting processes... 5632 Slog.w(TAG, "Exception thrown during bind!", e); 5633 5634 app.resetPackageList(mProcessStats); 5635 app.unlinkDeathRecipient(); 5636 startProcessLocked(app, "bind fail", processName); 5637 return false; 5638 } 5639 5640 // Remove this record from the list of starting applications. 5641 mPersistentStartingProcesses.remove(app); 5642 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 5643 "Attach application locked removing on hold: " + app); 5644 mProcessesOnHold.remove(app); 5645 5646 boolean badApp = false; 5647 boolean didSomething = false; 5648 5649 // See if the top visible activity is waiting to run in this process... 5650 if (normalMode) { 5651 try { 5652 if (mStackSupervisor.attachApplicationLocked(app)) { 5653 didSomething = true; 5654 } 5655 } catch (Exception e) { 5656 badApp = true; 5657 } 5658 } 5659 5660 // Find any services that should be running in this process... 5661 if (!badApp) { 5662 try { 5663 didSomething |= mServices.attachApplicationLocked(app, processName); 5664 } catch (Exception e) { 5665 badApp = true; 5666 } 5667 } 5668 5669 // Check if a next-broadcast receiver is in this process... 5670 if (!badApp && isPendingBroadcastProcessLocked(pid)) { 5671 try { 5672 didSomething |= sendPendingBroadcastsLocked(app); 5673 } catch (Exception e) { 5674 // If the app died trying to launch the receiver we declare it 'bad' 5675 badApp = true; 5676 } 5677 } 5678 5679 // Check whether the next backup agent is in this process... 5680 if (!badApp && mBackupTarget != null && mBackupTarget.appInfo.uid == app.uid) { 5681 if (DEBUG_BACKUP) Slog.v(TAG, "New app is backup target, launching agent for " + app); 5682 ensurePackageDexOpt(mBackupTarget.appInfo.packageName); 5683 try { 5684 thread.scheduleCreateBackupAgent(mBackupTarget.appInfo, 5685 compatibilityInfoForPackageLocked(mBackupTarget.appInfo), 5686 mBackupTarget.backupMode); 5687 } catch (Exception e) { 5688 Slog.w(TAG, "Exception scheduling backup agent creation: "); 5689 e.printStackTrace(); 5690 } 5691 } 5692 5693 if (badApp) { 5694 // todo: Also need to kill application to deal with all 5695 // kinds of exceptions. 5696 handleAppDiedLocked(app, false, true); 5697 return false; 5698 } 5699 5700 if (!didSomething) { 5701 updateOomAdjLocked(); 5702 } 5703 5704 return true; 5705 } 5706 5707 @Override 5708 public final void attachApplication(IApplicationThread thread) { 5709 synchronized (this) { 5710 int callingPid = Binder.getCallingPid(); 5711 final long origId = Binder.clearCallingIdentity(); 5712 attachApplicationLocked(thread, callingPid); 5713 Binder.restoreCallingIdentity(origId); 5714 } 5715 } 5716 5717 @Override 5718 public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) { 5719 final long origId = Binder.clearCallingIdentity(); 5720 synchronized (this) { 5721 ActivityStack stack = ActivityRecord.getStackLocked(token); 5722 if (stack != null) { 5723 ActivityRecord r = 5724 mStackSupervisor.activityIdleInternalLocked(token, false, config); 5725 if (stopProfiling) { 5726 if ((mProfileProc == r.app) && (mProfileFd != null)) { 5727 try { 5728 mProfileFd.close(); 5729 } catch (IOException e) { 5730 } 5731 clearProfilerLocked(); 5732 } 5733 } 5734 } 5735 } 5736 Binder.restoreCallingIdentity(origId); 5737 } 5738 5739 void postEnableScreenAfterBootLocked() { 5740 mHandler.sendEmptyMessage(ENABLE_SCREEN_AFTER_BOOT_MSG); 5741 } 5742 5743 void enableScreenAfterBoot() { 5744 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN, 5745 SystemClock.uptimeMillis()); 5746 mWindowManager.enableScreenAfterBoot(); 5747 5748 synchronized (this) { 5749 updateEventDispatchingLocked(); 5750 } 5751 } 5752 5753 @Override 5754 public void showBootMessage(final CharSequence msg, final boolean always) { 5755 enforceNotIsolatedCaller("showBootMessage"); 5756 mWindowManager.showBootMessage(msg, always); 5757 } 5758 5759 @Override 5760 public void keyguardWaitingForActivityDrawn() { 5761 enforceNotIsolatedCaller("keyguardWaitingForActivityDrawn"); 5762 final long token = Binder.clearCallingIdentity(); 5763 try { 5764 synchronized (this) { 5765 if (DEBUG_LOCKSCREEN) logLockScreen(""); 5766 mWindowManager.keyguardWaitingForActivityDrawn(); 5767 } 5768 } finally { 5769 Binder.restoreCallingIdentity(token); 5770 } 5771 } 5772 5773 final void finishBooting() { 5774 // Register receivers to handle package update events 5775 mPackageMonitor.register(mContext, Looper.getMainLooper(), false); 5776 5777 // Let system services know. 5778 mSystemServiceManager.startBootPhase(SystemService.PHASE_BOOT_COMPLETED); 5779 5780 synchronized (this) { 5781 // Ensure that any processes we had put on hold are now started 5782 // up. 5783 final int NP = mProcessesOnHold.size(); 5784 if (NP > 0) { 5785 ArrayList<ProcessRecord> procs = 5786 new ArrayList<ProcessRecord>(mProcessesOnHold); 5787 for (int ip=0; ip<NP; ip++) { 5788 if (DEBUG_PROCESSES) Slog.v(TAG, "Starting process on hold: " 5789 + procs.get(ip)); 5790 startProcessLocked(procs.get(ip), "on-hold", null); 5791 } 5792 } 5793 5794 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 5795 // Start looking for apps that are abusing wake locks. 5796 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 5797 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 5798 // Tell anyone interested that we are done booting! 5799 SystemProperties.set("sys.boot_completed", "1"); 5800 SystemProperties.set("dev.bootcomplete", "1"); 5801 for (int i=0; i<mStartedUsers.size(); i++) { 5802 UserStartedState uss = mStartedUsers.valueAt(i); 5803 if (uss.mState == UserStartedState.STATE_BOOTING) { 5804 uss.mState = UserStartedState.STATE_RUNNING; 5805 final int userId = mStartedUsers.keyAt(i); 5806 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 5807 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 5808 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 5809 broadcastIntentLocked(null, null, intent, null, 5810 new IIntentReceiver.Stub() { 5811 @Override 5812 public void performReceive(Intent intent, int resultCode, 5813 String data, Bundle extras, boolean ordered, 5814 boolean sticky, int sendingUser) { 5815 synchronized (ActivityManagerService.this) { 5816 requestPssAllProcsLocked(SystemClock.uptimeMillis(), 5817 true, false); 5818 } 5819 } 5820 }, 5821 0, null, null, 5822 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, 5823 AppOpsManager.OP_NONE, true, false, MY_PID, Process.SYSTEM_UID, 5824 userId); 5825 } 5826 } 5827 scheduleStartProfilesLocked(); 5828 } 5829 } 5830 } 5831 5832 final void ensureBootCompleted() { 5833 boolean booting; 5834 boolean enableScreen; 5835 synchronized (this) { 5836 booting = mBooting; 5837 mBooting = false; 5838 enableScreen = !mBooted; 5839 mBooted = true; 5840 } 5841 5842 if (booting) { 5843 finishBooting(); 5844 } 5845 5846 if (enableScreen) { 5847 enableScreenAfterBoot(); 5848 } 5849 } 5850 5851 @Override 5852 public final void activityResumed(IBinder token) { 5853 final long origId = Binder.clearCallingIdentity(); 5854 synchronized(this) { 5855 ActivityStack stack = ActivityRecord.getStackLocked(token); 5856 if (stack != null) { 5857 ActivityRecord.activityResumedLocked(token); 5858 } 5859 } 5860 Binder.restoreCallingIdentity(origId); 5861 } 5862 5863 @Override 5864 public final void activityPaused(IBinder token, PersistableBundle persistentState) { 5865 final long origId = Binder.clearCallingIdentity(); 5866 synchronized(this) { 5867 ActivityStack stack = ActivityRecord.getStackLocked(token); 5868 if (stack != null) { 5869 stack.activityPausedLocked(token, false, persistentState); 5870 } 5871 } 5872 Binder.restoreCallingIdentity(origId); 5873 } 5874 5875 @Override 5876 public final void activityStopped(IBinder token, Bundle icicle, 5877 PersistableBundle persistentState, CharSequence description) { 5878 if (localLOGV) Slog.v(TAG, "Activity stopped: token=" + token); 5879 5880 // Refuse possible leaked file descriptors 5881 if (icicle != null && icicle.hasFileDescriptors()) { 5882 throw new IllegalArgumentException("File descriptors passed in Bundle"); 5883 } 5884 5885 final long origId = Binder.clearCallingIdentity(); 5886 5887 synchronized (this) { 5888 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5889 if (r != null) { 5890 r.task.stack.activityStoppedLocked(r, icicle, persistentState, description); 5891 } 5892 } 5893 5894 trimApplications(); 5895 5896 Binder.restoreCallingIdentity(origId); 5897 } 5898 5899 @Override 5900 public final void activityDestroyed(IBinder token) { 5901 if (DEBUG_SWITCH) Slog.v(TAG, "ACTIVITY DESTROYED: " + token); 5902 synchronized (this) { 5903 ActivityStack stack = ActivityRecord.getStackLocked(token); 5904 if (stack != null) { 5905 stack.activityDestroyedLocked(token); 5906 } 5907 } 5908 } 5909 5910 @Override 5911 public final void backgroundResourcesReleased(IBinder token) { 5912 final long origId = Binder.clearCallingIdentity(); 5913 try { 5914 synchronized (this) { 5915 ActivityStack stack = ActivityRecord.getStackLocked(token); 5916 if (stack != null) { 5917 stack.backgroundResourcesReleased(token); 5918 } 5919 } 5920 } finally { 5921 Binder.restoreCallingIdentity(origId); 5922 } 5923 } 5924 5925 @Override 5926 public final void notifyLaunchTaskBehindComplete(IBinder token) { 5927 mStackSupervisor.scheduleLaunchTaskBehindComplete(token); 5928 } 5929 5930 @Override 5931 public final void notifyEnterAnimationComplete(IBinder token) { 5932 mHandler.sendMessage(mHandler.obtainMessage(ENTER_ANIMATION_COMPLETE_MSG, token)); 5933 } 5934 5935 @Override 5936 public String getCallingPackage(IBinder token) { 5937 synchronized (this) { 5938 ActivityRecord r = getCallingRecordLocked(token); 5939 return r != null ? r.info.packageName : null; 5940 } 5941 } 5942 5943 @Override 5944 public ComponentName getCallingActivity(IBinder token) { 5945 synchronized (this) { 5946 ActivityRecord r = getCallingRecordLocked(token); 5947 return r != null ? r.intent.getComponent() : null; 5948 } 5949 } 5950 5951 private ActivityRecord getCallingRecordLocked(IBinder token) { 5952 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5953 if (r == null) { 5954 return null; 5955 } 5956 return r.resultTo; 5957 } 5958 5959 @Override 5960 public ComponentName getActivityClassForToken(IBinder token) { 5961 synchronized(this) { 5962 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5963 if (r == null) { 5964 return null; 5965 } 5966 return r.intent.getComponent(); 5967 } 5968 } 5969 5970 @Override 5971 public String getPackageForToken(IBinder token) { 5972 synchronized(this) { 5973 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5974 if (r == null) { 5975 return null; 5976 } 5977 return r.packageName; 5978 } 5979 } 5980 5981 @Override 5982 public IIntentSender getIntentSender(int type, 5983 String packageName, IBinder token, String resultWho, 5984 int requestCode, Intent[] intents, String[] resolvedTypes, 5985 int flags, Bundle options, int userId) { 5986 enforceNotIsolatedCaller("getIntentSender"); 5987 // Refuse possible leaked file descriptors 5988 if (intents != null) { 5989 if (intents.length < 1) { 5990 throw new IllegalArgumentException("Intents array length must be >= 1"); 5991 } 5992 for (int i=0; i<intents.length; i++) { 5993 Intent intent = intents[i]; 5994 if (intent != null) { 5995 if (intent.hasFileDescriptors()) { 5996 throw new IllegalArgumentException("File descriptors passed in Intent"); 5997 } 5998 if (type == ActivityManager.INTENT_SENDER_BROADCAST && 5999 (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 6000 throw new IllegalArgumentException( 6001 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 6002 } 6003 intents[i] = new Intent(intent); 6004 } 6005 } 6006 if (resolvedTypes != null && resolvedTypes.length != intents.length) { 6007 throw new IllegalArgumentException( 6008 "Intent array length does not match resolvedTypes length"); 6009 } 6010 } 6011 if (options != null) { 6012 if (options.hasFileDescriptors()) { 6013 throw new IllegalArgumentException("File descriptors passed in options"); 6014 } 6015 } 6016 6017 synchronized(this) { 6018 int callingUid = Binder.getCallingUid(); 6019 int origUserId = userId; 6020 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 6021 type == ActivityManager.INTENT_SENDER_BROADCAST, 6022 ALLOW_NON_FULL, "getIntentSender", null); 6023 if (origUserId == UserHandle.USER_CURRENT) { 6024 // We don't want to evaluate this until the pending intent is 6025 // actually executed. However, we do want to always do the 6026 // security checking for it above. 6027 userId = UserHandle.USER_CURRENT; 6028 } 6029 try { 6030 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 6031 int uid = AppGlobals.getPackageManager() 6032 .getPackageUid(packageName, UserHandle.getUserId(callingUid)); 6033 if (!UserHandle.isSameApp(callingUid, uid)) { 6034 String msg = "Permission Denial: getIntentSender() from pid=" 6035 + Binder.getCallingPid() 6036 + ", uid=" + Binder.getCallingUid() 6037 + ", (need uid=" + uid + ")" 6038 + " is not allowed to send as package " + packageName; 6039 Slog.w(TAG, msg); 6040 throw new SecurityException(msg); 6041 } 6042 } 6043 6044 return getIntentSenderLocked(type, packageName, callingUid, userId, 6045 token, resultWho, requestCode, intents, resolvedTypes, flags, options); 6046 6047 } catch (RemoteException e) { 6048 throw new SecurityException(e); 6049 } 6050 } 6051 } 6052 6053 IIntentSender getIntentSenderLocked(int type, String packageName, 6054 int callingUid, int userId, IBinder token, String resultWho, 6055 int requestCode, Intent[] intents, String[] resolvedTypes, int flags, 6056 Bundle options) { 6057 if (DEBUG_MU) 6058 Slog.v(TAG_MU, "getIntentSenderLocked(): uid=" + callingUid); 6059 ActivityRecord activity = null; 6060 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 6061 activity = ActivityRecord.isInStackLocked(token); 6062 if (activity == null) { 6063 return null; 6064 } 6065 if (activity.finishing) { 6066 return null; 6067 } 6068 } 6069 6070 final boolean noCreate = (flags&PendingIntent.FLAG_NO_CREATE) != 0; 6071 final boolean cancelCurrent = (flags&PendingIntent.FLAG_CANCEL_CURRENT) != 0; 6072 final boolean updateCurrent = (flags&PendingIntent.FLAG_UPDATE_CURRENT) != 0; 6073 flags &= ~(PendingIntent.FLAG_NO_CREATE|PendingIntent.FLAG_CANCEL_CURRENT 6074 |PendingIntent.FLAG_UPDATE_CURRENT); 6075 6076 PendingIntentRecord.Key key = new PendingIntentRecord.Key( 6077 type, packageName, activity, resultWho, 6078 requestCode, intents, resolvedTypes, flags, options, userId); 6079 WeakReference<PendingIntentRecord> ref; 6080 ref = mIntentSenderRecords.get(key); 6081 PendingIntentRecord rec = ref != null ? ref.get() : null; 6082 if (rec != null) { 6083 if (!cancelCurrent) { 6084 if (updateCurrent) { 6085 if (rec.key.requestIntent != null) { 6086 rec.key.requestIntent.replaceExtras(intents != null ? 6087 intents[intents.length - 1] : null); 6088 } 6089 if (intents != null) { 6090 intents[intents.length-1] = rec.key.requestIntent; 6091 rec.key.allIntents = intents; 6092 rec.key.allResolvedTypes = resolvedTypes; 6093 } else { 6094 rec.key.allIntents = null; 6095 rec.key.allResolvedTypes = null; 6096 } 6097 } 6098 return rec; 6099 } 6100 rec.canceled = true; 6101 mIntentSenderRecords.remove(key); 6102 } 6103 if (noCreate) { 6104 return rec; 6105 } 6106 rec = new PendingIntentRecord(this, key, callingUid); 6107 mIntentSenderRecords.put(key, rec.ref); 6108 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 6109 if (activity.pendingResults == null) { 6110 activity.pendingResults 6111 = new HashSet<WeakReference<PendingIntentRecord>>(); 6112 } 6113 activity.pendingResults.add(rec.ref); 6114 } 6115 return rec; 6116 } 6117 6118 @Override 6119 public void cancelIntentSender(IIntentSender sender) { 6120 if (!(sender instanceof PendingIntentRecord)) { 6121 return; 6122 } 6123 synchronized(this) { 6124 PendingIntentRecord rec = (PendingIntentRecord)sender; 6125 try { 6126 int uid = AppGlobals.getPackageManager() 6127 .getPackageUid(rec.key.packageName, UserHandle.getCallingUserId()); 6128 if (!UserHandle.isSameApp(uid, Binder.getCallingUid())) { 6129 String msg = "Permission Denial: cancelIntentSender() from pid=" 6130 + Binder.getCallingPid() 6131 + ", uid=" + Binder.getCallingUid() 6132 + " is not allowed to cancel packges " 6133 + rec.key.packageName; 6134 Slog.w(TAG, msg); 6135 throw new SecurityException(msg); 6136 } 6137 } catch (RemoteException e) { 6138 throw new SecurityException(e); 6139 } 6140 cancelIntentSenderLocked(rec, true); 6141 } 6142 } 6143 6144 void cancelIntentSenderLocked(PendingIntentRecord rec, boolean cleanActivity) { 6145 rec.canceled = true; 6146 mIntentSenderRecords.remove(rec.key); 6147 if (cleanActivity && rec.key.activity != null) { 6148 rec.key.activity.pendingResults.remove(rec.ref); 6149 } 6150 } 6151 6152 @Override 6153 public String getPackageForIntentSender(IIntentSender pendingResult) { 6154 if (!(pendingResult instanceof PendingIntentRecord)) { 6155 return null; 6156 } 6157 try { 6158 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6159 return res.key.packageName; 6160 } catch (ClassCastException e) { 6161 } 6162 return null; 6163 } 6164 6165 @Override 6166 public int getUidForIntentSender(IIntentSender sender) { 6167 if (sender instanceof PendingIntentRecord) { 6168 try { 6169 PendingIntentRecord res = (PendingIntentRecord)sender; 6170 return res.uid; 6171 } catch (ClassCastException e) { 6172 } 6173 } 6174 return -1; 6175 } 6176 6177 @Override 6178 public boolean isIntentSenderTargetedToPackage(IIntentSender pendingResult) { 6179 if (!(pendingResult instanceof PendingIntentRecord)) { 6180 return false; 6181 } 6182 try { 6183 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6184 if (res.key.allIntents == null) { 6185 return false; 6186 } 6187 for (int i=0; i<res.key.allIntents.length; i++) { 6188 Intent intent = res.key.allIntents[i]; 6189 if (intent.getPackage() != null && intent.getComponent() != null) { 6190 return false; 6191 } 6192 } 6193 return true; 6194 } catch (ClassCastException e) { 6195 } 6196 return false; 6197 } 6198 6199 @Override 6200 public boolean isIntentSenderAnActivity(IIntentSender pendingResult) { 6201 if (!(pendingResult instanceof PendingIntentRecord)) { 6202 return false; 6203 } 6204 try { 6205 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6206 if (res.key.type == ActivityManager.INTENT_SENDER_ACTIVITY) { 6207 return true; 6208 } 6209 return false; 6210 } catch (ClassCastException e) { 6211 } 6212 return false; 6213 } 6214 6215 @Override 6216 public Intent getIntentForIntentSender(IIntentSender pendingResult) { 6217 if (!(pendingResult instanceof PendingIntentRecord)) { 6218 return null; 6219 } 6220 try { 6221 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6222 return res.key.requestIntent != null ? new Intent(res.key.requestIntent) : null; 6223 } catch (ClassCastException e) { 6224 } 6225 return null; 6226 } 6227 6228 @Override 6229 public String getTagForIntentSender(IIntentSender pendingResult, String prefix) { 6230 if (!(pendingResult instanceof PendingIntentRecord)) { 6231 return null; 6232 } 6233 try { 6234 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6235 Intent intent = res.key.requestIntent; 6236 if (intent != null) { 6237 if (res.lastTag != null && res.lastTagPrefix == prefix && (res.lastTagPrefix == null 6238 || res.lastTagPrefix.equals(prefix))) { 6239 return res.lastTag; 6240 } 6241 res.lastTagPrefix = prefix; 6242 StringBuilder sb = new StringBuilder(128); 6243 if (prefix != null) { 6244 sb.append(prefix); 6245 } 6246 if (intent.getAction() != null) { 6247 sb.append(intent.getAction()); 6248 } else if (intent.getComponent() != null) { 6249 intent.getComponent().appendShortString(sb); 6250 } else { 6251 sb.append("?"); 6252 } 6253 return res.lastTag = sb.toString(); 6254 } 6255 } catch (ClassCastException e) { 6256 } 6257 return null; 6258 } 6259 6260 @Override 6261 public void setProcessLimit(int max) { 6262 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 6263 "setProcessLimit()"); 6264 synchronized (this) { 6265 mProcessLimit = max < 0 ? ProcessList.MAX_CACHED_APPS : max; 6266 mProcessLimitOverride = max; 6267 } 6268 trimApplications(); 6269 } 6270 6271 @Override 6272 public int getProcessLimit() { 6273 synchronized (this) { 6274 return mProcessLimitOverride; 6275 } 6276 } 6277 6278 void foregroundTokenDied(ForegroundToken token) { 6279 synchronized (ActivityManagerService.this) { 6280 synchronized (mPidsSelfLocked) { 6281 ForegroundToken cur 6282 = mForegroundProcesses.get(token.pid); 6283 if (cur != token) { 6284 return; 6285 } 6286 mForegroundProcesses.remove(token.pid); 6287 ProcessRecord pr = mPidsSelfLocked.get(token.pid); 6288 if (pr == null) { 6289 return; 6290 } 6291 pr.forcingToForeground = null; 6292 updateProcessForegroundLocked(pr, false, false); 6293 } 6294 updateOomAdjLocked(); 6295 } 6296 } 6297 6298 @Override 6299 public void setProcessForeground(IBinder token, int pid, boolean isForeground) { 6300 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 6301 "setProcessForeground()"); 6302 synchronized(this) { 6303 boolean changed = false; 6304 6305 synchronized (mPidsSelfLocked) { 6306 ProcessRecord pr = mPidsSelfLocked.get(pid); 6307 if (pr == null && isForeground) { 6308 Slog.w(TAG, "setProcessForeground called on unknown pid: " + pid); 6309 return; 6310 } 6311 ForegroundToken oldToken = mForegroundProcesses.get(pid); 6312 if (oldToken != null) { 6313 oldToken.token.unlinkToDeath(oldToken, 0); 6314 mForegroundProcesses.remove(pid); 6315 if (pr != null) { 6316 pr.forcingToForeground = null; 6317 } 6318 changed = true; 6319 } 6320 if (isForeground && token != null) { 6321 ForegroundToken newToken = new ForegroundToken() { 6322 @Override 6323 public void binderDied() { 6324 foregroundTokenDied(this); 6325 } 6326 }; 6327 newToken.pid = pid; 6328 newToken.token = token; 6329 try { 6330 token.linkToDeath(newToken, 0); 6331 mForegroundProcesses.put(pid, newToken); 6332 pr.forcingToForeground = token; 6333 changed = true; 6334 } catch (RemoteException e) { 6335 // If the process died while doing this, we will later 6336 // do the cleanup with the process death link. 6337 } 6338 } 6339 } 6340 6341 if (changed) { 6342 updateOomAdjLocked(); 6343 } 6344 } 6345 } 6346 6347 // ========================================================= 6348 // PERMISSIONS 6349 // ========================================================= 6350 6351 static class PermissionController extends IPermissionController.Stub { 6352 ActivityManagerService mActivityManagerService; 6353 PermissionController(ActivityManagerService activityManagerService) { 6354 mActivityManagerService = activityManagerService; 6355 } 6356 6357 @Override 6358 public boolean checkPermission(String permission, int pid, int uid) { 6359 return mActivityManagerService.checkPermission(permission, pid, 6360 uid) == PackageManager.PERMISSION_GRANTED; 6361 } 6362 } 6363 6364 class IntentFirewallInterface implements IntentFirewall.AMSInterface { 6365 @Override 6366 public int checkComponentPermission(String permission, int pid, int uid, 6367 int owningUid, boolean exported) { 6368 return ActivityManagerService.this.checkComponentPermission(permission, pid, uid, 6369 owningUid, exported); 6370 } 6371 6372 @Override 6373 public Object getAMSLock() { 6374 return ActivityManagerService.this; 6375 } 6376 } 6377 6378 /** 6379 * This can be called with or without the global lock held. 6380 */ 6381 int checkComponentPermission(String permission, int pid, int uid, 6382 int owningUid, boolean exported) { 6383 // We might be performing an operation on behalf of an indirect binder 6384 // invocation, e.g. via {@link #openContentUri}. Check and adjust the 6385 // client identity accordingly before proceeding. 6386 Identity tlsIdentity = sCallerIdentity.get(); 6387 if (tlsIdentity != null) { 6388 Slog.d(TAG, "checkComponentPermission() adjusting {pid,uid} to {" 6389 + tlsIdentity.pid + "," + tlsIdentity.uid + "}"); 6390 uid = tlsIdentity.uid; 6391 pid = tlsIdentity.pid; 6392 } 6393 6394 if (pid == MY_PID) { 6395 return PackageManager.PERMISSION_GRANTED; 6396 } 6397 6398 return ActivityManager.checkComponentPermission(permission, uid, 6399 owningUid, exported); 6400 } 6401 6402 /** 6403 * As the only public entry point for permissions checking, this method 6404 * can enforce the semantic that requesting a check on a null global 6405 * permission is automatically denied. (Internally a null permission 6406 * string is used when calling {@link #checkComponentPermission} in cases 6407 * when only uid-based security is needed.) 6408 * 6409 * This can be called with or without the global lock held. 6410 */ 6411 @Override 6412 public int checkPermission(String permission, int pid, int uid) { 6413 if (permission == null) { 6414 return PackageManager.PERMISSION_DENIED; 6415 } 6416 return checkComponentPermission(permission, pid, UserHandle.getAppId(uid), -1, true); 6417 } 6418 6419 /** 6420 * Binder IPC calls go through the public entry point. 6421 * This can be called with or without the global lock held. 6422 */ 6423 int checkCallingPermission(String permission) { 6424 return checkPermission(permission, 6425 Binder.getCallingPid(), 6426 UserHandle.getAppId(Binder.getCallingUid())); 6427 } 6428 6429 /** 6430 * This can be called with or without the global lock held. 6431 */ 6432 void enforceCallingPermission(String permission, String func) { 6433 if (checkCallingPermission(permission) 6434 == PackageManager.PERMISSION_GRANTED) { 6435 return; 6436 } 6437 6438 String msg = "Permission Denial: " + func + " from pid=" 6439 + Binder.getCallingPid() 6440 + ", uid=" + Binder.getCallingUid() 6441 + " requires " + permission; 6442 Slog.w(TAG, msg); 6443 throw new SecurityException(msg); 6444 } 6445 6446 /** 6447 * Determine if UID is holding permissions required to access {@link Uri} in 6448 * the given {@link ProviderInfo}. Final permission checking is always done 6449 * in {@link ContentProvider}. 6450 */ 6451 private final boolean checkHoldingPermissionsLocked( 6452 IPackageManager pm, ProviderInfo pi, GrantUri grantUri, int uid, final int modeFlags) { 6453 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6454 "checkHoldingPermissionsLocked: uri=" + grantUri + " uid=" + uid); 6455 if (UserHandle.getUserId(uid) != grantUri.sourceUserId) { 6456 if (ActivityManager.checkComponentPermission(INTERACT_ACROSS_USERS, uid, -1, true) 6457 != PERMISSION_GRANTED) { 6458 return false; 6459 } 6460 } 6461 return checkHoldingPermissionsInternalLocked(pm, pi, grantUri, uid, modeFlags, true); 6462 } 6463 6464 private final boolean checkHoldingPermissionsInternalLocked(IPackageManager pm, ProviderInfo pi, 6465 GrantUri grantUri, int uid, final int modeFlags, boolean considerUidPermissions) { 6466 if (pi.applicationInfo.uid == uid) { 6467 return true; 6468 } else if (!pi.exported) { 6469 return false; 6470 } 6471 6472 boolean readMet = (modeFlags & Intent.FLAG_GRANT_READ_URI_PERMISSION) == 0; 6473 boolean writeMet = (modeFlags & Intent.FLAG_GRANT_WRITE_URI_PERMISSION) == 0; 6474 try { 6475 // check if target holds top-level <provider> permissions 6476 if (!readMet && pi.readPermission != null && considerUidPermissions 6477 && (pm.checkUidPermission(pi.readPermission, uid) == PERMISSION_GRANTED)) { 6478 readMet = true; 6479 } 6480 if (!writeMet && pi.writePermission != null && considerUidPermissions 6481 && (pm.checkUidPermission(pi.writePermission, uid) == PERMISSION_GRANTED)) { 6482 writeMet = true; 6483 } 6484 6485 // track if unprotected read/write is allowed; any denied 6486 // <path-permission> below removes this ability 6487 boolean allowDefaultRead = pi.readPermission == null; 6488 boolean allowDefaultWrite = pi.writePermission == null; 6489 6490 // check if target holds any <path-permission> that match uri 6491 final PathPermission[] pps = pi.pathPermissions; 6492 if (pps != null) { 6493 final String path = grantUri.uri.getPath(); 6494 int i = pps.length; 6495 while (i > 0 && (!readMet || !writeMet)) { 6496 i--; 6497 PathPermission pp = pps[i]; 6498 if (pp.match(path)) { 6499 if (!readMet) { 6500 final String pprperm = pp.getReadPermission(); 6501 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking read perm for " 6502 + pprperm + " for " + pp.getPath() 6503 + ": match=" + pp.match(path) 6504 + " check=" + pm.checkUidPermission(pprperm, uid)); 6505 if (pprperm != null) { 6506 if (considerUidPermissions && pm.checkUidPermission(pprperm, uid) 6507 == PERMISSION_GRANTED) { 6508 readMet = true; 6509 } else { 6510 allowDefaultRead = false; 6511 } 6512 } 6513 } 6514 if (!writeMet) { 6515 final String ppwperm = pp.getWritePermission(); 6516 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking write perm " 6517 + ppwperm + " for " + pp.getPath() 6518 + ": match=" + pp.match(path) 6519 + " check=" + pm.checkUidPermission(ppwperm, uid)); 6520 if (ppwperm != null) { 6521 if (considerUidPermissions && pm.checkUidPermission(ppwperm, uid) 6522 == PERMISSION_GRANTED) { 6523 writeMet = true; 6524 } else { 6525 allowDefaultWrite = false; 6526 } 6527 } 6528 } 6529 } 6530 } 6531 } 6532 6533 // grant unprotected <provider> read/write, if not blocked by 6534 // <path-permission> above 6535 if (allowDefaultRead) readMet = true; 6536 if (allowDefaultWrite) writeMet = true; 6537 6538 } catch (RemoteException e) { 6539 return false; 6540 } 6541 6542 return readMet && writeMet; 6543 } 6544 6545 private ProviderInfo getProviderInfoLocked(String authority, int userHandle) { 6546 ProviderInfo pi = null; 6547 ContentProviderRecord cpr = mProviderMap.getProviderByName(authority, userHandle); 6548 if (cpr != null) { 6549 pi = cpr.info; 6550 } else { 6551 try { 6552 pi = AppGlobals.getPackageManager().resolveContentProvider( 6553 authority, PackageManager.GET_URI_PERMISSION_PATTERNS, userHandle); 6554 } catch (RemoteException ex) { 6555 } 6556 } 6557 return pi; 6558 } 6559 6560 private UriPermission findUriPermissionLocked(int targetUid, GrantUri grantUri) { 6561 final ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6562 if (targetUris != null) { 6563 return targetUris.get(grantUri); 6564 } 6565 return null; 6566 } 6567 6568 private UriPermission findOrCreateUriPermissionLocked(String sourcePkg, 6569 String targetPkg, int targetUid, GrantUri grantUri) { 6570 ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6571 if (targetUris == null) { 6572 targetUris = Maps.newArrayMap(); 6573 mGrantedUriPermissions.put(targetUid, targetUris); 6574 } 6575 6576 UriPermission perm = targetUris.get(grantUri); 6577 if (perm == null) { 6578 perm = new UriPermission(sourcePkg, targetPkg, targetUid, grantUri); 6579 targetUris.put(grantUri, perm); 6580 } 6581 6582 return perm; 6583 } 6584 6585 private final boolean checkUriPermissionLocked(GrantUri grantUri, int uid, 6586 final int modeFlags) { 6587 final boolean persistable = (modeFlags & Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION) != 0; 6588 final int minStrength = persistable ? UriPermission.STRENGTH_PERSISTABLE 6589 : UriPermission.STRENGTH_OWNED; 6590 6591 // Root gets to do everything. 6592 if (uid == 0) { 6593 return true; 6594 } 6595 6596 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 6597 if (perms == null) return false; 6598 6599 // First look for exact match 6600 final UriPermission exactPerm = perms.get(grantUri); 6601 if (exactPerm != null && exactPerm.getStrength(modeFlags) >= minStrength) { 6602 return true; 6603 } 6604 6605 // No exact match, look for prefixes 6606 final int N = perms.size(); 6607 for (int i = 0; i < N; i++) { 6608 final UriPermission perm = perms.valueAt(i); 6609 if (perm.uri.prefix && grantUri.uri.isPathPrefixMatch(perm.uri.uri) 6610 && perm.getStrength(modeFlags) >= minStrength) { 6611 return true; 6612 } 6613 } 6614 6615 return false; 6616 } 6617 6618 /** 6619 * @param uri This uri must NOT contain an embedded userId. 6620 * @param userId The userId in which the uri is to be resolved. 6621 */ 6622 @Override 6623 public int checkUriPermission(Uri uri, int pid, int uid, 6624 final int modeFlags, int userId) { 6625 enforceNotIsolatedCaller("checkUriPermission"); 6626 6627 // Another redirected-binder-call permissions check as in 6628 // {@link checkComponentPermission}. 6629 Identity tlsIdentity = sCallerIdentity.get(); 6630 if (tlsIdentity != null) { 6631 uid = tlsIdentity.uid; 6632 pid = tlsIdentity.pid; 6633 } 6634 6635 // Our own process gets to do everything. 6636 if (pid == MY_PID) { 6637 return PackageManager.PERMISSION_GRANTED; 6638 } 6639 synchronized (this) { 6640 return checkUriPermissionLocked(new GrantUri(userId, uri, false), uid, modeFlags) 6641 ? PackageManager.PERMISSION_GRANTED 6642 : PackageManager.PERMISSION_DENIED; 6643 } 6644 } 6645 6646 /** 6647 * Check if the targetPkg can be granted permission to access uri by 6648 * the callingUid using the given modeFlags. Throws a security exception 6649 * if callingUid is not allowed to do this. Returns the uid of the target 6650 * if the URI permission grant should be performed; returns -1 if it is not 6651 * needed (for example targetPkg already has permission to access the URI). 6652 * If you already know the uid of the target, you can supply it in 6653 * lastTargetUid else set that to -1. 6654 */ 6655 int checkGrantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 6656 final int modeFlags, int lastTargetUid) { 6657 if (!Intent.isAccessUriMode(modeFlags)) { 6658 return -1; 6659 } 6660 6661 if (targetPkg != null) { 6662 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6663 "Checking grant " + targetPkg + " permission to " + grantUri); 6664 } 6665 6666 final IPackageManager pm = AppGlobals.getPackageManager(); 6667 6668 // If this is not a content: uri, we can't do anything with it. 6669 if (!ContentResolver.SCHEME_CONTENT.equals(grantUri.uri.getScheme())) { 6670 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6671 "Can't grant URI permission for non-content URI: " + grantUri); 6672 return -1; 6673 } 6674 6675 final String authority = grantUri.uri.getAuthority(); 6676 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6677 if (pi == null) { 6678 Slog.w(TAG, "No content provider found for permission check: " + 6679 grantUri.uri.toSafeString()); 6680 return -1; 6681 } 6682 6683 int targetUid = lastTargetUid; 6684 if (targetUid < 0 && targetPkg != null) { 6685 try { 6686 targetUid = pm.getPackageUid(targetPkg, UserHandle.getUserId(callingUid)); 6687 if (targetUid < 0) { 6688 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6689 "Can't grant URI permission no uid for: " + targetPkg); 6690 return -1; 6691 } 6692 } catch (RemoteException ex) { 6693 return -1; 6694 } 6695 } 6696 6697 if (targetUid >= 0) { 6698 // First... does the target actually need this permission? 6699 if (checkHoldingPermissionsLocked(pm, pi, grantUri, targetUid, modeFlags)) { 6700 // No need to grant the target this permission. 6701 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6702 "Target " + targetPkg + " already has full permission to " + grantUri); 6703 return -1; 6704 } 6705 } else { 6706 // First... there is no target package, so can anyone access it? 6707 boolean allowed = pi.exported; 6708 if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) { 6709 if (pi.readPermission != null) { 6710 allowed = false; 6711 } 6712 } 6713 if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) { 6714 if (pi.writePermission != null) { 6715 allowed = false; 6716 } 6717 } 6718 if (allowed) { 6719 return -1; 6720 } 6721 } 6722 6723 /* There is a special cross user grant if: 6724 * - The target is on another user. 6725 * - Apps on the current user can access the uri without any uid permissions. 6726 * In this case, we grant a uri permission, even if the ContentProvider does not normally 6727 * grant uri permissions. 6728 */ 6729 boolean specialCrossUserGrant = UserHandle.getUserId(targetUid) != grantUri.sourceUserId 6730 && checkHoldingPermissionsInternalLocked(pm, pi, grantUri, callingUid, 6731 modeFlags, false /*without considering the uid permissions*/); 6732 6733 // Second... is the provider allowing granting of URI permissions? 6734 if (!specialCrossUserGrant) { 6735 if (!pi.grantUriPermissions) { 6736 throw new SecurityException("Provider " + pi.packageName 6737 + "/" + pi.name 6738 + " does not allow granting of Uri permissions (uri " 6739 + grantUri + ")"); 6740 } 6741 if (pi.uriPermissionPatterns != null) { 6742 final int N = pi.uriPermissionPatterns.length; 6743 boolean allowed = false; 6744 for (int i=0; i<N; i++) { 6745 if (pi.uriPermissionPatterns[i] != null 6746 && pi.uriPermissionPatterns[i].match(grantUri.uri.getPath())) { 6747 allowed = true; 6748 break; 6749 } 6750 } 6751 if (!allowed) { 6752 throw new SecurityException("Provider " + pi.packageName 6753 + "/" + pi.name 6754 + " does not allow granting of permission to path of Uri " 6755 + grantUri); 6756 } 6757 } 6758 } 6759 6760 // Third... does the caller itself have permission to access 6761 // this uri? 6762 if (UserHandle.getAppId(callingUid) != Process.SYSTEM_UID) { 6763 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 6764 // Require they hold a strong enough Uri permission 6765 if (!checkUriPermissionLocked(grantUri, callingUid, modeFlags)) { 6766 throw new SecurityException("Uid " + callingUid 6767 + " does not have permission to uri " + grantUri); 6768 } 6769 } 6770 } 6771 return targetUid; 6772 } 6773 6774 /** 6775 * @param uri This uri must NOT contain an embedded userId. 6776 * @param userId The userId in which the uri is to be resolved. 6777 */ 6778 @Override 6779 public int checkGrantUriPermission(int callingUid, String targetPkg, Uri uri, 6780 final int modeFlags, int userId) { 6781 enforceNotIsolatedCaller("checkGrantUriPermission"); 6782 synchronized(this) { 6783 return checkGrantUriPermissionLocked(callingUid, targetPkg, 6784 new GrantUri(userId, uri, false), modeFlags, -1); 6785 } 6786 } 6787 6788 void grantUriPermissionUncheckedLocked(int targetUid, String targetPkg, GrantUri grantUri, 6789 final int modeFlags, UriPermissionOwner owner) { 6790 if (!Intent.isAccessUriMode(modeFlags)) { 6791 return; 6792 } 6793 6794 // So here we are: the caller has the assumed permission 6795 // to the uri, and the target doesn't. Let's now give this to 6796 // the target. 6797 6798 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6799 "Granting " + targetPkg + "/" + targetUid + " permission to " + grantUri); 6800 6801 final String authority = grantUri.uri.getAuthority(); 6802 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6803 if (pi == null) { 6804 Slog.w(TAG, "No content provider found for grant: " + grantUri.toSafeString()); 6805 return; 6806 } 6807 6808 if ((modeFlags & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0) { 6809 grantUri.prefix = true; 6810 } 6811 final UriPermission perm = findOrCreateUriPermissionLocked( 6812 pi.packageName, targetPkg, targetUid, grantUri); 6813 perm.grantModes(modeFlags, owner); 6814 } 6815 6816 void grantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 6817 final int modeFlags, UriPermissionOwner owner, int targetUserId) { 6818 if (targetPkg == null) { 6819 throw new NullPointerException("targetPkg"); 6820 } 6821 int targetUid; 6822 final IPackageManager pm = AppGlobals.getPackageManager(); 6823 try { 6824 targetUid = pm.getPackageUid(targetPkg, targetUserId); 6825 } catch (RemoteException ex) { 6826 return; 6827 } 6828 6829 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, modeFlags, 6830 targetUid); 6831 if (targetUid < 0) { 6832 return; 6833 } 6834 6835 grantUriPermissionUncheckedLocked(targetUid, targetPkg, grantUri, modeFlags, 6836 owner); 6837 } 6838 6839 static class NeededUriGrants extends ArrayList<GrantUri> { 6840 final String targetPkg; 6841 final int targetUid; 6842 final int flags; 6843 6844 NeededUriGrants(String targetPkg, int targetUid, int flags) { 6845 this.targetPkg = targetPkg; 6846 this.targetUid = targetUid; 6847 this.flags = flags; 6848 } 6849 } 6850 6851 /** 6852 * Like checkGrantUriPermissionLocked, but takes an Intent. 6853 */ 6854 NeededUriGrants checkGrantUriPermissionFromIntentLocked(int callingUid, 6855 String targetPkg, Intent intent, int mode, NeededUriGrants needed, int targetUserId) { 6856 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6857 "Checking URI perm to data=" + (intent != null ? intent.getData() : null) 6858 + " clip=" + (intent != null ? intent.getClipData() : null) 6859 + " from " + intent + "; flags=0x" 6860 + Integer.toHexString(intent != null ? intent.getFlags() : 0)); 6861 6862 if (targetPkg == null) { 6863 throw new NullPointerException("targetPkg"); 6864 } 6865 6866 if (intent == null) { 6867 return null; 6868 } 6869 Uri data = intent.getData(); 6870 ClipData clip = intent.getClipData(); 6871 if (data == null && clip == null) { 6872 return null; 6873 } 6874 // Default userId for uris in the intent (if they don't specify it themselves) 6875 int contentUserHint = intent.getContentUserHint(); 6876 if (contentUserHint == UserHandle.USER_CURRENT) { 6877 contentUserHint = UserHandle.getUserId(callingUid); 6878 } 6879 final IPackageManager pm = AppGlobals.getPackageManager(); 6880 int targetUid; 6881 if (needed != null) { 6882 targetUid = needed.targetUid; 6883 } else { 6884 try { 6885 targetUid = pm.getPackageUid(targetPkg, targetUserId); 6886 } catch (RemoteException ex) { 6887 return null; 6888 } 6889 if (targetUid < 0) { 6890 if (DEBUG_URI_PERMISSION) { 6891 Slog.v(TAG, "Can't grant URI permission no uid for: " + targetPkg 6892 + " on user " + targetUserId); 6893 } 6894 return null; 6895 } 6896 } 6897 if (data != null) { 6898 GrantUri grantUri = GrantUri.resolve(contentUserHint, data); 6899 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 6900 targetUid); 6901 if (targetUid > 0) { 6902 if (needed == null) { 6903 needed = new NeededUriGrants(targetPkg, targetUid, mode); 6904 } 6905 needed.add(grantUri); 6906 } 6907 } 6908 if (clip != null) { 6909 for (int i=0; i<clip.getItemCount(); i++) { 6910 Uri uri = clip.getItemAt(i).getUri(); 6911 if (uri != null) { 6912 GrantUri grantUri = GrantUri.resolve(contentUserHint, uri); 6913 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 6914 targetUid); 6915 if (targetUid > 0) { 6916 if (needed == null) { 6917 needed = new NeededUriGrants(targetPkg, targetUid, mode); 6918 } 6919 needed.add(grantUri); 6920 } 6921 } else { 6922 Intent clipIntent = clip.getItemAt(i).getIntent(); 6923 if (clipIntent != null) { 6924 NeededUriGrants newNeeded = checkGrantUriPermissionFromIntentLocked( 6925 callingUid, targetPkg, clipIntent, mode, needed, targetUserId); 6926 if (newNeeded != null) { 6927 needed = newNeeded; 6928 } 6929 } 6930 } 6931 } 6932 } 6933 6934 return needed; 6935 } 6936 6937 /** 6938 * Like grantUriPermissionUncheckedLocked, but takes an Intent. 6939 */ 6940 void grantUriPermissionUncheckedFromIntentLocked(NeededUriGrants needed, 6941 UriPermissionOwner owner) { 6942 if (needed != null) { 6943 for (int i=0; i<needed.size(); i++) { 6944 GrantUri grantUri = needed.get(i); 6945 grantUriPermissionUncheckedLocked(needed.targetUid, needed.targetPkg, 6946 grantUri, needed.flags, owner); 6947 } 6948 } 6949 } 6950 6951 void grantUriPermissionFromIntentLocked(int callingUid, 6952 String targetPkg, Intent intent, UriPermissionOwner owner, int targetUserId) { 6953 NeededUriGrants needed = checkGrantUriPermissionFromIntentLocked(callingUid, targetPkg, 6954 intent, intent != null ? intent.getFlags() : 0, null, targetUserId); 6955 if (needed == null) { 6956 return; 6957 } 6958 6959 grantUriPermissionUncheckedFromIntentLocked(needed, owner); 6960 } 6961 6962 /** 6963 * @param uri This uri must NOT contain an embedded userId. 6964 * @param userId The userId in which the uri is to be resolved. 6965 */ 6966 @Override 6967 public void grantUriPermission(IApplicationThread caller, String targetPkg, Uri uri, 6968 final int modeFlags, int userId) { 6969 enforceNotIsolatedCaller("grantUriPermission"); 6970 GrantUri grantUri = new GrantUri(userId, uri, false); 6971 synchronized(this) { 6972 final ProcessRecord r = getRecordForAppLocked(caller); 6973 if (r == null) { 6974 throw new SecurityException("Unable to find app for caller " 6975 + caller 6976 + " when granting permission to uri " + grantUri); 6977 } 6978 if (targetPkg == null) { 6979 throw new IllegalArgumentException("null target"); 6980 } 6981 if (grantUri == null) { 6982 throw new IllegalArgumentException("null uri"); 6983 } 6984 6985 Preconditions.checkFlagsArgument(modeFlags, Intent.FLAG_GRANT_READ_URI_PERMISSION 6986 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION 6987 | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION 6988 | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION); 6989 6990 grantUriPermissionLocked(r.uid, targetPkg, grantUri, modeFlags, null, 6991 UserHandle.getUserId(r.uid)); 6992 } 6993 } 6994 6995 void removeUriPermissionIfNeededLocked(UriPermission perm) { 6996 if (perm.modeFlags == 0) { 6997 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 6998 perm.targetUid); 6999 if (perms != null) { 7000 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7001 "Removing " + perm.targetUid + " permission to " + perm.uri); 7002 7003 perms.remove(perm.uri); 7004 if (perms.isEmpty()) { 7005 mGrantedUriPermissions.remove(perm.targetUid); 7006 } 7007 } 7008 } 7009 } 7010 7011 private void revokeUriPermissionLocked(int callingUid, GrantUri grantUri, final int modeFlags) { 7012 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Revoking all granted permissions to " + grantUri); 7013 7014 final IPackageManager pm = AppGlobals.getPackageManager(); 7015 final String authority = grantUri.uri.getAuthority(); 7016 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 7017 if (pi == null) { 7018 Slog.w(TAG, "No content provider found for permission revoke: " 7019 + grantUri.toSafeString()); 7020 return; 7021 } 7022 7023 // Does the caller have this permission on the URI? 7024 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 7025 // Right now, if you are not the original owner of the permission, 7026 // you are not allowed to revoke it. 7027 //if (!checkUriPermissionLocked(uri, callingUid, modeFlags)) { 7028 throw new SecurityException("Uid " + callingUid 7029 + " does not have permission to uri " + grantUri); 7030 //} 7031 } 7032 7033 boolean persistChanged = false; 7034 7035 // Go through all of the permissions and remove any that match. 7036 int N = mGrantedUriPermissions.size(); 7037 for (int i = 0; i < N; i++) { 7038 final int targetUid = mGrantedUriPermissions.keyAt(i); 7039 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 7040 7041 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 7042 final UriPermission perm = it.next(); 7043 if (perm.uri.sourceUserId == grantUri.sourceUserId 7044 && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) { 7045 if (DEBUG_URI_PERMISSION) 7046 Slog.v(TAG, 7047 "Revoking " + perm.targetUid + " permission to " + perm.uri); 7048 persistChanged |= perm.revokeModes( 7049 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 7050 if (perm.modeFlags == 0) { 7051 it.remove(); 7052 } 7053 } 7054 } 7055 7056 if (perms.isEmpty()) { 7057 mGrantedUriPermissions.remove(targetUid); 7058 N--; 7059 i--; 7060 } 7061 } 7062 7063 if (persistChanged) { 7064 schedulePersistUriGrants(); 7065 } 7066 } 7067 7068 /** 7069 * @param uri This uri must NOT contain an embedded userId. 7070 * @param userId The userId in which the uri is to be resolved. 7071 */ 7072 @Override 7073 public void revokeUriPermission(IApplicationThread caller, Uri uri, final int modeFlags, 7074 int userId) { 7075 enforceNotIsolatedCaller("revokeUriPermission"); 7076 synchronized(this) { 7077 final ProcessRecord r = getRecordForAppLocked(caller); 7078 if (r == null) { 7079 throw new SecurityException("Unable to find app for caller " 7080 + caller 7081 + " when revoking permission to uri " + uri); 7082 } 7083 if (uri == null) { 7084 Slog.w(TAG, "revokeUriPermission: null uri"); 7085 return; 7086 } 7087 7088 if (!Intent.isAccessUriMode(modeFlags)) { 7089 return; 7090 } 7091 7092 final IPackageManager pm = AppGlobals.getPackageManager(); 7093 final String authority = uri.getAuthority(); 7094 final ProviderInfo pi = getProviderInfoLocked(authority, userId); 7095 if (pi == null) { 7096 Slog.w(TAG, "No content provider found for permission revoke: " 7097 + uri.toSafeString()); 7098 return; 7099 } 7100 7101 revokeUriPermissionLocked(r.uid, new GrantUri(userId, uri, false), modeFlags); 7102 } 7103 } 7104 7105 /** 7106 * Remove any {@link UriPermission} granted <em>from</em> or <em>to</em> the 7107 * given package. 7108 * 7109 * @param packageName Package name to match, or {@code null} to apply to all 7110 * packages. 7111 * @param userHandle User to match, or {@link UserHandle#USER_ALL} to apply 7112 * to all users. 7113 * @param persistable If persistable grants should be removed. 7114 */ 7115 private void removeUriPermissionsForPackageLocked( 7116 String packageName, int userHandle, boolean persistable) { 7117 if (userHandle == UserHandle.USER_ALL && packageName == null) { 7118 throw new IllegalArgumentException("Must narrow by either package or user"); 7119 } 7120 7121 boolean persistChanged = false; 7122 7123 int N = mGrantedUriPermissions.size(); 7124 for (int i = 0; i < N; i++) { 7125 final int targetUid = mGrantedUriPermissions.keyAt(i); 7126 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 7127 7128 // Only inspect grants matching user 7129 if (userHandle == UserHandle.USER_ALL 7130 || userHandle == UserHandle.getUserId(targetUid)) { 7131 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 7132 final UriPermission perm = it.next(); 7133 7134 // Only inspect grants matching package 7135 if (packageName == null || perm.sourcePkg.equals(packageName) 7136 || perm.targetPkg.equals(packageName)) { 7137 persistChanged |= perm.revokeModes( 7138 persistable ? ~0 : ~Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 7139 7140 // Only remove when no modes remain; any persisted grants 7141 // will keep this alive. 7142 if (perm.modeFlags == 0) { 7143 it.remove(); 7144 } 7145 } 7146 } 7147 7148 if (perms.isEmpty()) { 7149 mGrantedUriPermissions.remove(targetUid); 7150 N--; 7151 i--; 7152 } 7153 } 7154 } 7155 7156 if (persistChanged) { 7157 schedulePersistUriGrants(); 7158 } 7159 } 7160 7161 @Override 7162 public IBinder newUriPermissionOwner(String name) { 7163 enforceNotIsolatedCaller("newUriPermissionOwner"); 7164 synchronized(this) { 7165 UriPermissionOwner owner = new UriPermissionOwner(this, name); 7166 return owner.getExternalTokenLocked(); 7167 } 7168 } 7169 7170 /** 7171 * @param uri This uri must NOT contain an embedded userId. 7172 * @param sourceUserId The userId in which the uri is to be resolved. 7173 * @param targetUserId The userId of the app that receives the grant. 7174 */ 7175 @Override 7176 public void grantUriPermissionFromOwner(IBinder token, int fromUid, String targetPkg, Uri uri, 7177 final int modeFlags, int sourceUserId, int targetUserId) { 7178 targetUserId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 7179 targetUserId, false, ALLOW_FULL_ONLY, "grantUriPermissionFromOwner", null); 7180 synchronized(this) { 7181 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 7182 if (owner == null) { 7183 throw new IllegalArgumentException("Unknown owner: " + token); 7184 } 7185 if (fromUid != Binder.getCallingUid()) { 7186 if (Binder.getCallingUid() != Process.myUid()) { 7187 // Only system code can grant URI permissions on behalf 7188 // of other users. 7189 throw new SecurityException("nice try"); 7190 } 7191 } 7192 if (targetPkg == null) { 7193 throw new IllegalArgumentException("null target"); 7194 } 7195 if (uri == null) { 7196 throw new IllegalArgumentException("null uri"); 7197 } 7198 7199 grantUriPermissionLocked(fromUid, targetPkg, new GrantUri(sourceUserId, uri, false), 7200 modeFlags, owner, targetUserId); 7201 } 7202 } 7203 7204 /** 7205 * @param uri This uri must NOT contain an embedded userId. 7206 * @param userId The userId in which the uri is to be resolved. 7207 */ 7208 @Override 7209 public void revokeUriPermissionFromOwner(IBinder token, Uri uri, int mode, int userId) { 7210 synchronized(this) { 7211 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 7212 if (owner == null) { 7213 throw new IllegalArgumentException("Unknown owner: " + token); 7214 } 7215 7216 if (uri == null) { 7217 owner.removeUriPermissionsLocked(mode); 7218 } else { 7219 owner.removeUriPermissionLocked(new GrantUri(userId, uri, false), mode); 7220 } 7221 } 7222 } 7223 7224 private void schedulePersistUriGrants() { 7225 if (!mHandler.hasMessages(PERSIST_URI_GRANTS_MSG)) { 7226 mHandler.sendMessageDelayed(mHandler.obtainMessage(PERSIST_URI_GRANTS_MSG), 7227 10 * DateUtils.SECOND_IN_MILLIS); 7228 } 7229 } 7230 7231 private void writeGrantedUriPermissions() { 7232 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "writeGrantedUriPermissions()"); 7233 7234 // Snapshot permissions so we can persist without lock 7235 ArrayList<UriPermission.Snapshot> persist = Lists.newArrayList(); 7236 synchronized (this) { 7237 final int size = mGrantedUriPermissions.size(); 7238 for (int i = 0; i < size; i++) { 7239 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 7240 for (UriPermission perm : perms.values()) { 7241 if (perm.persistedModeFlags != 0) { 7242 persist.add(perm.snapshot()); 7243 } 7244 } 7245 } 7246 } 7247 7248 FileOutputStream fos = null; 7249 try { 7250 fos = mGrantFile.startWrite(); 7251 7252 XmlSerializer out = new FastXmlSerializer(); 7253 out.setOutput(fos, "utf-8"); 7254 out.startDocument(null, true); 7255 out.startTag(null, TAG_URI_GRANTS); 7256 for (UriPermission.Snapshot perm : persist) { 7257 out.startTag(null, TAG_URI_GRANT); 7258 writeIntAttribute(out, ATTR_SOURCE_USER_ID, perm.uri.sourceUserId); 7259 writeIntAttribute(out, ATTR_TARGET_USER_ID, perm.targetUserId); 7260 out.attribute(null, ATTR_SOURCE_PKG, perm.sourcePkg); 7261 out.attribute(null, ATTR_TARGET_PKG, perm.targetPkg); 7262 out.attribute(null, ATTR_URI, String.valueOf(perm.uri.uri)); 7263 writeBooleanAttribute(out, ATTR_PREFIX, perm.uri.prefix); 7264 writeIntAttribute(out, ATTR_MODE_FLAGS, perm.persistedModeFlags); 7265 writeLongAttribute(out, ATTR_CREATED_TIME, perm.persistedCreateTime); 7266 out.endTag(null, TAG_URI_GRANT); 7267 } 7268 out.endTag(null, TAG_URI_GRANTS); 7269 out.endDocument(); 7270 7271 mGrantFile.finishWrite(fos); 7272 } catch (IOException e) { 7273 if (fos != null) { 7274 mGrantFile.failWrite(fos); 7275 } 7276 } 7277 } 7278 7279 private void readGrantedUriPermissionsLocked() { 7280 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "readGrantedUriPermissions()"); 7281 7282 final long now = System.currentTimeMillis(); 7283 7284 FileInputStream fis = null; 7285 try { 7286 fis = mGrantFile.openRead(); 7287 final XmlPullParser in = Xml.newPullParser(); 7288 in.setInput(fis, null); 7289 7290 int type; 7291 while ((type = in.next()) != END_DOCUMENT) { 7292 final String tag = in.getName(); 7293 if (type == START_TAG) { 7294 if (TAG_URI_GRANT.equals(tag)) { 7295 final int sourceUserId; 7296 final int targetUserId; 7297 final int userHandle = readIntAttribute(in, 7298 ATTR_USER_HANDLE, UserHandle.USER_NULL); 7299 if (userHandle != UserHandle.USER_NULL) { 7300 // For backwards compatibility. 7301 sourceUserId = userHandle; 7302 targetUserId = userHandle; 7303 } else { 7304 sourceUserId = readIntAttribute(in, ATTR_SOURCE_USER_ID); 7305 targetUserId = readIntAttribute(in, ATTR_TARGET_USER_ID); 7306 } 7307 final String sourcePkg = in.getAttributeValue(null, ATTR_SOURCE_PKG); 7308 final String targetPkg = in.getAttributeValue(null, ATTR_TARGET_PKG); 7309 final Uri uri = Uri.parse(in.getAttributeValue(null, ATTR_URI)); 7310 final boolean prefix = readBooleanAttribute(in, ATTR_PREFIX); 7311 final int modeFlags = readIntAttribute(in, ATTR_MODE_FLAGS); 7312 final long createdTime = readLongAttribute(in, ATTR_CREATED_TIME, now); 7313 7314 // Sanity check that provider still belongs to source package 7315 final ProviderInfo pi = getProviderInfoLocked( 7316 uri.getAuthority(), sourceUserId); 7317 if (pi != null && sourcePkg.equals(pi.packageName)) { 7318 int targetUid = -1; 7319 try { 7320 targetUid = AppGlobals.getPackageManager() 7321 .getPackageUid(targetPkg, targetUserId); 7322 } catch (RemoteException e) { 7323 } 7324 if (targetUid != -1) { 7325 final UriPermission perm = findOrCreateUriPermissionLocked( 7326 sourcePkg, targetPkg, targetUid, 7327 new GrantUri(sourceUserId, uri, prefix)); 7328 perm.initPersistedModes(modeFlags, createdTime); 7329 } 7330 } else { 7331 Slog.w(TAG, "Persisted grant for " + uri + " had source " + sourcePkg 7332 + " but instead found " + pi); 7333 } 7334 } 7335 } 7336 } 7337 } catch (FileNotFoundException e) { 7338 // Missing grants is okay 7339 } catch (IOException e) { 7340 Log.wtf(TAG, "Failed reading Uri grants", e); 7341 } catch (XmlPullParserException e) { 7342 Log.wtf(TAG, "Failed reading Uri grants", e); 7343 } finally { 7344 IoUtils.closeQuietly(fis); 7345 } 7346 } 7347 7348 /** 7349 * @param uri This uri must NOT contain an embedded userId. 7350 * @param userId The userId in which the uri is to be resolved. 7351 */ 7352 @Override 7353 public void takePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 7354 enforceNotIsolatedCaller("takePersistableUriPermission"); 7355 7356 Preconditions.checkFlagsArgument(modeFlags, 7357 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 7358 7359 synchronized (this) { 7360 final int callingUid = Binder.getCallingUid(); 7361 boolean persistChanged = false; 7362 GrantUri grantUri = new GrantUri(userId, uri, false); 7363 7364 UriPermission exactPerm = findUriPermissionLocked(callingUid, 7365 new GrantUri(userId, uri, false)); 7366 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 7367 new GrantUri(userId, uri, true)); 7368 7369 final boolean exactValid = (exactPerm != null) 7370 && ((modeFlags & exactPerm.persistableModeFlags) == modeFlags); 7371 final boolean prefixValid = (prefixPerm != null) 7372 && ((modeFlags & prefixPerm.persistableModeFlags) == modeFlags); 7373 7374 if (!(exactValid || prefixValid)) { 7375 throw new SecurityException("No persistable permission grants found for UID " 7376 + callingUid + " and Uri " + grantUri.toSafeString()); 7377 } 7378 7379 if (exactValid) { 7380 persistChanged |= exactPerm.takePersistableModes(modeFlags); 7381 } 7382 if (prefixValid) { 7383 persistChanged |= prefixPerm.takePersistableModes(modeFlags); 7384 } 7385 7386 persistChanged |= maybePrunePersistedUriGrantsLocked(callingUid); 7387 7388 if (persistChanged) { 7389 schedulePersistUriGrants(); 7390 } 7391 } 7392 } 7393 7394 /** 7395 * @param uri This uri must NOT contain an embedded userId. 7396 * @param userId The userId in which the uri is to be resolved. 7397 */ 7398 @Override 7399 public void releasePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 7400 enforceNotIsolatedCaller("releasePersistableUriPermission"); 7401 7402 Preconditions.checkFlagsArgument(modeFlags, 7403 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 7404 7405 synchronized (this) { 7406 final int callingUid = Binder.getCallingUid(); 7407 boolean persistChanged = false; 7408 7409 UriPermission exactPerm = findUriPermissionLocked(callingUid, 7410 new GrantUri(userId, uri, false)); 7411 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 7412 new GrantUri(userId, uri, true)); 7413 if (exactPerm == null && prefixPerm == null) { 7414 throw new SecurityException("No permission grants found for UID " + callingUid 7415 + " and Uri " + uri.toSafeString()); 7416 } 7417 7418 if (exactPerm != null) { 7419 persistChanged |= exactPerm.releasePersistableModes(modeFlags); 7420 removeUriPermissionIfNeededLocked(exactPerm); 7421 } 7422 if (prefixPerm != null) { 7423 persistChanged |= prefixPerm.releasePersistableModes(modeFlags); 7424 removeUriPermissionIfNeededLocked(prefixPerm); 7425 } 7426 7427 if (persistChanged) { 7428 schedulePersistUriGrants(); 7429 } 7430 } 7431 } 7432 7433 /** 7434 * Prune any older {@link UriPermission} for the given UID until outstanding 7435 * persisted grants are below {@link #MAX_PERSISTED_URI_GRANTS}. 7436 * 7437 * @return if any mutations occured that require persisting. 7438 */ 7439 private boolean maybePrunePersistedUriGrantsLocked(int uid) { 7440 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 7441 if (perms == null) return false; 7442 if (perms.size() < MAX_PERSISTED_URI_GRANTS) return false; 7443 7444 final ArrayList<UriPermission> persisted = Lists.newArrayList(); 7445 for (UriPermission perm : perms.values()) { 7446 if (perm.persistedModeFlags != 0) { 7447 persisted.add(perm); 7448 } 7449 } 7450 7451 final int trimCount = persisted.size() - MAX_PERSISTED_URI_GRANTS; 7452 if (trimCount <= 0) return false; 7453 7454 Collections.sort(persisted, new UriPermission.PersistedTimeComparator()); 7455 for (int i = 0; i < trimCount; i++) { 7456 final UriPermission perm = persisted.get(i); 7457 7458 if (DEBUG_URI_PERMISSION) { 7459 Slog.v(TAG, "Trimming grant created at " + perm.persistedCreateTime); 7460 } 7461 7462 perm.releasePersistableModes(~0); 7463 removeUriPermissionIfNeededLocked(perm); 7464 } 7465 7466 return true; 7467 } 7468 7469 @Override 7470 public ParceledListSlice<android.content.UriPermission> getPersistedUriPermissions( 7471 String packageName, boolean incoming) { 7472 enforceNotIsolatedCaller("getPersistedUriPermissions"); 7473 Preconditions.checkNotNull(packageName, "packageName"); 7474 7475 final int callingUid = Binder.getCallingUid(); 7476 final IPackageManager pm = AppGlobals.getPackageManager(); 7477 try { 7478 final int packageUid = pm.getPackageUid(packageName, UserHandle.getUserId(callingUid)); 7479 if (packageUid != callingUid) { 7480 throw new SecurityException( 7481 "Package " + packageName + " does not belong to calling UID " + callingUid); 7482 } 7483 } catch (RemoteException e) { 7484 throw new SecurityException("Failed to verify package name ownership"); 7485 } 7486 7487 final ArrayList<android.content.UriPermission> result = Lists.newArrayList(); 7488 synchronized (this) { 7489 if (incoming) { 7490 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 7491 callingUid); 7492 if (perms == null) { 7493 Slog.w(TAG, "No permission grants found for " + packageName); 7494 } else { 7495 for (UriPermission perm : perms.values()) { 7496 if (packageName.equals(perm.targetPkg) && perm.persistedModeFlags != 0) { 7497 result.add(perm.buildPersistedPublicApiObject()); 7498 } 7499 } 7500 } 7501 } else { 7502 final int size = mGrantedUriPermissions.size(); 7503 for (int i = 0; i < size; i++) { 7504 final ArrayMap<GrantUri, UriPermission> perms = 7505 mGrantedUriPermissions.valueAt(i); 7506 for (UriPermission perm : perms.values()) { 7507 if (packageName.equals(perm.sourcePkg) && perm.persistedModeFlags != 0) { 7508 result.add(perm.buildPersistedPublicApiObject()); 7509 } 7510 } 7511 } 7512 } 7513 } 7514 return new ParceledListSlice<android.content.UriPermission>(result); 7515 } 7516 7517 @Override 7518 public void showWaitingForDebugger(IApplicationThread who, boolean waiting) { 7519 synchronized (this) { 7520 ProcessRecord app = 7521 who != null ? getRecordForAppLocked(who) : null; 7522 if (app == null) return; 7523 7524 Message msg = Message.obtain(); 7525 msg.what = WAIT_FOR_DEBUGGER_MSG; 7526 msg.obj = app; 7527 msg.arg1 = waiting ? 1 : 0; 7528 mHandler.sendMessage(msg); 7529 } 7530 } 7531 7532 @Override 7533 public void getMemoryInfo(ActivityManager.MemoryInfo outInfo) { 7534 final long homeAppMem = mProcessList.getMemLevel(ProcessList.HOME_APP_ADJ); 7535 final long cachedAppMem = mProcessList.getMemLevel(ProcessList.CACHED_APP_MIN_ADJ); 7536 outInfo.availMem = Process.getFreeMemory(); 7537 outInfo.totalMem = Process.getTotalMemory(); 7538 outInfo.threshold = homeAppMem; 7539 outInfo.lowMemory = outInfo.availMem < (homeAppMem + ((cachedAppMem-homeAppMem)/2)); 7540 outInfo.hiddenAppThreshold = cachedAppMem; 7541 outInfo.secondaryServerThreshold = mProcessList.getMemLevel( 7542 ProcessList.SERVICE_ADJ); 7543 outInfo.visibleAppThreshold = mProcessList.getMemLevel( 7544 ProcessList.VISIBLE_APP_ADJ); 7545 outInfo.foregroundAppThreshold = mProcessList.getMemLevel( 7546 ProcessList.FOREGROUND_APP_ADJ); 7547 } 7548 7549 // ========================================================= 7550 // TASK MANAGEMENT 7551 // ========================================================= 7552 7553 @Override 7554 public List<IAppTask> getAppTasks(String callingPackage) { 7555 int callingUid = Binder.getCallingUid(); 7556 long ident = Binder.clearCallingIdentity(); 7557 7558 synchronized(this) { 7559 ArrayList<IAppTask> list = new ArrayList<IAppTask>(); 7560 try { 7561 if (localLOGV) Slog.v(TAG, "getAppTasks"); 7562 7563 final int N = mRecentTasks.size(); 7564 for (int i = 0; i < N; i++) { 7565 TaskRecord tr = mRecentTasks.get(i); 7566 // Skip tasks that do not match the caller. We don't need to verify 7567 // callingPackage, because we are also limiting to callingUid and know 7568 // that will limit to the correct security sandbox. 7569 if (tr.effectiveUid != callingUid) { 7570 continue; 7571 } 7572 Intent intent = tr.getBaseIntent(); 7573 if (intent == null || 7574 !callingPackage.equals(intent.getComponent().getPackageName())) { 7575 continue; 7576 } 7577 ActivityManager.RecentTaskInfo taskInfo = 7578 createRecentTaskInfoFromTaskRecord(tr); 7579 AppTaskImpl taskImpl = new AppTaskImpl(taskInfo.persistentId, callingUid); 7580 list.add(taskImpl); 7581 } 7582 } finally { 7583 Binder.restoreCallingIdentity(ident); 7584 } 7585 return list; 7586 } 7587 } 7588 7589 @Override 7590 public List<RunningTaskInfo> getTasks(int maxNum, int flags) { 7591 final int callingUid = Binder.getCallingUid(); 7592 ArrayList<RunningTaskInfo> list = new ArrayList<RunningTaskInfo>(); 7593 7594 synchronized(this) { 7595 if (localLOGV) Slog.v( 7596 TAG, "getTasks: max=" + maxNum + ", flags=" + flags); 7597 7598 final boolean allowed = checkCallingPermission( 7599 android.Manifest.permission.GET_TASKS) 7600 == PackageManager.PERMISSION_GRANTED; 7601 if (!allowed) { 7602 Slog.w(TAG, "getTasks: caller " + callingUid 7603 + " does not hold GET_TASKS; limiting output"); 7604 } 7605 7606 // TODO: Improve with MRU list from all ActivityStacks. 7607 mStackSupervisor.getTasksLocked(maxNum, list, callingUid, allowed); 7608 } 7609 7610 return list; 7611 } 7612 7613 TaskRecord getMostRecentTask() { 7614 return mRecentTasks.get(0); 7615 } 7616 7617 /** 7618 * Creates a new RecentTaskInfo from a TaskRecord. 7619 */ 7620 private ActivityManager.RecentTaskInfo createRecentTaskInfoFromTaskRecord(TaskRecord tr) { 7621 // Update the task description to reflect any changes in the task stack 7622 tr.updateTaskDescription(); 7623 7624 // Compose the recent task info 7625 ActivityManager.RecentTaskInfo rti = new ActivityManager.RecentTaskInfo(); 7626 rti.id = tr.getTopActivity() == null ? -1 : tr.taskId; 7627 rti.persistentId = tr.taskId; 7628 rti.baseIntent = new Intent(tr.getBaseIntent()); 7629 rti.origActivity = tr.origActivity; 7630 rti.description = tr.lastDescription; 7631 rti.stackId = tr.stack != null ? tr.stack.mStackId : -1; 7632 rti.userId = tr.userId; 7633 rti.taskDescription = new ActivityManager.TaskDescription(tr.lastTaskDescription); 7634 rti.firstActiveTime = tr.firstActiveTime; 7635 rti.lastActiveTime = tr.lastActiveTime; 7636 rti.affiliatedTaskId = tr.mAffiliatedTaskId; 7637 rti.affiliatedTaskColor = tr.mAffiliatedTaskColor; 7638 return rti; 7639 } 7640 7641 @Override 7642 public List<ActivityManager.RecentTaskInfo> getRecentTasks(int maxNum, int flags, int userId) { 7643 final int callingUid = Binder.getCallingUid(); 7644 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 7645 false, ALLOW_FULL_ONLY, "getRecentTasks", null); 7646 7647 final boolean includeProfiles = (flags & ActivityManager.RECENT_INCLUDE_PROFILES) != 0; 7648 final boolean withExcluded = (flags&ActivityManager.RECENT_WITH_EXCLUDED) != 0; 7649 synchronized (this) { 7650 final boolean allowed = checkCallingPermission(android.Manifest.permission.GET_TASKS) 7651 == PackageManager.PERMISSION_GRANTED; 7652 if (!allowed) { 7653 Slog.w(TAG, "getRecentTasks: caller " + callingUid 7654 + " does not hold GET_TASKS; limiting output"); 7655 } 7656 final boolean detailed = checkCallingPermission( 7657 android.Manifest.permission.GET_DETAILED_TASKS) 7658 == PackageManager.PERMISSION_GRANTED; 7659 7660 IPackageManager pm = AppGlobals.getPackageManager(); 7661 7662 final int N = mRecentTasks.size(); 7663 ArrayList<ActivityManager.RecentTaskInfo> res 7664 = new ArrayList<ActivityManager.RecentTaskInfo>( 7665 maxNum < N ? maxNum : N); 7666 7667 final Set<Integer> includedUsers; 7668 if (includeProfiles) { 7669 includedUsers = getProfileIdsLocked(userId); 7670 } else { 7671 includedUsers = new HashSet<Integer>(); 7672 } 7673 includedUsers.add(Integer.valueOf(userId)); 7674 7675 // Regroup affiliated tasks together. 7676 for (int i = 0; i < N; ) { 7677 TaskRecord task = mRecentTasks.remove(i); 7678 if (mTmpRecents.contains(task)) { 7679 continue; 7680 } 7681 int affiliatedTaskId = task.mAffiliatedTaskId; 7682 while (true) { 7683 TaskRecord next = task.mNextAffiliate; 7684 if (next == null) { 7685 break; 7686 } 7687 if (next.mAffiliatedTaskId != affiliatedTaskId) { 7688 Slog.e(TAG, "Error in Recents: next.affiliatedTaskId=" + 7689 next.mAffiliatedTaskId + " affiliatedTaskId=" + affiliatedTaskId); 7690 task.setNextAffiliate(null); 7691 if (next.mPrevAffiliate == task) { 7692 next.setPrevAffiliate(null); 7693 } 7694 break; 7695 } 7696 if (next.mPrevAffiliate != task) { 7697 Slog.e(TAG, "Error in Recents chain prev.mNextAffiliate=" + 7698 next.mPrevAffiliate + " task=" + task); 7699 next.setPrevAffiliate(null); 7700 break; 7701 } 7702 if (!mRecentTasks.contains(next)) { 7703 Slog.e(TAG, "Error in Recents: next=" + next + " not in mRecentTasks"); 7704 task.setNextAffiliate(null); 7705 if (next.mPrevAffiliate == task) { 7706 next.setPrevAffiliate(null); 7707 } 7708 break; 7709 } 7710 task = next; 7711 } 7712 // task is now the end of the list 7713 do { 7714 mRecentTasks.remove(task); 7715 mRecentTasks.add(i++, task); 7716 mTmpRecents.add(task); 7717 } while ((task = task.mPrevAffiliate) != null); 7718 } 7719 mTmpRecents.clear(); 7720 // mRecentTasks is now in sorted, affiliated order. 7721 7722 for (int i=0; i<N && maxNum > 0; i++) { 7723 TaskRecord tr = mRecentTasks.get(i); 7724 // Only add calling user or related users recent tasks 7725 if (!includedUsers.contains(Integer.valueOf(tr.userId))) { 7726 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, not user: " + tr); 7727 continue; 7728 } 7729 7730 // Return the entry if desired by the caller. We always return 7731 // the first entry, because callers always expect this to be the 7732 // foreground app. We may filter others if the caller has 7733 // not supplied RECENT_WITH_EXCLUDED and there is some reason 7734 // we should exclude the entry. 7735 7736 if (i == 0 7737 || withExcluded 7738 || (tr.intent == null) 7739 || ((tr.intent.getFlags() & Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS) 7740 == 0)) { 7741 if (!allowed) { 7742 // If the caller doesn't have the GET_TASKS permission, then only 7743 // allow them to see a small subset of tasks -- their own and home. 7744 if (!tr.isHomeTask() && tr.effectiveUid != callingUid) { 7745 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, not allowed: " + tr); 7746 continue; 7747 } 7748 } 7749 if (tr.autoRemoveRecents && tr.getTopActivity() == null) { 7750 // Don't include auto remove tasks that are finished or finishing. 7751 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, auto-remove without activity: " 7752 + tr); 7753 continue; 7754 } 7755 7756 ActivityManager.RecentTaskInfo rti = createRecentTaskInfoFromTaskRecord(tr); 7757 if (!detailed) { 7758 rti.baseIntent.replaceExtras((Bundle)null); 7759 } 7760 7761 if ((flags&ActivityManager.RECENT_IGNORE_UNAVAILABLE) != 0) { 7762 // Check whether this activity is currently available. 7763 try { 7764 if (rti.origActivity != null) { 7765 if (pm.getActivityInfo(rti.origActivity, 0, userId) 7766 == null) { 7767 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, unavail orig act: " 7768 + tr); 7769 continue; 7770 } 7771 } else if (rti.baseIntent != null) { 7772 if (pm.queryIntentActivities(rti.baseIntent, 7773 null, 0, userId) == null) { 7774 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, unavail intent: " 7775 + tr); 7776 continue; 7777 } 7778 } 7779 } catch (RemoteException e) { 7780 // Will never happen. 7781 } 7782 } 7783 7784 res.add(rti); 7785 maxNum--; 7786 } 7787 } 7788 return res; 7789 } 7790 } 7791 7792 private TaskRecord recentTaskForIdLocked(int id) { 7793 final int N = mRecentTasks.size(); 7794 for (int i=0; i<N; i++) { 7795 TaskRecord tr = mRecentTasks.get(i); 7796 if (tr.taskId == id) { 7797 return tr; 7798 } 7799 } 7800 return null; 7801 } 7802 7803 @Override 7804 public ActivityManager.TaskThumbnail getTaskThumbnail(int id) { 7805 synchronized (this) { 7806 enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER, 7807 "getTaskThumbnail()"); 7808 TaskRecord tr = recentTaskForIdLocked(id); 7809 if (tr != null) { 7810 return tr.getTaskThumbnailLocked(); 7811 } 7812 } 7813 return null; 7814 } 7815 7816 @Override 7817 public int addAppTask(IBinder activityToken, Intent intent, 7818 ActivityManager.TaskDescription description, Bitmap thumbnail) throws RemoteException { 7819 final int callingUid = Binder.getCallingUid(); 7820 final long callingIdent = Binder.clearCallingIdentity(); 7821 7822 try { 7823 synchronized (this) { 7824 ActivityRecord r = ActivityRecord.isInStackLocked(activityToken); 7825 if (r == null) { 7826 throw new IllegalArgumentException("Activity does not exist; token=" 7827 + activityToken); 7828 } 7829 ComponentName comp = intent.getComponent(); 7830 if (comp == null) { 7831 throw new IllegalArgumentException("Intent " + intent 7832 + " must specify explicit component"); 7833 } 7834 if (thumbnail.getWidth() != mThumbnailWidth 7835 || thumbnail.getHeight() != mThumbnailHeight) { 7836 throw new IllegalArgumentException("Bad thumbnail size: got " 7837 + thumbnail.getWidth() + "x" + thumbnail.getHeight() + ", require " 7838 + mThumbnailWidth + "x" + mThumbnailHeight); 7839 } 7840 if (intent.getSelector() != null) { 7841 intent.setSelector(null); 7842 } 7843 if (intent.getSourceBounds() != null) { 7844 intent.setSourceBounds(null); 7845 } 7846 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_DOCUMENT) != 0) { 7847 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS) == 0) { 7848 // The caller has added this as an auto-remove task... that makes no 7849 // sense, so turn off auto-remove. 7850 intent.addFlags(Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS); 7851 } 7852 } else if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_TASK) != 0) { 7853 // Must be a new task. 7854 intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 7855 } 7856 if (!comp.equals(mLastAddedTaskComponent) || callingUid != mLastAddedTaskUid) { 7857 mLastAddedTaskActivity = null; 7858 } 7859 ActivityInfo ainfo = mLastAddedTaskActivity; 7860 if (ainfo == null) { 7861 ainfo = mLastAddedTaskActivity = AppGlobals.getPackageManager().getActivityInfo( 7862 comp, 0, UserHandle.getUserId(callingUid)); 7863 if (ainfo.applicationInfo.uid != callingUid) { 7864 throw new SecurityException( 7865 "Can't add task for another application: target uid=" 7866 + ainfo.applicationInfo.uid + ", calling uid=" + callingUid); 7867 } 7868 } 7869 7870 TaskRecord task = new TaskRecord(this, mStackSupervisor.getNextTaskId(), ainfo, 7871 intent, description); 7872 7873 int trimIdx = trimRecentsForTask(task, false); 7874 if (trimIdx >= 0) { 7875 // If this would have caused a trim, then we'll abort because that 7876 // means it would be added at the end of the list but then just removed. 7877 return -1; 7878 } 7879 7880 final int N = mRecentTasks.size(); 7881 if (N >= (MAX_RECENT_TASKS-1)) { 7882 final TaskRecord tr = mRecentTasks.remove(N - 1); 7883 tr.disposeThumbnail(); 7884 tr.closeRecentsChain(); 7885 } 7886 7887 mRecentTasks.add(task); 7888 r.task.stack.addTask(task, false, false); 7889 7890 task.setLastThumbnail(thumbnail); 7891 task.freeLastThumbnail(); 7892 7893 return task.taskId; 7894 } 7895 } finally { 7896 Binder.restoreCallingIdentity(callingIdent); 7897 } 7898 } 7899 7900 @Override 7901 public Point getAppTaskThumbnailSize() { 7902 synchronized (this) { 7903 return new Point(mThumbnailWidth, mThumbnailHeight); 7904 } 7905 } 7906 7907 @Override 7908 public void setTaskDescription(IBinder token, ActivityManager.TaskDescription td) { 7909 synchronized (this) { 7910 ActivityRecord r = ActivityRecord.isInStackLocked(token); 7911 if (r != null) { 7912 r.taskDescription = td; 7913 r.task.updateTaskDescription(); 7914 } 7915 } 7916 } 7917 7918 private void killUnneededProcessLocked(ProcessRecord pr, String reason) { 7919 if (!pr.killedByAm) { 7920 Slog.i(TAG, "Killing " + pr.toShortString() + " (adj " + pr.setAdj + "): " + reason); 7921 EventLog.writeEvent(EventLogTags.AM_KILL, pr.userId, pr.pid, 7922 pr.processName, pr.setAdj, reason); 7923 pr.killedByAm = true; 7924 Process.killProcessQuiet(pr.pid); 7925 Process.killProcessGroup(pr.info.uid, pr.pid); 7926 } 7927 } 7928 7929 private void cleanUpRemovedTaskLocked(TaskRecord tr, int flags) { 7930 tr.disposeThumbnail(); 7931 mRecentTasks.remove(tr); 7932 tr.closeRecentsChain(); 7933 final boolean killProcesses = (flags&ActivityManager.REMOVE_TASK_KILL_PROCESS) != 0; 7934 Intent baseIntent = new Intent( 7935 tr.intent != null ? tr.intent : tr.affinityIntent); 7936 ComponentName component = baseIntent.getComponent(); 7937 if (component == null) { 7938 Slog.w(TAG, "Now component for base intent of task: " + tr); 7939 return; 7940 } 7941 7942 // Find any running services associated with this app. 7943 mServices.cleanUpRemovedTaskLocked(tr, component, baseIntent); 7944 7945 if (killProcesses) { 7946 // Find any running processes associated with this app. 7947 final String pkg = component.getPackageName(); 7948 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 7949 ArrayMap<String, SparseArray<ProcessRecord>> pmap = mProcessNames.getMap(); 7950 for (int i=0; i<pmap.size(); i++) { 7951 SparseArray<ProcessRecord> uids = pmap.valueAt(i); 7952 for (int j=0; j<uids.size(); j++) { 7953 ProcessRecord proc = uids.valueAt(j); 7954 if (proc.userId != tr.userId) { 7955 continue; 7956 } 7957 if (!proc.pkgList.containsKey(pkg)) { 7958 continue; 7959 } 7960 procs.add(proc); 7961 } 7962 } 7963 7964 // Kill the running processes. 7965 for (int i=0; i<procs.size(); i++) { 7966 ProcessRecord pr = procs.get(i); 7967 if (pr == mHomeProcess) { 7968 // Don't kill the home process along with tasks from the same package. 7969 continue; 7970 } 7971 if (pr.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 7972 killUnneededProcessLocked(pr, "remove task"); 7973 } else { 7974 pr.waitingToKill = "remove task"; 7975 } 7976 } 7977 } 7978 } 7979 7980 /** 7981 * Removes the task with the specified task id. 7982 * 7983 * @param taskId Identifier of the task to be removed. 7984 * @param flags Additional operational flags. May be 0 or 7985 * {@link ActivityManager#REMOVE_TASK_KILL_PROCESS}. 7986 * @return Returns true if the given task was found and removed. 7987 */ 7988 private boolean removeTaskByIdLocked(int taskId, int flags) { 7989 TaskRecord tr = recentTaskForIdLocked(taskId); 7990 if (tr != null) { 7991 tr.removeTaskActivitiesLocked(); 7992 cleanUpRemovedTaskLocked(tr, flags); 7993 if (tr.isPersistable) { 7994 notifyTaskPersisterLocked(null, true); 7995 } 7996 return true; 7997 } 7998 return false; 7999 } 8000 8001 @Override 8002 public boolean removeTask(int taskId, int flags) { 8003 synchronized (this) { 8004 enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, 8005 "removeTask()"); 8006 long ident = Binder.clearCallingIdentity(); 8007 try { 8008 return removeTaskByIdLocked(taskId, flags); 8009 } finally { 8010 Binder.restoreCallingIdentity(ident); 8011 } 8012 } 8013 } 8014 8015 /** 8016 * TODO: Add mController hook 8017 */ 8018 @Override 8019 public void moveTaskToFront(int taskId, int flags, Bundle options) { 8020 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 8021 "moveTaskToFront()"); 8022 8023 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToFront: moving taskId=" + taskId); 8024 synchronized(this) { 8025 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 8026 Binder.getCallingUid(), "Task to front")) { 8027 ActivityOptions.abort(options); 8028 return; 8029 } 8030 final long origId = Binder.clearCallingIdentity(); 8031 try { 8032 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 8033 if (task == null) { 8034 return; 8035 } 8036 if (mStackSupervisor.isLockTaskModeViolation(task)) { 8037 mStackSupervisor.showLockTaskToast(); 8038 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode"); 8039 return; 8040 } 8041 final ActivityRecord prev = mStackSupervisor.topRunningActivityLocked(); 8042 if (prev != null && prev.isRecentsActivity()) { 8043 task.setTaskToReturnTo(ActivityRecord.RECENTS_ACTIVITY_TYPE); 8044 } 8045 mStackSupervisor.findTaskToMoveToFrontLocked(task, flags, options); 8046 } finally { 8047 Binder.restoreCallingIdentity(origId); 8048 } 8049 ActivityOptions.abort(options); 8050 } 8051 } 8052 8053 @Override 8054 public void moveTaskToBack(int taskId) { 8055 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 8056 "moveTaskToBack()"); 8057 8058 synchronized(this) { 8059 TaskRecord tr = recentTaskForIdLocked(taskId); 8060 if (tr != null) { 8061 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToBack: moving task=" + tr); 8062 ActivityStack stack = tr.stack; 8063 if (stack.mResumedActivity != null && stack.mResumedActivity.task == tr) { 8064 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 8065 Binder.getCallingUid(), "Task to back")) { 8066 return; 8067 } 8068 } 8069 final long origId = Binder.clearCallingIdentity(); 8070 try { 8071 stack.moveTaskToBackLocked(taskId, null); 8072 } finally { 8073 Binder.restoreCallingIdentity(origId); 8074 } 8075 } 8076 } 8077 } 8078 8079 /** 8080 * Moves an activity, and all of the other activities within the same task, to the bottom 8081 * of the history stack. The activity's order within the task is unchanged. 8082 * 8083 * @param token A reference to the activity we wish to move 8084 * @param nonRoot If false then this only works if the activity is the root 8085 * of a task; if true it will work for any activity in a task. 8086 * @return Returns true if the move completed, false if not. 8087 */ 8088 @Override 8089 public boolean moveActivityTaskToBack(IBinder token, boolean nonRoot) { 8090 enforceNotIsolatedCaller("moveActivityTaskToBack"); 8091 synchronized(this) { 8092 final long origId = Binder.clearCallingIdentity(); 8093 int taskId = ActivityRecord.getTaskForActivityLocked(token, !nonRoot); 8094 if (taskId >= 0) { 8095 return ActivityRecord.getStackLocked(token).moveTaskToBackLocked(taskId, null); 8096 } 8097 Binder.restoreCallingIdentity(origId); 8098 } 8099 return false; 8100 } 8101 8102 @Override 8103 public void moveTaskBackwards(int task) { 8104 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 8105 "moveTaskBackwards()"); 8106 8107 synchronized(this) { 8108 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 8109 Binder.getCallingUid(), "Task backwards")) { 8110 return; 8111 } 8112 final long origId = Binder.clearCallingIdentity(); 8113 moveTaskBackwardsLocked(task); 8114 Binder.restoreCallingIdentity(origId); 8115 } 8116 } 8117 8118 private final void moveTaskBackwardsLocked(int task) { 8119 Slog.e(TAG, "moveTaskBackwards not yet implemented!"); 8120 } 8121 8122 @Override 8123 public IBinder getHomeActivityToken() throws RemoteException { 8124 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8125 "getHomeActivityToken()"); 8126 synchronized (this) { 8127 return mStackSupervisor.getHomeActivityToken(); 8128 } 8129 } 8130 8131 @Override 8132 public IActivityContainer createActivityContainer(IBinder parentActivityToken, 8133 IActivityContainerCallback callback) throws RemoteException { 8134 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8135 "createActivityContainer()"); 8136 synchronized (this) { 8137 if (parentActivityToken == null) { 8138 throw new IllegalArgumentException("parent token must not be null"); 8139 } 8140 ActivityRecord r = ActivityRecord.forToken(parentActivityToken); 8141 if (r == null) { 8142 return null; 8143 } 8144 if (callback == null) { 8145 throw new IllegalArgumentException("callback must not be null"); 8146 } 8147 return mStackSupervisor.createActivityContainer(r, callback); 8148 } 8149 } 8150 8151 @Override 8152 public void deleteActivityContainer(IActivityContainer container) throws RemoteException { 8153 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8154 "deleteActivityContainer()"); 8155 synchronized (this) { 8156 mStackSupervisor.deleteActivityContainer(container); 8157 } 8158 } 8159 8160 @Override 8161 public IActivityContainer getEnclosingActivityContainer(IBinder activityToken) 8162 throws RemoteException { 8163 synchronized (this) { 8164 ActivityStack stack = ActivityRecord.getStackLocked(activityToken); 8165 if (stack != null) { 8166 return stack.mActivityContainer; 8167 } 8168 return null; 8169 } 8170 } 8171 8172 @Override 8173 public void moveTaskToStack(int taskId, int stackId, boolean toTop) { 8174 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8175 "moveTaskToStack()"); 8176 if (stackId == HOME_STACK_ID) { 8177 Slog.e(TAG, "moveTaskToStack: Attempt to move task " + taskId + " to home stack", 8178 new RuntimeException("here").fillInStackTrace()); 8179 } 8180 synchronized (this) { 8181 long ident = Binder.clearCallingIdentity(); 8182 try { 8183 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToStack: moving task=" + taskId + " to stackId=" 8184 + stackId + " toTop=" + toTop); 8185 mStackSupervisor.moveTaskToStack(taskId, stackId, toTop); 8186 } finally { 8187 Binder.restoreCallingIdentity(ident); 8188 } 8189 } 8190 } 8191 8192 @Override 8193 public void resizeStack(int stackBoxId, Rect bounds) { 8194 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8195 "resizeStackBox()"); 8196 long ident = Binder.clearCallingIdentity(); 8197 try { 8198 mWindowManager.resizeStack(stackBoxId, bounds); 8199 } finally { 8200 Binder.restoreCallingIdentity(ident); 8201 } 8202 } 8203 8204 @Override 8205 public List<StackInfo> getAllStackInfos() { 8206 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8207 "getAllStackInfos()"); 8208 long ident = Binder.clearCallingIdentity(); 8209 try { 8210 synchronized (this) { 8211 return mStackSupervisor.getAllStackInfosLocked(); 8212 } 8213 } finally { 8214 Binder.restoreCallingIdentity(ident); 8215 } 8216 } 8217 8218 @Override 8219 public StackInfo getStackInfo(int stackId) { 8220 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8221 "getStackInfo()"); 8222 long ident = Binder.clearCallingIdentity(); 8223 try { 8224 synchronized (this) { 8225 return mStackSupervisor.getStackInfoLocked(stackId); 8226 } 8227 } finally { 8228 Binder.restoreCallingIdentity(ident); 8229 } 8230 } 8231 8232 @Override 8233 public boolean isInHomeStack(int taskId) { 8234 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8235 "getStackInfo()"); 8236 long ident = Binder.clearCallingIdentity(); 8237 try { 8238 synchronized (this) { 8239 TaskRecord tr = recentTaskForIdLocked(taskId); 8240 return tr != null && tr.stack != null && tr.stack.isHomeStack(); 8241 } 8242 } finally { 8243 Binder.restoreCallingIdentity(ident); 8244 } 8245 } 8246 8247 @Override 8248 public int getTaskForActivity(IBinder token, boolean onlyRoot) { 8249 synchronized(this) { 8250 return ActivityRecord.getTaskForActivityLocked(token, onlyRoot); 8251 } 8252 } 8253 8254 private boolean isLockTaskAuthorized(String pkg) { 8255 final DevicePolicyManager dpm = (DevicePolicyManager) 8256 mContext.getSystemService(Context.DEVICE_POLICY_SERVICE); 8257 try { 8258 int uid = mContext.getPackageManager().getPackageUid(pkg, 8259 Binder.getCallingUserHandle().getIdentifier()); 8260 return (uid == Binder.getCallingUid()) && dpm != null && dpm.isLockTaskPermitted(pkg); 8261 } catch (NameNotFoundException e) { 8262 return false; 8263 } 8264 } 8265 8266 void startLockTaskMode(TaskRecord task) { 8267 final String pkg; 8268 synchronized (this) { 8269 pkg = task.intent.getComponent().getPackageName(); 8270 } 8271 boolean isSystemInitiated = Binder.getCallingUid() == Process.SYSTEM_UID; 8272 if (!isSystemInitiated && !isLockTaskAuthorized(pkg)) { 8273 final TaskRecord taskRecord = task; 8274 mHandler.post(new Runnable() { 8275 @Override 8276 public void run() { 8277 mLockToAppRequest.showLockTaskPrompt(taskRecord); 8278 } 8279 }); 8280 return; 8281 } 8282 long ident = Binder.clearCallingIdentity(); 8283 try { 8284 synchronized (this) { 8285 // Since we lost lock on task, make sure it is still there. 8286 task = mStackSupervisor.anyTaskForIdLocked(task.taskId); 8287 if (task != null) { 8288 if (!isSystemInitiated 8289 && ((mFocusedActivity == null) || (task != mFocusedActivity.task))) { 8290 throw new IllegalArgumentException("Invalid task, not in foreground"); 8291 } 8292 mStackSupervisor.setLockTaskModeLocked(task, !isSystemInitiated); 8293 } 8294 } 8295 } finally { 8296 Binder.restoreCallingIdentity(ident); 8297 } 8298 } 8299 8300 @Override 8301 public void startLockTaskMode(int taskId) { 8302 final TaskRecord task; 8303 long ident = Binder.clearCallingIdentity(); 8304 try { 8305 synchronized (this) { 8306 task = mStackSupervisor.anyTaskForIdLocked(taskId); 8307 } 8308 } finally { 8309 Binder.restoreCallingIdentity(ident); 8310 } 8311 if (task != null) { 8312 startLockTaskMode(task); 8313 } 8314 } 8315 8316 @Override 8317 public void startLockTaskMode(IBinder token) { 8318 final TaskRecord task; 8319 long ident = Binder.clearCallingIdentity(); 8320 try { 8321 synchronized (this) { 8322 final ActivityRecord r = ActivityRecord.forToken(token); 8323 if (r == null) { 8324 return; 8325 } 8326 task = r.task; 8327 } 8328 } finally { 8329 Binder.restoreCallingIdentity(ident); 8330 } 8331 if (task != null) { 8332 startLockTaskMode(task); 8333 } 8334 } 8335 8336 @Override 8337 public void startLockTaskModeOnCurrent() throws RemoteException { 8338 checkCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS); 8339 ActivityRecord r = null; 8340 synchronized (this) { 8341 r = mStackSupervisor.topRunningActivityLocked(); 8342 } 8343 startLockTaskMode(r.task); 8344 } 8345 8346 @Override 8347 public void stopLockTaskMode() { 8348 // Verify that the user matches the package of the intent for the TaskRecord 8349 // we are locked to or systtem. This will ensure the same caller for startLockTaskMode 8350 // and stopLockTaskMode. 8351 final int callingUid = Binder.getCallingUid(); 8352 if (callingUid != Process.SYSTEM_UID) { 8353 try { 8354 String pkg = 8355 mStackSupervisor.mLockTaskModeTask.intent.getComponent().getPackageName(); 8356 int uid = mContext.getPackageManager().getPackageUid(pkg, 8357 Binder.getCallingUserHandle().getIdentifier()); 8358 if (uid != callingUid) { 8359 throw new SecurityException("Invalid uid, expected " + uid); 8360 } 8361 } catch (NameNotFoundException e) { 8362 Log.d(TAG, "stopLockTaskMode " + e); 8363 return; 8364 } 8365 } 8366 long ident = Binder.clearCallingIdentity(); 8367 try { 8368 Log.d(TAG, "stopLockTaskMode"); 8369 // Stop lock task 8370 synchronized (this) { 8371 mStackSupervisor.setLockTaskModeLocked(null, false); 8372 } 8373 } finally { 8374 Binder.restoreCallingIdentity(ident); 8375 } 8376 } 8377 8378 @Override 8379 public void stopLockTaskModeOnCurrent() throws RemoteException { 8380 checkCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS); 8381 long ident = Binder.clearCallingIdentity(); 8382 try { 8383 stopLockTaskMode(); 8384 } finally { 8385 Binder.restoreCallingIdentity(ident); 8386 } 8387 } 8388 8389 @Override 8390 public boolean isInLockTaskMode() { 8391 synchronized (this) { 8392 return mStackSupervisor.isInLockTaskMode(); 8393 } 8394 } 8395 8396 // ========================================================= 8397 // CONTENT PROVIDERS 8398 // ========================================================= 8399 8400 private final List<ProviderInfo> generateApplicationProvidersLocked(ProcessRecord app) { 8401 List<ProviderInfo> providers = null; 8402 try { 8403 providers = AppGlobals.getPackageManager(). 8404 queryContentProviders(app.processName, app.uid, 8405 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS); 8406 } catch (RemoteException ex) { 8407 } 8408 if (DEBUG_MU) 8409 Slog.v(TAG_MU, "generateApplicationProvidersLocked, app.info.uid = " + app.uid); 8410 int userId = app.userId; 8411 if (providers != null) { 8412 int N = providers.size(); 8413 app.pubProviders.ensureCapacity(N + app.pubProviders.size()); 8414 for (int i=0; i<N; i++) { 8415 ProviderInfo cpi = 8416 (ProviderInfo)providers.get(i); 8417 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo, 8418 cpi.name, cpi.flags); 8419 if (singleton && UserHandle.getUserId(app.uid) != 0) { 8420 // This is a singleton provider, but a user besides the 8421 // default user is asking to initialize a process it runs 8422 // in... well, no, it doesn't actually run in this process, 8423 // it runs in the process of the default user. Get rid of it. 8424 providers.remove(i); 8425 N--; 8426 i--; 8427 continue; 8428 } 8429 8430 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 8431 ContentProviderRecord cpr = mProviderMap.getProviderByClass(comp, userId); 8432 if (cpr == null) { 8433 cpr = new ContentProviderRecord(this, cpi, app.info, comp, singleton); 8434 mProviderMap.putProviderByClass(comp, cpr); 8435 } 8436 if (DEBUG_MU) 8437 Slog.v(TAG_MU, "generateApplicationProvidersLocked, cpi.uid = " + cpr.uid); 8438 app.pubProviders.put(cpi.name, cpr); 8439 if (!cpi.multiprocess || !"android".equals(cpi.packageName)) { 8440 // Don't add this if it is a platform component that is marked 8441 // to run in multiple processes, because this is actually 8442 // part of the framework so doesn't make sense to track as a 8443 // separate apk in the process. 8444 app.addPackage(cpi.applicationInfo.packageName, cpi.applicationInfo.versionCode, 8445 mProcessStats); 8446 } 8447 ensurePackageDexOpt(cpi.applicationInfo.packageName); 8448 } 8449 } 8450 return providers; 8451 } 8452 8453 /** 8454 * Check if {@link ProcessRecord} has a possible chance at accessing the 8455 * given {@link ProviderInfo}. Final permission checking is always done 8456 * in {@link ContentProvider}. 8457 */ 8458 private final String checkContentProviderPermissionLocked( 8459 ProviderInfo cpi, ProcessRecord r, int userId, boolean checkUser) { 8460 final int callingPid = (r != null) ? r.pid : Binder.getCallingPid(); 8461 final int callingUid = (r != null) ? r.uid : Binder.getCallingUid(); 8462 boolean checkedGrants = false; 8463 if (checkUser) { 8464 // Looking for cross-user grants before enforcing the typical cross-users permissions 8465 int tmpTargetUserId = unsafeConvertIncomingUser(userId); 8466 if (tmpTargetUserId != UserHandle.getUserId(callingUid)) { 8467 if (checkAuthorityGrants(callingUid, cpi, tmpTargetUserId, checkUser)) { 8468 return null; 8469 } 8470 checkedGrants = true; 8471 } 8472 userId = handleIncomingUser(callingPid, callingUid, userId, 8473 false, ALLOW_NON_FULL, 8474 "checkContentProviderPermissionLocked " + cpi.authority, null); 8475 if (userId != tmpTargetUserId) { 8476 // When we actually went to determine the final targer user ID, this ended 8477 // up different than our initial check for the authority. This is because 8478 // they had asked for USER_CURRENT_OR_SELF and we ended up switching to 8479 // SELF. So we need to re-check the grants again. 8480 checkedGrants = false; 8481 } 8482 } 8483 if (checkComponentPermission(cpi.readPermission, callingPid, callingUid, 8484 cpi.applicationInfo.uid, cpi.exported) 8485 == PackageManager.PERMISSION_GRANTED) { 8486 return null; 8487 } 8488 if (checkComponentPermission(cpi.writePermission, callingPid, callingUid, 8489 cpi.applicationInfo.uid, cpi.exported) 8490 == PackageManager.PERMISSION_GRANTED) { 8491 return null; 8492 } 8493 8494 PathPermission[] pps = cpi.pathPermissions; 8495 if (pps != null) { 8496 int i = pps.length; 8497 while (i > 0) { 8498 i--; 8499 PathPermission pp = pps[i]; 8500 String pprperm = pp.getReadPermission(); 8501 if (pprperm != null && checkComponentPermission(pprperm, callingPid, callingUid, 8502 cpi.applicationInfo.uid, cpi.exported) 8503 == PackageManager.PERMISSION_GRANTED) { 8504 return null; 8505 } 8506 String ppwperm = pp.getWritePermission(); 8507 if (ppwperm != null && checkComponentPermission(ppwperm, callingPid, callingUid, 8508 cpi.applicationInfo.uid, cpi.exported) 8509 == PackageManager.PERMISSION_GRANTED) { 8510 return null; 8511 } 8512 } 8513 } 8514 if (!checkedGrants && checkAuthorityGrants(callingUid, cpi, userId, checkUser)) { 8515 return null; 8516 } 8517 8518 String msg; 8519 if (!cpi.exported) { 8520 msg = "Permission Denial: opening provider " + cpi.name 8521 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 8522 + ", uid=" + callingUid + ") that is not exported from uid " 8523 + cpi.applicationInfo.uid; 8524 } else { 8525 msg = "Permission Denial: opening provider " + cpi.name 8526 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 8527 + ", uid=" + callingUid + ") requires " 8528 + cpi.readPermission + " or " + cpi.writePermission; 8529 } 8530 Slog.w(TAG, msg); 8531 return msg; 8532 } 8533 8534 /** 8535 * Returns if the ContentProvider has granted a uri to callingUid 8536 */ 8537 boolean checkAuthorityGrants(int callingUid, ProviderInfo cpi, int userId, boolean checkUser) { 8538 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 8539 if (perms != null) { 8540 for (int i=perms.size()-1; i>=0; i--) { 8541 GrantUri grantUri = perms.keyAt(i); 8542 if (grantUri.sourceUserId == userId || !checkUser) { 8543 if (matchesProvider(grantUri.uri, cpi)) { 8544 return true; 8545 } 8546 } 8547 } 8548 } 8549 return false; 8550 } 8551 8552 /** 8553 * Returns true if the uri authority is one of the authorities specified in the provider. 8554 */ 8555 boolean matchesProvider(Uri uri, ProviderInfo cpi) { 8556 String uriAuth = uri.getAuthority(); 8557 String cpiAuth = cpi.authority; 8558 if (cpiAuth.indexOf(';') == -1) { 8559 return cpiAuth.equals(uriAuth); 8560 } 8561 String[] cpiAuths = cpiAuth.split(";"); 8562 int length = cpiAuths.length; 8563 for (int i = 0; i < length; i++) { 8564 if (cpiAuths[i].equals(uriAuth)) return true; 8565 } 8566 return false; 8567 } 8568 8569 ContentProviderConnection incProviderCountLocked(ProcessRecord r, 8570 final ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 8571 if (r != null) { 8572 for (int i=0; i<r.conProviders.size(); i++) { 8573 ContentProviderConnection conn = r.conProviders.get(i); 8574 if (conn.provider == cpr) { 8575 if (DEBUG_PROVIDER) Slog.v(TAG, 8576 "Adding provider requested by " 8577 + r.processName + " from process " 8578 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 8579 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 8580 if (stable) { 8581 conn.stableCount++; 8582 conn.numStableIncs++; 8583 } else { 8584 conn.unstableCount++; 8585 conn.numUnstableIncs++; 8586 } 8587 return conn; 8588 } 8589 } 8590 ContentProviderConnection conn = new ContentProviderConnection(cpr, r); 8591 if (stable) { 8592 conn.stableCount = 1; 8593 conn.numStableIncs = 1; 8594 } else { 8595 conn.unstableCount = 1; 8596 conn.numUnstableIncs = 1; 8597 } 8598 cpr.connections.add(conn); 8599 r.conProviders.add(conn); 8600 return conn; 8601 } 8602 cpr.addExternalProcessHandleLocked(externalProcessToken); 8603 return null; 8604 } 8605 8606 boolean decProviderCountLocked(ContentProviderConnection conn, 8607 ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 8608 if (conn != null) { 8609 cpr = conn.provider; 8610 if (DEBUG_PROVIDER) Slog.v(TAG, 8611 "Removing provider requested by " 8612 + conn.client.processName + " from process " 8613 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 8614 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 8615 if (stable) { 8616 conn.stableCount--; 8617 } else { 8618 conn.unstableCount--; 8619 } 8620 if (conn.stableCount == 0 && conn.unstableCount == 0) { 8621 cpr.connections.remove(conn); 8622 conn.client.conProviders.remove(conn); 8623 return true; 8624 } 8625 return false; 8626 } 8627 cpr.removeExternalProcessHandleLocked(externalProcessToken); 8628 return false; 8629 } 8630 8631 private final ContentProviderHolder getContentProviderImpl(IApplicationThread caller, 8632 String name, IBinder token, boolean stable, int userId) { 8633 ContentProviderRecord cpr; 8634 ContentProviderConnection conn = null; 8635 ProviderInfo cpi = null; 8636 8637 synchronized(this) { 8638 ProcessRecord r = null; 8639 if (caller != null) { 8640 r = getRecordForAppLocked(caller); 8641 if (r == null) { 8642 throw new SecurityException( 8643 "Unable to find app for caller " + caller 8644 + " (pid=" + Binder.getCallingPid() 8645 + ") when getting content provider " + name); 8646 } 8647 } 8648 8649 boolean checkCrossUser = true; 8650 8651 // First check if this content provider has been published... 8652 cpr = mProviderMap.getProviderByName(name, userId); 8653 // If that didn't work, check if it exists for user 0 and then 8654 // verify that it's a singleton provider before using it. 8655 if (cpr == null && userId != UserHandle.USER_OWNER) { 8656 cpr = mProviderMap.getProviderByName(name, UserHandle.USER_OWNER); 8657 if (cpr != null) { 8658 cpi = cpr.info; 8659 if (isSingleton(cpi.processName, cpi.applicationInfo, 8660 cpi.name, cpi.flags) 8661 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid)) { 8662 userId = UserHandle.USER_OWNER; 8663 checkCrossUser = false; 8664 } else { 8665 cpr = null; 8666 cpi = null; 8667 } 8668 } 8669 } 8670 8671 boolean providerRunning = cpr != null; 8672 if (providerRunning) { 8673 cpi = cpr.info; 8674 String msg; 8675 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, checkCrossUser)) 8676 != null) { 8677 throw new SecurityException(msg); 8678 } 8679 8680 if (r != null && cpr.canRunHere(r)) { 8681 // This provider has been published or is in the process 8682 // of being published... but it is also allowed to run 8683 // in the caller's process, so don't make a connection 8684 // and just let the caller instantiate its own instance. 8685 ContentProviderHolder holder = cpr.newHolder(null); 8686 // don't give caller the provider object, it needs 8687 // to make its own. 8688 holder.provider = null; 8689 return holder; 8690 } 8691 8692 final long origId = Binder.clearCallingIdentity(); 8693 8694 // In this case the provider instance already exists, so we can 8695 // return it right away. 8696 conn = incProviderCountLocked(r, cpr, token, stable); 8697 if (conn != null && (conn.stableCount+conn.unstableCount) == 1) { 8698 if (cpr.proc != null && r.setAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 8699 // If this is a perceptible app accessing the provider, 8700 // make sure to count it as being accessed and thus 8701 // back up on the LRU list. This is good because 8702 // content providers are often expensive to start. 8703 updateLruProcessLocked(cpr.proc, false, null); 8704 } 8705 } 8706 8707 if (cpr.proc != null) { 8708 if (false) { 8709 if (cpr.name.flattenToShortString().equals( 8710 "com.android.providers.calendar/.CalendarProvider2")) { 8711 Slog.v(TAG, "****************** KILLING " 8712 + cpr.name.flattenToShortString()); 8713 Process.killProcess(cpr.proc.pid); 8714 } 8715 } 8716 boolean success = updateOomAdjLocked(cpr.proc); 8717 if (DEBUG_PROVIDER) Slog.i(TAG, "Adjust success: " + success); 8718 // NOTE: there is still a race here where a signal could be 8719 // pending on the process even though we managed to update its 8720 // adj level. Not sure what to do about this, but at least 8721 // the race is now smaller. 8722 if (!success) { 8723 // Uh oh... it looks like the provider's process 8724 // has been killed on us. We need to wait for a new 8725 // process to be started, and make sure its death 8726 // doesn't kill our process. 8727 Slog.i(TAG, 8728 "Existing provider " + cpr.name.flattenToShortString() 8729 + " is crashing; detaching " + r); 8730 boolean lastRef = decProviderCountLocked(conn, cpr, token, stable); 8731 appDiedLocked(cpr.proc); 8732 if (!lastRef) { 8733 // This wasn't the last ref our process had on 8734 // the provider... we have now been killed, bail. 8735 return null; 8736 } 8737 providerRunning = false; 8738 conn = null; 8739 } 8740 } 8741 8742 Binder.restoreCallingIdentity(origId); 8743 } 8744 8745 boolean singleton; 8746 if (!providerRunning) { 8747 try { 8748 cpi = AppGlobals.getPackageManager(). 8749 resolveContentProvider(name, 8750 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS, userId); 8751 } catch (RemoteException ex) { 8752 } 8753 if (cpi == null) { 8754 return null; 8755 } 8756 // If the provider is a singleton AND 8757 // (it's a call within the same user || the provider is a 8758 // privileged app) 8759 // Then allow connecting to the singleton provider 8760 singleton = isSingleton(cpi.processName, cpi.applicationInfo, 8761 cpi.name, cpi.flags) 8762 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid); 8763 if (singleton) { 8764 userId = UserHandle.USER_OWNER; 8765 } 8766 cpi.applicationInfo = getAppInfoForUser(cpi.applicationInfo, userId); 8767 8768 String msg; 8769 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, !singleton)) 8770 != null) { 8771 throw new SecurityException(msg); 8772 } 8773 8774 if (!mProcessesReady && !mDidUpdate && !mWaitingUpdate 8775 && !cpi.processName.equals("system")) { 8776 // If this content provider does not run in the system 8777 // process, and the system is not yet ready to run other 8778 // processes, then fail fast instead of hanging. 8779 throw new IllegalArgumentException( 8780 "Attempt to launch content provider before system ready"); 8781 } 8782 8783 // Make sure that the user who owns this provider is started. If not, 8784 // we don't want to allow it to run. 8785 if (mStartedUsers.get(userId) == null) { 8786 Slog.w(TAG, "Unable to launch app " 8787 + cpi.applicationInfo.packageName + "/" 8788 + cpi.applicationInfo.uid + " for provider " 8789 + name + ": user " + userId + " is stopped"); 8790 return null; 8791 } 8792 8793 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 8794 cpr = mProviderMap.getProviderByClass(comp, userId); 8795 final boolean firstClass = cpr == null; 8796 if (firstClass) { 8797 try { 8798 ApplicationInfo ai = 8799 AppGlobals.getPackageManager(). 8800 getApplicationInfo( 8801 cpi.applicationInfo.packageName, 8802 STOCK_PM_FLAGS, userId); 8803 if (ai == null) { 8804 Slog.w(TAG, "No package info for content provider " 8805 + cpi.name); 8806 return null; 8807 } 8808 ai = getAppInfoForUser(ai, userId); 8809 cpr = new ContentProviderRecord(this, cpi, ai, comp, singleton); 8810 } catch (RemoteException ex) { 8811 // pm is in same process, this will never happen. 8812 } 8813 } 8814 8815 if (r != null && cpr.canRunHere(r)) { 8816 // If this is a multiprocess provider, then just return its 8817 // info and allow the caller to instantiate it. Only do 8818 // this if the provider is the same user as the caller's 8819 // process, or can run as root (so can be in any process). 8820 return cpr.newHolder(null); 8821 } 8822 8823 if (DEBUG_PROVIDER) { 8824 RuntimeException e = new RuntimeException("here"); 8825 Slog.w(TAG, "LAUNCHING REMOTE PROVIDER (myuid " + (r != null ? r.uid : null) 8826 + " pruid " + cpr.appInfo.uid + "): " + cpr.info.name, e); 8827 } 8828 8829 // This is single process, and our app is now connecting to it. 8830 // See if we are already in the process of launching this 8831 // provider. 8832 final int N = mLaunchingProviders.size(); 8833 int i; 8834 for (i=0; i<N; i++) { 8835 if (mLaunchingProviders.get(i) == cpr) { 8836 break; 8837 } 8838 } 8839 8840 // If the provider is not already being launched, then get it 8841 // started. 8842 if (i >= N) { 8843 final long origId = Binder.clearCallingIdentity(); 8844 8845 try { 8846 // Content provider is now in use, its package can't be stopped. 8847 try { 8848 AppGlobals.getPackageManager().setPackageStoppedState( 8849 cpr.appInfo.packageName, false, userId); 8850 } catch (RemoteException e) { 8851 } catch (IllegalArgumentException e) { 8852 Slog.w(TAG, "Failed trying to unstop package " 8853 + cpr.appInfo.packageName + ": " + e); 8854 } 8855 8856 // Use existing process if already started 8857 ProcessRecord proc = getProcessRecordLocked( 8858 cpi.processName, cpr.appInfo.uid, false); 8859 if (proc != null && proc.thread != null) { 8860 if (DEBUG_PROVIDER) { 8861 Slog.d(TAG, "Installing in existing process " + proc); 8862 } 8863 proc.pubProviders.put(cpi.name, cpr); 8864 try { 8865 proc.thread.scheduleInstallProvider(cpi); 8866 } catch (RemoteException e) { 8867 } 8868 } else { 8869 proc = startProcessLocked(cpi.processName, 8870 cpr.appInfo, false, 0, "content provider", 8871 new ComponentName(cpi.applicationInfo.packageName, 8872 cpi.name), false, false, false); 8873 if (proc == null) { 8874 Slog.w(TAG, "Unable to launch app " 8875 + cpi.applicationInfo.packageName + "/" 8876 + cpi.applicationInfo.uid + " for provider " 8877 + name + ": process is bad"); 8878 return null; 8879 } 8880 } 8881 cpr.launchingApp = proc; 8882 mLaunchingProviders.add(cpr); 8883 } finally { 8884 Binder.restoreCallingIdentity(origId); 8885 } 8886 } 8887 8888 // Make sure the provider is published (the same provider class 8889 // may be published under multiple names). 8890 if (firstClass) { 8891 mProviderMap.putProviderByClass(comp, cpr); 8892 } 8893 8894 mProviderMap.putProviderByName(name, cpr); 8895 conn = incProviderCountLocked(r, cpr, token, stable); 8896 if (conn != null) { 8897 conn.waiting = true; 8898 } 8899 } 8900 } 8901 8902 // Wait for the provider to be published... 8903 synchronized (cpr) { 8904 while (cpr.provider == null) { 8905 if (cpr.launchingApp == null) { 8906 Slog.w(TAG, "Unable to launch app " 8907 + cpi.applicationInfo.packageName + "/" 8908 + cpi.applicationInfo.uid + " for provider " 8909 + name + ": launching app became null"); 8910 EventLog.writeEvent(EventLogTags.AM_PROVIDER_LOST_PROCESS, 8911 UserHandle.getUserId(cpi.applicationInfo.uid), 8912 cpi.applicationInfo.packageName, 8913 cpi.applicationInfo.uid, name); 8914 return null; 8915 } 8916 try { 8917 if (DEBUG_MU) { 8918 Slog.v(TAG_MU, "Waiting to start provider " + cpr + " launchingApp=" 8919 + cpr.launchingApp); 8920 } 8921 if (conn != null) { 8922 conn.waiting = true; 8923 } 8924 cpr.wait(); 8925 } catch (InterruptedException ex) { 8926 } finally { 8927 if (conn != null) { 8928 conn.waiting = false; 8929 } 8930 } 8931 } 8932 } 8933 return cpr != null ? cpr.newHolder(conn) : null; 8934 } 8935 8936 @Override 8937 public final ContentProviderHolder getContentProvider( 8938 IApplicationThread caller, String name, int userId, boolean stable) { 8939 enforceNotIsolatedCaller("getContentProvider"); 8940 if (caller == null) { 8941 String msg = "null IApplicationThread when getting content provider " 8942 + name; 8943 Slog.w(TAG, msg); 8944 throw new SecurityException(msg); 8945 } 8946 // The incoming user check is now handled in checkContentProviderPermissionLocked() to deal 8947 // with cross-user grant. 8948 return getContentProviderImpl(caller, name, null, stable, userId); 8949 } 8950 8951 public ContentProviderHolder getContentProviderExternal( 8952 String name, int userId, IBinder token) { 8953 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 8954 "Do not have permission in call getContentProviderExternal()"); 8955 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 8956 false, ALLOW_FULL_ONLY, "getContentProvider", null); 8957 return getContentProviderExternalUnchecked(name, token, userId); 8958 } 8959 8960 private ContentProviderHolder getContentProviderExternalUnchecked(String name, 8961 IBinder token, int userId) { 8962 return getContentProviderImpl(null, name, token, true, userId); 8963 } 8964 8965 /** 8966 * Drop a content provider from a ProcessRecord's bookkeeping 8967 */ 8968 public void removeContentProvider(IBinder connection, boolean stable) { 8969 enforceNotIsolatedCaller("removeContentProvider"); 8970 long ident = Binder.clearCallingIdentity(); 8971 try { 8972 synchronized (this) { 8973 ContentProviderConnection conn; 8974 try { 8975 conn = (ContentProviderConnection)connection; 8976 } catch (ClassCastException e) { 8977 String msg ="removeContentProvider: " + connection 8978 + " not a ContentProviderConnection"; 8979 Slog.w(TAG, msg); 8980 throw new IllegalArgumentException(msg); 8981 } 8982 if (conn == null) { 8983 throw new NullPointerException("connection is null"); 8984 } 8985 if (decProviderCountLocked(conn, null, null, stable)) { 8986 updateOomAdjLocked(); 8987 } 8988 } 8989 } finally { 8990 Binder.restoreCallingIdentity(ident); 8991 } 8992 } 8993 8994 public void removeContentProviderExternal(String name, IBinder token) { 8995 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 8996 "Do not have permission in call removeContentProviderExternal()"); 8997 removeContentProviderExternalUnchecked(name, token, UserHandle.getCallingUserId()); 8998 } 8999 9000 private void removeContentProviderExternalUnchecked(String name, IBinder token, int userId) { 9001 synchronized (this) { 9002 ContentProviderRecord cpr = mProviderMap.getProviderByName(name, userId); 9003 if(cpr == null) { 9004 //remove from mProvidersByClass 9005 if(localLOGV) Slog.v(TAG, name+" content provider not found in providers list"); 9006 return; 9007 } 9008 9009 //update content provider record entry info 9010 ComponentName comp = new ComponentName(cpr.info.packageName, cpr.info.name); 9011 ContentProviderRecord localCpr = mProviderMap.getProviderByClass(comp, userId); 9012 if (localCpr.hasExternalProcessHandles()) { 9013 if (localCpr.removeExternalProcessHandleLocked(token)) { 9014 updateOomAdjLocked(); 9015 } else { 9016 Slog.e(TAG, "Attmpt to remove content provider " + localCpr 9017 + " with no external reference for token: " 9018 + token + "."); 9019 } 9020 } else { 9021 Slog.e(TAG, "Attmpt to remove content provider: " + localCpr 9022 + " with no external references."); 9023 } 9024 } 9025 } 9026 9027 public final void publishContentProviders(IApplicationThread caller, 9028 List<ContentProviderHolder> providers) { 9029 if (providers == null) { 9030 return; 9031 } 9032 9033 enforceNotIsolatedCaller("publishContentProviders"); 9034 synchronized (this) { 9035 final ProcessRecord r = getRecordForAppLocked(caller); 9036 if (DEBUG_MU) 9037 Slog.v(TAG_MU, "ProcessRecord uid = " + r.uid); 9038 if (r == null) { 9039 throw new SecurityException( 9040 "Unable to find app for caller " + caller 9041 + " (pid=" + Binder.getCallingPid() 9042 + ") when publishing content providers"); 9043 } 9044 9045 final long origId = Binder.clearCallingIdentity(); 9046 9047 final int N = providers.size(); 9048 for (int i=0; i<N; i++) { 9049 ContentProviderHolder src = providers.get(i); 9050 if (src == null || src.info == null || src.provider == null) { 9051 continue; 9052 } 9053 ContentProviderRecord dst = r.pubProviders.get(src.info.name); 9054 if (DEBUG_MU) 9055 Slog.v(TAG_MU, "ContentProviderRecord uid = " + dst.uid); 9056 if (dst != null) { 9057 ComponentName comp = new ComponentName(dst.info.packageName, dst.info.name); 9058 mProviderMap.putProviderByClass(comp, dst); 9059 String names[] = dst.info.authority.split(";"); 9060 for (int j = 0; j < names.length; j++) { 9061 mProviderMap.putProviderByName(names[j], dst); 9062 } 9063 9064 int NL = mLaunchingProviders.size(); 9065 int j; 9066 for (j=0; j<NL; j++) { 9067 if (mLaunchingProviders.get(j) == dst) { 9068 mLaunchingProviders.remove(j); 9069 j--; 9070 NL--; 9071 } 9072 } 9073 synchronized (dst) { 9074 dst.provider = src.provider; 9075 dst.proc = r; 9076 dst.notifyAll(); 9077 } 9078 updateOomAdjLocked(r); 9079 } 9080 } 9081 9082 Binder.restoreCallingIdentity(origId); 9083 } 9084 } 9085 9086 public boolean refContentProvider(IBinder connection, int stable, int unstable) { 9087 ContentProviderConnection conn; 9088 try { 9089 conn = (ContentProviderConnection)connection; 9090 } catch (ClassCastException e) { 9091 String msg ="refContentProvider: " + connection 9092 + " not a ContentProviderConnection"; 9093 Slog.w(TAG, msg); 9094 throw new IllegalArgumentException(msg); 9095 } 9096 if (conn == null) { 9097 throw new NullPointerException("connection is null"); 9098 } 9099 9100 synchronized (this) { 9101 if (stable > 0) { 9102 conn.numStableIncs += stable; 9103 } 9104 stable = conn.stableCount + stable; 9105 if (stable < 0) { 9106 throw new IllegalStateException("stableCount < 0: " + stable); 9107 } 9108 9109 if (unstable > 0) { 9110 conn.numUnstableIncs += unstable; 9111 } 9112 unstable = conn.unstableCount + unstable; 9113 if (unstable < 0) { 9114 throw new IllegalStateException("unstableCount < 0: " + unstable); 9115 } 9116 9117 if ((stable+unstable) <= 0) { 9118 throw new IllegalStateException("ref counts can't go to zero here: stable=" 9119 + stable + " unstable=" + unstable); 9120 } 9121 conn.stableCount = stable; 9122 conn.unstableCount = unstable; 9123 return !conn.dead; 9124 } 9125 } 9126 9127 public void unstableProviderDied(IBinder connection) { 9128 ContentProviderConnection conn; 9129 try { 9130 conn = (ContentProviderConnection)connection; 9131 } catch (ClassCastException e) { 9132 String msg ="refContentProvider: " + connection 9133 + " not a ContentProviderConnection"; 9134 Slog.w(TAG, msg); 9135 throw new IllegalArgumentException(msg); 9136 } 9137 if (conn == null) { 9138 throw new NullPointerException("connection is null"); 9139 } 9140 9141 // Safely retrieve the content provider associated with the connection. 9142 IContentProvider provider; 9143 synchronized (this) { 9144 provider = conn.provider.provider; 9145 } 9146 9147 if (provider == null) { 9148 // Um, yeah, we're way ahead of you. 9149 return; 9150 } 9151 9152 // Make sure the caller is being honest with us. 9153 if (provider.asBinder().pingBinder()) { 9154 // Er, no, still looks good to us. 9155 synchronized (this) { 9156 Slog.w(TAG, "unstableProviderDied: caller " + Binder.getCallingUid() 9157 + " says " + conn + " died, but we don't agree"); 9158 return; 9159 } 9160 } 9161 9162 // Well look at that! It's dead! 9163 synchronized (this) { 9164 if (conn.provider.provider != provider) { 9165 // But something changed... good enough. 9166 return; 9167 } 9168 9169 ProcessRecord proc = conn.provider.proc; 9170 if (proc == null || proc.thread == null) { 9171 // Seems like the process is already cleaned up. 9172 return; 9173 } 9174 9175 // As far as we're concerned, this is just like receiving a 9176 // death notification... just a bit prematurely. 9177 Slog.i(TAG, "Process " + proc.processName + " (pid " + proc.pid 9178 + ") early provider death"); 9179 final long ident = Binder.clearCallingIdentity(); 9180 try { 9181 appDiedLocked(proc); 9182 } finally { 9183 Binder.restoreCallingIdentity(ident); 9184 } 9185 } 9186 } 9187 9188 @Override 9189 public void appNotRespondingViaProvider(IBinder connection) { 9190 enforceCallingPermission( 9191 android.Manifest.permission.REMOVE_TASKS, "appNotRespondingViaProvider()"); 9192 9193 final ContentProviderConnection conn = (ContentProviderConnection) connection; 9194 if (conn == null) { 9195 Slog.w(TAG, "ContentProviderConnection is null"); 9196 return; 9197 } 9198 9199 final ProcessRecord host = conn.provider.proc; 9200 if (host == null) { 9201 Slog.w(TAG, "Failed to find hosting ProcessRecord"); 9202 return; 9203 } 9204 9205 final long token = Binder.clearCallingIdentity(); 9206 try { 9207 appNotResponding(host, null, null, false, "ContentProvider not responding"); 9208 } finally { 9209 Binder.restoreCallingIdentity(token); 9210 } 9211 } 9212 9213 public final void installSystemProviders() { 9214 List<ProviderInfo> providers; 9215 synchronized (this) { 9216 ProcessRecord app = mProcessNames.get("system", Process.SYSTEM_UID); 9217 providers = generateApplicationProvidersLocked(app); 9218 if (providers != null) { 9219 for (int i=providers.size()-1; i>=0; i--) { 9220 ProviderInfo pi = (ProviderInfo)providers.get(i); 9221 if ((pi.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) == 0) { 9222 Slog.w(TAG, "Not installing system proc provider " + pi.name 9223 + ": not system .apk"); 9224 providers.remove(i); 9225 } 9226 } 9227 } 9228 } 9229 if (providers != null) { 9230 mSystemThread.installSystemProviders(providers); 9231 } 9232 9233 mCoreSettingsObserver = new CoreSettingsObserver(this); 9234 9235 //mUsageStatsService.monitorPackages(); 9236 } 9237 9238 /** 9239 * Allows apps to retrieve the MIME type of a URI. 9240 * If an app is in the same user as the ContentProvider, or if it is allowed to interact across 9241 * users, then it does not need permission to access the ContentProvider. 9242 * Either, it needs cross-user uri grants. 9243 * 9244 * CTS tests for this functionality can be run with "runtest cts-appsecurity". 9245 * 9246 * Test cases are at cts/tests/appsecurity-tests/test-apps/UsePermissionDiffCert/ 9247 * src/com/android/cts/usespermissiondiffcertapp/AccessPermissionWithDiffSigTest.java 9248 */ 9249 public String getProviderMimeType(Uri uri, int userId) { 9250 enforceNotIsolatedCaller("getProviderMimeType"); 9251 final String name = uri.getAuthority(); 9252 int callingUid = Binder.getCallingUid(); 9253 int callingPid = Binder.getCallingPid(); 9254 long ident = 0; 9255 boolean clearedIdentity = false; 9256 userId = unsafeConvertIncomingUser(userId); 9257 if (UserHandle.getUserId(callingUid) != userId) { 9258 if (checkComponentPermission(INTERACT_ACROSS_USERS, callingPid, 9259 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED 9260 || checkComponentPermission(INTERACT_ACROSS_USERS_FULL, callingPid, 9261 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED) { 9262 clearedIdentity = true; 9263 ident = Binder.clearCallingIdentity(); 9264 } 9265 } 9266 ContentProviderHolder holder = null; 9267 try { 9268 holder = getContentProviderExternalUnchecked(name, null, userId); 9269 if (holder != null) { 9270 return holder.provider.getType(uri); 9271 } 9272 } catch (RemoteException e) { 9273 Log.w(TAG, "Content provider dead retrieving " + uri, e); 9274 return null; 9275 } finally { 9276 // We need to clear the identity to call removeContentProviderExternalUnchecked 9277 if (!clearedIdentity) { 9278 ident = Binder.clearCallingIdentity(); 9279 } 9280 try { 9281 if (holder != null) { 9282 removeContentProviderExternalUnchecked(name, null, userId); 9283 } 9284 } finally { 9285 Binder.restoreCallingIdentity(ident); 9286 } 9287 } 9288 9289 return null; 9290 } 9291 9292 // ========================================================= 9293 // GLOBAL MANAGEMENT 9294 // ========================================================= 9295 9296 final ProcessRecord newProcessRecordLocked(ApplicationInfo info, String customProcess, 9297 boolean isolated, int isolatedUid) { 9298 String proc = customProcess != null ? customProcess : info.processName; 9299 BatteryStatsImpl.Uid.Proc ps = null; 9300 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 9301 int uid = info.uid; 9302 if (isolated) { 9303 if (isolatedUid == 0) { 9304 int userId = UserHandle.getUserId(uid); 9305 int stepsLeft = Process.LAST_ISOLATED_UID - Process.FIRST_ISOLATED_UID + 1; 9306 while (true) { 9307 if (mNextIsolatedProcessUid < Process.FIRST_ISOLATED_UID 9308 || mNextIsolatedProcessUid > Process.LAST_ISOLATED_UID) { 9309 mNextIsolatedProcessUid = Process.FIRST_ISOLATED_UID; 9310 } 9311 uid = UserHandle.getUid(userId, mNextIsolatedProcessUid); 9312 mNextIsolatedProcessUid++; 9313 if (mIsolatedProcesses.indexOfKey(uid) < 0) { 9314 // No process for this uid, use it. 9315 break; 9316 } 9317 stepsLeft--; 9318 if (stepsLeft <= 0) { 9319 return null; 9320 } 9321 } 9322 } else { 9323 // Special case for startIsolatedProcess (internal only), where 9324 // the uid of the isolated process is specified by the caller. 9325 uid = isolatedUid; 9326 } 9327 } 9328 return new ProcessRecord(stats, info, proc, uid); 9329 } 9330 9331 final ProcessRecord addAppLocked(ApplicationInfo info, boolean isolated, 9332 String abiOverride) { 9333 ProcessRecord app; 9334 if (!isolated) { 9335 app = getProcessRecordLocked(info.processName, info.uid, true); 9336 } else { 9337 app = null; 9338 } 9339 9340 if (app == null) { 9341 app = newProcessRecordLocked(info, null, isolated, 0); 9342 mProcessNames.put(info.processName, app.uid, app); 9343 if (isolated) { 9344 mIsolatedProcesses.put(app.uid, app); 9345 } 9346 updateLruProcessLocked(app, false, null); 9347 updateOomAdjLocked(); 9348 } 9349 9350 // This package really, really can not be stopped. 9351 try { 9352 AppGlobals.getPackageManager().setPackageStoppedState( 9353 info.packageName, false, UserHandle.getUserId(app.uid)); 9354 } catch (RemoteException e) { 9355 } catch (IllegalArgumentException e) { 9356 Slog.w(TAG, "Failed trying to unstop package " 9357 + info.packageName + ": " + e); 9358 } 9359 9360 if ((info.flags&(ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) 9361 == (ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) { 9362 app.persistent = true; 9363 app.maxAdj = ProcessList.PERSISTENT_PROC_ADJ; 9364 } 9365 if (app.thread == null && mPersistentStartingProcesses.indexOf(app) < 0) { 9366 mPersistentStartingProcesses.add(app); 9367 startProcessLocked(app, "added application", app.processName, abiOverride, 9368 null /* entryPoint */, null /* entryPointArgs */); 9369 } 9370 9371 return app; 9372 } 9373 9374 public void unhandledBack() { 9375 enforceCallingPermission(android.Manifest.permission.FORCE_BACK, 9376 "unhandledBack()"); 9377 9378 synchronized(this) { 9379 final long origId = Binder.clearCallingIdentity(); 9380 try { 9381 getFocusedStack().unhandledBackLocked(); 9382 } finally { 9383 Binder.restoreCallingIdentity(origId); 9384 } 9385 } 9386 } 9387 9388 public ParcelFileDescriptor openContentUri(Uri uri) throws RemoteException { 9389 enforceNotIsolatedCaller("openContentUri"); 9390 final int userId = UserHandle.getCallingUserId(); 9391 String name = uri.getAuthority(); 9392 ContentProviderHolder cph = getContentProviderExternalUnchecked(name, null, userId); 9393 ParcelFileDescriptor pfd = null; 9394 if (cph != null) { 9395 // We record the binder invoker's uid in thread-local storage before 9396 // going to the content provider to open the file. Later, in the code 9397 // that handles all permissions checks, we look for this uid and use 9398 // that rather than the Activity Manager's own uid. The effect is that 9399 // we do the check against the caller's permissions even though it looks 9400 // to the content provider like the Activity Manager itself is making 9401 // the request. 9402 sCallerIdentity.set(new Identity( 9403 Binder.getCallingPid(), Binder.getCallingUid())); 9404 try { 9405 pfd = cph.provider.openFile(null, uri, "r", null); 9406 } catch (FileNotFoundException e) { 9407 // do nothing; pfd will be returned null 9408 } finally { 9409 // Ensure that whatever happens, we clean up the identity state 9410 sCallerIdentity.remove(); 9411 } 9412 9413 // We've got the fd now, so we're done with the provider. 9414 removeContentProviderExternalUnchecked(name, null, userId); 9415 } else { 9416 Slog.d(TAG, "Failed to get provider for authority '" + name + "'"); 9417 } 9418 return pfd; 9419 } 9420 9421 // Actually is sleeping or shutting down or whatever else in the future 9422 // is an inactive state. 9423 public boolean isSleepingOrShuttingDown() { 9424 return mSleeping || mShuttingDown; 9425 } 9426 9427 public boolean isSleeping() { 9428 return mSleeping; 9429 } 9430 9431 void goingToSleep() { 9432 synchronized(this) { 9433 mWentToSleep = true; 9434 updateEventDispatchingLocked(); 9435 goToSleepIfNeededLocked(); 9436 } 9437 } 9438 9439 void finishRunningVoiceLocked() { 9440 if (mRunningVoice) { 9441 mRunningVoice = false; 9442 goToSleepIfNeededLocked(); 9443 } 9444 } 9445 9446 void goToSleepIfNeededLocked() { 9447 if (mWentToSleep && !mRunningVoice) { 9448 if (!mSleeping) { 9449 mSleeping = true; 9450 mStackSupervisor.goingToSleepLocked(); 9451 9452 // Initialize the wake times of all processes. 9453 checkExcessivePowerUsageLocked(false); 9454 mHandler.removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 9455 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 9456 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 9457 } 9458 } 9459 } 9460 9461 void notifyTaskPersisterLocked(TaskRecord task, boolean flush) { 9462 if (task != null && task.stack != null && task.stack.isHomeStack()) { 9463 // Never persist the home stack. 9464 return; 9465 } 9466 mTaskPersister.wakeup(task, flush); 9467 } 9468 9469 @Override 9470 public boolean shutdown(int timeout) { 9471 if (checkCallingPermission(android.Manifest.permission.SHUTDOWN) 9472 != PackageManager.PERMISSION_GRANTED) { 9473 throw new SecurityException("Requires permission " 9474 + android.Manifest.permission.SHUTDOWN); 9475 } 9476 9477 boolean timedout = false; 9478 9479 synchronized(this) { 9480 mShuttingDown = true; 9481 updateEventDispatchingLocked(); 9482 timedout = mStackSupervisor.shutdownLocked(timeout); 9483 } 9484 9485 mAppOpsService.shutdown(); 9486 if (mUsageStatsService != null) { 9487 mUsageStatsService.prepareShutdown(); 9488 } 9489 mBatteryStatsService.shutdown(); 9490 synchronized (this) { 9491 mProcessStats.shutdownLocked(); 9492 } 9493 notifyTaskPersisterLocked(null, true); 9494 9495 return timedout; 9496 } 9497 9498 public final void activitySlept(IBinder token) { 9499 if (localLOGV) Slog.v(TAG, "Activity slept: token=" + token); 9500 9501 final long origId = Binder.clearCallingIdentity(); 9502 9503 synchronized (this) { 9504 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9505 if (r != null) { 9506 mStackSupervisor.activitySleptLocked(r); 9507 } 9508 } 9509 9510 Binder.restoreCallingIdentity(origId); 9511 } 9512 9513 void logLockScreen(String msg) { 9514 if (DEBUG_LOCKSCREEN) Slog.d(TAG, Debug.getCallers(2) + ":" + msg + 9515 " mLockScreenShown=" + mLockScreenShown + " mWentToSleep=" + 9516 mWentToSleep + " mSleeping=" + mSleeping); 9517 } 9518 9519 private void comeOutOfSleepIfNeededLocked() { 9520 if ((!mWentToSleep && !mLockScreenShown) || mRunningVoice) { 9521 if (mSleeping) { 9522 mSleeping = false; 9523 mStackSupervisor.comeOutOfSleepIfNeededLocked(); 9524 } 9525 } 9526 } 9527 9528 void wakingUp() { 9529 synchronized(this) { 9530 mWentToSleep = false; 9531 updateEventDispatchingLocked(); 9532 comeOutOfSleepIfNeededLocked(); 9533 } 9534 } 9535 9536 void startRunningVoiceLocked() { 9537 if (!mRunningVoice) { 9538 mRunningVoice = true; 9539 comeOutOfSleepIfNeededLocked(); 9540 } 9541 } 9542 9543 private void updateEventDispatchingLocked() { 9544 mWindowManager.setEventDispatching(mBooted && !mWentToSleep && !mShuttingDown); 9545 } 9546 9547 public void setLockScreenShown(boolean shown) { 9548 if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER) 9549 != PackageManager.PERMISSION_GRANTED) { 9550 throw new SecurityException("Requires permission " 9551 + android.Manifest.permission.DEVICE_POWER); 9552 } 9553 9554 synchronized(this) { 9555 long ident = Binder.clearCallingIdentity(); 9556 try { 9557 if (DEBUG_LOCKSCREEN) logLockScreen(" shown=" + shown); 9558 mLockScreenShown = shown; 9559 comeOutOfSleepIfNeededLocked(); 9560 } finally { 9561 Binder.restoreCallingIdentity(ident); 9562 } 9563 } 9564 } 9565 9566 @Override 9567 public void stopAppSwitches() { 9568 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 9569 != PackageManager.PERMISSION_GRANTED) { 9570 throw new SecurityException("Requires permission " 9571 + android.Manifest.permission.STOP_APP_SWITCHES); 9572 } 9573 9574 synchronized(this) { 9575 mAppSwitchesAllowedTime = SystemClock.uptimeMillis() 9576 + APP_SWITCH_DELAY_TIME; 9577 mDidAppSwitch = false; 9578 mHandler.removeMessages(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 9579 Message msg = mHandler.obtainMessage(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 9580 mHandler.sendMessageDelayed(msg, APP_SWITCH_DELAY_TIME); 9581 } 9582 } 9583 9584 public void resumeAppSwitches() { 9585 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 9586 != PackageManager.PERMISSION_GRANTED) { 9587 throw new SecurityException("Requires permission " 9588 + android.Manifest.permission.STOP_APP_SWITCHES); 9589 } 9590 9591 synchronized(this) { 9592 // Note that we don't execute any pending app switches... we will 9593 // let those wait until either the timeout, or the next start 9594 // activity request. 9595 mAppSwitchesAllowedTime = 0; 9596 } 9597 } 9598 9599 boolean checkAppSwitchAllowedLocked(int callingPid, int callingUid, 9600 String name) { 9601 if (mAppSwitchesAllowedTime < SystemClock.uptimeMillis()) { 9602 return true; 9603 } 9604 9605 final int perm = checkComponentPermission( 9606 android.Manifest.permission.STOP_APP_SWITCHES, callingPid, 9607 callingUid, -1, true); 9608 if (perm == PackageManager.PERMISSION_GRANTED) { 9609 return true; 9610 } 9611 9612 Slog.w(TAG, name + " request from " + callingUid + " stopped"); 9613 return false; 9614 } 9615 9616 public void setDebugApp(String packageName, boolean waitForDebugger, 9617 boolean persistent) { 9618 enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP, 9619 "setDebugApp()"); 9620 9621 long ident = Binder.clearCallingIdentity(); 9622 try { 9623 // Note that this is not really thread safe if there are multiple 9624 // callers into it at the same time, but that's not a situation we 9625 // care about. 9626 if (persistent) { 9627 final ContentResolver resolver = mContext.getContentResolver(); 9628 Settings.Global.putString( 9629 resolver, Settings.Global.DEBUG_APP, 9630 packageName); 9631 Settings.Global.putInt( 9632 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 9633 waitForDebugger ? 1 : 0); 9634 } 9635 9636 synchronized (this) { 9637 if (!persistent) { 9638 mOrigDebugApp = mDebugApp; 9639 mOrigWaitForDebugger = mWaitForDebugger; 9640 } 9641 mDebugApp = packageName; 9642 mWaitForDebugger = waitForDebugger; 9643 mDebugTransient = !persistent; 9644 if (packageName != null) { 9645 forceStopPackageLocked(packageName, -1, false, false, true, true, 9646 false, UserHandle.USER_ALL, "set debug app"); 9647 } 9648 } 9649 } finally { 9650 Binder.restoreCallingIdentity(ident); 9651 } 9652 } 9653 9654 void setOpenGlTraceApp(ApplicationInfo app, String processName) { 9655 synchronized (this) { 9656 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 9657 if (!isDebuggable) { 9658 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 9659 throw new SecurityException("Process not debuggable: " + app.packageName); 9660 } 9661 } 9662 9663 mOpenGlTraceApp = processName; 9664 } 9665 } 9666 9667 void setProfileApp(ApplicationInfo app, String processName, String profileFile, 9668 ParcelFileDescriptor profileFd, boolean autoStopProfiler) { 9669 synchronized (this) { 9670 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 9671 if (!isDebuggable) { 9672 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 9673 throw new SecurityException("Process not debuggable: " + app.packageName); 9674 } 9675 } 9676 mProfileApp = processName; 9677 mProfileFile = profileFile; 9678 if (mProfileFd != null) { 9679 try { 9680 mProfileFd.close(); 9681 } catch (IOException e) { 9682 } 9683 mProfileFd = null; 9684 } 9685 mProfileFd = profileFd; 9686 mProfileType = 0; 9687 mAutoStopProfiler = autoStopProfiler; 9688 } 9689 } 9690 9691 @Override 9692 public void setAlwaysFinish(boolean enabled) { 9693 enforceCallingPermission(android.Manifest.permission.SET_ALWAYS_FINISH, 9694 "setAlwaysFinish()"); 9695 9696 Settings.Global.putInt( 9697 mContext.getContentResolver(), 9698 Settings.Global.ALWAYS_FINISH_ACTIVITIES, enabled ? 1 : 0); 9699 9700 synchronized (this) { 9701 mAlwaysFinishActivities = enabled; 9702 } 9703 } 9704 9705 @Override 9706 public void setActivityController(IActivityController controller) { 9707 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 9708 "setActivityController()"); 9709 synchronized (this) { 9710 mController = controller; 9711 Watchdog.getInstance().setActivityController(controller); 9712 } 9713 } 9714 9715 @Override 9716 public void setUserIsMonkey(boolean userIsMonkey) { 9717 synchronized (this) { 9718 synchronized (mPidsSelfLocked) { 9719 final int callingPid = Binder.getCallingPid(); 9720 ProcessRecord precessRecord = mPidsSelfLocked.get(callingPid); 9721 if (precessRecord == null) { 9722 throw new SecurityException("Unknown process: " + callingPid); 9723 } 9724 if (precessRecord.instrumentationUiAutomationConnection == null) { 9725 throw new SecurityException("Only an instrumentation process " 9726 + "with a UiAutomation can call setUserIsMonkey"); 9727 } 9728 } 9729 mUserIsMonkey = userIsMonkey; 9730 } 9731 } 9732 9733 @Override 9734 public boolean isUserAMonkey() { 9735 synchronized (this) { 9736 // If there is a controller also implies the user is a monkey. 9737 return (mUserIsMonkey || mController != null); 9738 } 9739 } 9740 9741 public void requestBugReport() { 9742 enforceCallingPermission(android.Manifest.permission.DUMP, "requestBugReport"); 9743 SystemProperties.set("ctl.start", "bugreport"); 9744 } 9745 9746 public static long getInputDispatchingTimeoutLocked(ActivityRecord r) { 9747 return r != null ? getInputDispatchingTimeoutLocked(r.app) : KEY_DISPATCHING_TIMEOUT; 9748 } 9749 9750 public static long getInputDispatchingTimeoutLocked(ProcessRecord r) { 9751 if (r != null && (r.instrumentationClass != null || r.usingWrapper)) { 9752 return INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT; 9753 } 9754 return KEY_DISPATCHING_TIMEOUT; 9755 } 9756 9757 @Override 9758 public long inputDispatchingTimedOut(int pid, final boolean aboveSystem, String reason) { 9759 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 9760 != PackageManager.PERMISSION_GRANTED) { 9761 throw new SecurityException("Requires permission " 9762 + android.Manifest.permission.FILTER_EVENTS); 9763 } 9764 ProcessRecord proc; 9765 long timeout; 9766 synchronized (this) { 9767 synchronized (mPidsSelfLocked) { 9768 proc = mPidsSelfLocked.get(pid); 9769 } 9770 timeout = getInputDispatchingTimeoutLocked(proc); 9771 } 9772 9773 if (!inputDispatchingTimedOut(proc, null, null, aboveSystem, reason)) { 9774 return -1; 9775 } 9776 9777 return timeout; 9778 } 9779 9780 /** 9781 * Handle input dispatching timeouts. 9782 * Returns whether input dispatching should be aborted or not. 9783 */ 9784 public boolean inputDispatchingTimedOut(final ProcessRecord proc, 9785 final ActivityRecord activity, final ActivityRecord parent, 9786 final boolean aboveSystem, String reason) { 9787 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 9788 != PackageManager.PERMISSION_GRANTED) { 9789 throw new SecurityException("Requires permission " 9790 + android.Manifest.permission.FILTER_EVENTS); 9791 } 9792 9793 final String annotation; 9794 if (reason == null) { 9795 annotation = "Input dispatching timed out"; 9796 } else { 9797 annotation = "Input dispatching timed out (" + reason + ")"; 9798 } 9799 9800 if (proc != null) { 9801 synchronized (this) { 9802 if (proc.debugging) { 9803 return false; 9804 } 9805 9806 if (mDidDexOpt) { 9807 // Give more time since we were dexopting. 9808 mDidDexOpt = false; 9809 return false; 9810 } 9811 9812 if (proc.instrumentationClass != null) { 9813 Bundle info = new Bundle(); 9814 info.putString("shortMsg", "keyDispatchingTimedOut"); 9815 info.putString("longMsg", annotation); 9816 finishInstrumentationLocked(proc, Activity.RESULT_CANCELED, info); 9817 return true; 9818 } 9819 } 9820 mHandler.post(new Runnable() { 9821 @Override 9822 public void run() { 9823 appNotResponding(proc, activity, parent, aboveSystem, annotation); 9824 } 9825 }); 9826 } 9827 9828 return true; 9829 } 9830 9831 public Bundle getAssistContextExtras(int requestType) { 9832 enforceCallingPermission(android.Manifest.permission.GET_TOP_ACTIVITY_INFO, 9833 "getAssistContextExtras()"); 9834 PendingAssistExtras pae; 9835 Bundle extras = new Bundle(); 9836 synchronized (this) { 9837 ActivityRecord activity = getFocusedStack().mResumedActivity; 9838 if (activity == null) { 9839 Slog.w(TAG, "getAssistContextExtras failed: no resumed activity"); 9840 return null; 9841 } 9842 extras.putString(Intent.EXTRA_ASSIST_PACKAGE, activity.packageName); 9843 if (activity.app == null || activity.app.thread == null) { 9844 Slog.w(TAG, "getAssistContextExtras failed: no process for " + activity); 9845 return extras; 9846 } 9847 if (activity.app.pid == Binder.getCallingPid()) { 9848 Slog.w(TAG, "getAssistContextExtras failed: request process same as " + activity); 9849 return extras; 9850 } 9851 pae = new PendingAssistExtras(activity); 9852 try { 9853 activity.app.thread.requestAssistContextExtras(activity.appToken, pae, 9854 requestType); 9855 mPendingAssistExtras.add(pae); 9856 mHandler.postDelayed(pae, PENDING_ASSIST_EXTRAS_TIMEOUT); 9857 } catch (RemoteException e) { 9858 Slog.w(TAG, "getAssistContextExtras failed: crash calling " + activity); 9859 return extras; 9860 } 9861 } 9862 synchronized (pae) { 9863 while (!pae.haveResult) { 9864 try { 9865 pae.wait(); 9866 } catch (InterruptedException e) { 9867 } 9868 } 9869 if (pae.result != null) { 9870 extras.putBundle(Intent.EXTRA_ASSIST_CONTEXT, pae.result); 9871 } 9872 } 9873 synchronized (this) { 9874 mPendingAssistExtras.remove(pae); 9875 mHandler.removeCallbacks(pae); 9876 } 9877 return extras; 9878 } 9879 9880 public void reportAssistContextExtras(IBinder token, Bundle extras) { 9881 PendingAssistExtras pae = (PendingAssistExtras)token; 9882 synchronized (pae) { 9883 pae.result = extras; 9884 pae.haveResult = true; 9885 pae.notifyAll(); 9886 } 9887 } 9888 9889 public void registerProcessObserver(IProcessObserver observer) { 9890 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 9891 "registerProcessObserver()"); 9892 synchronized (this) { 9893 mProcessObservers.register(observer); 9894 } 9895 } 9896 9897 @Override 9898 public void unregisterProcessObserver(IProcessObserver observer) { 9899 synchronized (this) { 9900 mProcessObservers.unregister(observer); 9901 } 9902 } 9903 9904 @Override 9905 public boolean convertFromTranslucent(IBinder token) { 9906 final long origId = Binder.clearCallingIdentity(); 9907 try { 9908 synchronized (this) { 9909 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9910 if (r == null) { 9911 return false; 9912 } 9913 if (r.changeWindowTranslucency(true)) { 9914 mWindowManager.setAppFullscreen(token, true); 9915 r.task.stack.releaseBackgroundResources(); 9916 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9917 return true; 9918 } 9919 return false; 9920 } 9921 } finally { 9922 Binder.restoreCallingIdentity(origId); 9923 } 9924 } 9925 9926 @Override 9927 public boolean convertToTranslucent(IBinder token, ActivityOptions options) { 9928 final long origId = Binder.clearCallingIdentity(); 9929 try { 9930 synchronized (this) { 9931 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9932 if (r == null) { 9933 return false; 9934 } 9935 int index = r.task.mActivities.lastIndexOf(r); 9936 if (index > 0) { 9937 ActivityRecord under = r.task.mActivities.get(index - 1); 9938 under.returningOptions = options; 9939 } 9940 if (r.changeWindowTranslucency(false)) { 9941 r.task.stack.convertToTranslucent(r); 9942 mWindowManager.setAppFullscreen(token, false); 9943 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9944 return true; 9945 } else { 9946 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9947 return false; 9948 } 9949 } 9950 } finally { 9951 Binder.restoreCallingIdentity(origId); 9952 } 9953 } 9954 9955 @Override 9956 public boolean requestVisibleBehind(IBinder token, boolean visible) { 9957 final long origId = Binder.clearCallingIdentity(); 9958 try { 9959 synchronized (this) { 9960 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9961 if (r != null) { 9962 return mStackSupervisor.requestVisibleBehindLocked(r, visible); 9963 } 9964 } 9965 return false; 9966 } finally { 9967 Binder.restoreCallingIdentity(origId); 9968 } 9969 } 9970 9971 @Override 9972 public boolean isBackgroundVisibleBehind(IBinder token) { 9973 final long origId = Binder.clearCallingIdentity(); 9974 try { 9975 synchronized (this) { 9976 final ActivityStack stack = ActivityRecord.getStackLocked(token); 9977 final boolean visible = stack == null ? false : stack.hasVisibleBehindActivity(); 9978 if (ActivityStackSupervisor.DEBUG_VISIBLE_BEHIND) Slog.d(TAG, 9979 "isBackgroundVisibleBehind: stack=" + stack + " visible=" + visible); 9980 return visible; 9981 } 9982 } finally { 9983 Binder.restoreCallingIdentity(origId); 9984 } 9985 } 9986 9987 @Override 9988 public ActivityOptions getActivityOptions(IBinder token) { 9989 final long origId = Binder.clearCallingIdentity(); 9990 try { 9991 synchronized (this) { 9992 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9993 if (r != null) { 9994 final ActivityOptions activityOptions = r.pendingOptions; 9995 r.pendingOptions = null; 9996 return activityOptions; 9997 } 9998 return null; 9999 } 10000 } finally { 10001 Binder.restoreCallingIdentity(origId); 10002 } 10003 } 10004 10005 @Override 10006 public void setImmersive(IBinder token, boolean immersive) { 10007 synchronized(this) { 10008 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10009 if (r == null) { 10010 throw new IllegalArgumentException(); 10011 } 10012 r.immersive = immersive; 10013 10014 // update associated state if we're frontmost 10015 if (r == mFocusedActivity) { 10016 if (DEBUG_IMMERSIVE) { 10017 Slog.d(TAG, "Frontmost changed immersion: "+ r); 10018 } 10019 applyUpdateLockStateLocked(r); 10020 } 10021 } 10022 } 10023 10024 @Override 10025 public boolean isImmersive(IBinder token) { 10026 synchronized (this) { 10027 ActivityRecord r = ActivityRecord.isInStackLocked(token); 10028 if (r == null) { 10029 throw new IllegalArgumentException(); 10030 } 10031 return r.immersive; 10032 } 10033 } 10034 10035 public boolean isTopActivityImmersive() { 10036 enforceNotIsolatedCaller("startActivity"); 10037 synchronized (this) { 10038 ActivityRecord r = getFocusedStack().topRunningActivityLocked(null); 10039 return (r != null) ? r.immersive : false; 10040 } 10041 } 10042 10043 @Override 10044 public boolean isTopOfTask(IBinder token) { 10045 synchronized (this) { 10046 ActivityRecord r = ActivityRecord.isInStackLocked(token); 10047 if (r == null) { 10048 throw new IllegalArgumentException(); 10049 } 10050 return r.task.getTopActivity() == r; 10051 } 10052 } 10053 10054 public final void enterSafeMode() { 10055 synchronized(this) { 10056 // It only makes sense to do this before the system is ready 10057 // and started launching other packages. 10058 if (!mSystemReady) { 10059 try { 10060 AppGlobals.getPackageManager().enterSafeMode(); 10061 } catch (RemoteException e) { 10062 } 10063 } 10064 10065 mSafeMode = true; 10066 } 10067 } 10068 10069 public final void showSafeModeOverlay() { 10070 View v = LayoutInflater.from(mContext).inflate( 10071 com.android.internal.R.layout.safe_mode, null); 10072 WindowManager.LayoutParams lp = new WindowManager.LayoutParams(); 10073 lp.type = WindowManager.LayoutParams.TYPE_SECURE_SYSTEM_OVERLAY; 10074 lp.width = WindowManager.LayoutParams.WRAP_CONTENT; 10075 lp.height = WindowManager.LayoutParams.WRAP_CONTENT; 10076 lp.gravity = Gravity.BOTTOM | Gravity.START; 10077 lp.format = v.getBackground().getOpacity(); 10078 lp.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE 10079 | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE; 10080 lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; 10081 ((WindowManager)mContext.getSystemService( 10082 Context.WINDOW_SERVICE)).addView(v, lp); 10083 } 10084 10085 public void noteWakeupAlarm(IIntentSender sender, int sourceUid, String sourcePkg) { 10086 if (!(sender instanceof PendingIntentRecord)) { 10087 return; 10088 } 10089 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 10090 synchronized (stats) { 10091 if (mBatteryStatsService.isOnBattery()) { 10092 mBatteryStatsService.enforceCallingPermission(); 10093 PendingIntentRecord rec = (PendingIntentRecord)sender; 10094 int MY_UID = Binder.getCallingUid(); 10095 int uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid; 10096 BatteryStatsImpl.Uid.Pkg pkg = 10097 stats.getPackageStatsLocked(sourceUid >= 0 ? sourceUid : uid, 10098 sourcePkg != null ? sourcePkg : rec.key.packageName); 10099 pkg.incWakeupsLocked(); 10100 } 10101 } 10102 } 10103 10104 public boolean killPids(int[] pids, String pReason, boolean secure) { 10105 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10106 throw new SecurityException("killPids only available to the system"); 10107 } 10108 String reason = (pReason == null) ? "Unknown" : pReason; 10109 // XXX Note: don't acquire main activity lock here, because the window 10110 // manager calls in with its locks held. 10111 10112 boolean killed = false; 10113 synchronized (mPidsSelfLocked) { 10114 int[] types = new int[pids.length]; 10115 int worstType = 0; 10116 for (int i=0; i<pids.length; i++) { 10117 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 10118 if (proc != null) { 10119 int type = proc.setAdj; 10120 types[i] = type; 10121 if (type > worstType) { 10122 worstType = type; 10123 } 10124 } 10125 } 10126 10127 // If the worst oom_adj is somewhere in the cached proc LRU range, 10128 // then constrain it so we will kill all cached procs. 10129 if (worstType < ProcessList.CACHED_APP_MAX_ADJ 10130 && worstType > ProcessList.CACHED_APP_MIN_ADJ) { 10131 worstType = ProcessList.CACHED_APP_MIN_ADJ; 10132 } 10133 10134 // If this is not a secure call, don't let it kill processes that 10135 // are important. 10136 if (!secure && worstType < ProcessList.SERVICE_ADJ) { 10137 worstType = ProcessList.SERVICE_ADJ; 10138 } 10139 10140 Slog.w(TAG, "Killing processes " + reason + " at adjustment " + worstType); 10141 for (int i=0; i<pids.length; i++) { 10142 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 10143 if (proc == null) { 10144 continue; 10145 } 10146 int adj = proc.setAdj; 10147 if (adj >= worstType && !proc.killedByAm) { 10148 killUnneededProcessLocked(proc, reason); 10149 killed = true; 10150 } 10151 } 10152 } 10153 return killed; 10154 } 10155 10156 @Override 10157 public void killUid(int uid, String reason) { 10158 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10159 throw new SecurityException("killUid only available to the system"); 10160 } 10161 synchronized (this) { 10162 killPackageProcessesLocked(null, UserHandle.getAppId(uid), UserHandle.getUserId(uid), 10163 ProcessList.FOREGROUND_APP_ADJ-1, false, true, true, false, 10164 reason != null ? reason : "kill uid"); 10165 } 10166 } 10167 10168 @Override 10169 public boolean killProcessesBelowForeground(String reason) { 10170 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10171 throw new SecurityException("killProcessesBelowForeground() only available to system"); 10172 } 10173 10174 return killProcessesBelowAdj(ProcessList.FOREGROUND_APP_ADJ, reason); 10175 } 10176 10177 private boolean killProcessesBelowAdj(int belowAdj, String reason) { 10178 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10179 throw new SecurityException("killProcessesBelowAdj() only available to system"); 10180 } 10181 10182 boolean killed = false; 10183 synchronized (mPidsSelfLocked) { 10184 final int size = mPidsSelfLocked.size(); 10185 for (int i = 0; i < size; i++) { 10186 final int pid = mPidsSelfLocked.keyAt(i); 10187 final ProcessRecord proc = mPidsSelfLocked.valueAt(i); 10188 if (proc == null) continue; 10189 10190 final int adj = proc.setAdj; 10191 if (adj > belowAdj && !proc.killedByAm) { 10192 killUnneededProcessLocked(proc, reason); 10193 killed = true; 10194 } 10195 } 10196 } 10197 return killed; 10198 } 10199 10200 @Override 10201 public void hang(final IBinder who, boolean allowRestart) { 10202 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 10203 != PackageManager.PERMISSION_GRANTED) { 10204 throw new SecurityException("Requires permission " 10205 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 10206 } 10207 10208 final IBinder.DeathRecipient death = new DeathRecipient() { 10209 @Override 10210 public void binderDied() { 10211 synchronized (this) { 10212 notifyAll(); 10213 } 10214 } 10215 }; 10216 10217 try { 10218 who.linkToDeath(death, 0); 10219 } catch (RemoteException e) { 10220 Slog.w(TAG, "hang: given caller IBinder is already dead."); 10221 return; 10222 } 10223 10224 synchronized (this) { 10225 Watchdog.getInstance().setAllowRestart(allowRestart); 10226 Slog.i(TAG, "Hanging system process at request of pid " + Binder.getCallingPid()); 10227 synchronized (death) { 10228 while (who.isBinderAlive()) { 10229 try { 10230 death.wait(); 10231 } catch (InterruptedException e) { 10232 } 10233 } 10234 } 10235 Watchdog.getInstance().setAllowRestart(true); 10236 } 10237 } 10238 10239 @Override 10240 public void restart() { 10241 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 10242 != PackageManager.PERMISSION_GRANTED) { 10243 throw new SecurityException("Requires permission " 10244 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 10245 } 10246 10247 Log.i(TAG, "Sending shutdown broadcast..."); 10248 10249 BroadcastReceiver br = new BroadcastReceiver() { 10250 @Override public void onReceive(Context context, Intent intent) { 10251 // Now the broadcast is done, finish up the low-level shutdown. 10252 Log.i(TAG, "Shutting down activity manager..."); 10253 shutdown(10000); 10254 Log.i(TAG, "Shutdown complete, restarting!"); 10255 Process.killProcess(Process.myPid()); 10256 System.exit(10); 10257 } 10258 }; 10259 10260 // First send the high-level shut down broadcast. 10261 Intent intent = new Intent(Intent.ACTION_SHUTDOWN); 10262 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 10263 intent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 10264 /* For now we are not doing a clean shutdown, because things seem to get unhappy. 10265 mContext.sendOrderedBroadcastAsUser(intent, 10266 UserHandle.ALL, null, br, mHandler, 0, null, null); 10267 */ 10268 br.onReceive(mContext, intent); 10269 } 10270 10271 private long getLowRamTimeSinceIdle(long now) { 10272 return mLowRamTimeSinceLastIdle + (mLowRamStartTime > 0 ? (now-mLowRamStartTime) : 0); 10273 } 10274 10275 @Override 10276 public void performIdleMaintenance() { 10277 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 10278 != PackageManager.PERMISSION_GRANTED) { 10279 throw new SecurityException("Requires permission " 10280 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 10281 } 10282 10283 synchronized (this) { 10284 final long now = SystemClock.uptimeMillis(); 10285 final long timeSinceLastIdle = now - mLastIdleTime; 10286 final long lowRamSinceLastIdle = getLowRamTimeSinceIdle(now); 10287 mLastIdleTime = now; 10288 mLowRamTimeSinceLastIdle = 0; 10289 if (mLowRamStartTime != 0) { 10290 mLowRamStartTime = now; 10291 } 10292 10293 StringBuilder sb = new StringBuilder(128); 10294 sb.append("Idle maintenance over "); 10295 TimeUtils.formatDuration(timeSinceLastIdle, sb); 10296 sb.append(" low RAM for "); 10297 TimeUtils.formatDuration(lowRamSinceLastIdle, sb); 10298 Slog.i(TAG, sb.toString()); 10299 10300 // If at least 1/3 of our time since the last idle period has been spent 10301 // with RAM low, then we want to kill processes. 10302 boolean doKilling = lowRamSinceLastIdle > (timeSinceLastIdle/3); 10303 10304 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 10305 ProcessRecord proc = mLruProcesses.get(i); 10306 if (proc.notCachedSinceIdle) { 10307 if (proc.setProcState > ActivityManager.PROCESS_STATE_TOP 10308 && proc.setProcState <= ActivityManager.PROCESS_STATE_SERVICE) { 10309 if (doKilling && proc.initialIdlePss != 0 10310 && proc.lastPss > ((proc.initialIdlePss*3)/2)) { 10311 killUnneededProcessLocked(proc, "idle maint (pss " + proc.lastPss 10312 + " from " + proc.initialIdlePss + ")"); 10313 } 10314 } 10315 } else if (proc.setProcState < ActivityManager.PROCESS_STATE_HOME) { 10316 proc.notCachedSinceIdle = true; 10317 proc.initialIdlePss = 0; 10318 proc.nextPssTime = ProcessList.computeNextPssTime(proc.curProcState, true, 10319 isSleeping(), now); 10320 } 10321 } 10322 10323 mHandler.removeMessages(REQUEST_ALL_PSS_MSG); 10324 mHandler.sendEmptyMessageDelayed(REQUEST_ALL_PSS_MSG, 2*60*1000); 10325 } 10326 } 10327 10328 private void retrieveSettings() { 10329 final ContentResolver resolver = mContext.getContentResolver(); 10330 String debugApp = Settings.Global.getString( 10331 resolver, Settings.Global.DEBUG_APP); 10332 boolean waitForDebugger = Settings.Global.getInt( 10333 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 0) != 0; 10334 boolean alwaysFinishActivities = Settings.Global.getInt( 10335 resolver, Settings.Global.ALWAYS_FINISH_ACTIVITIES, 0) != 0; 10336 boolean forceRtl = Settings.Global.getInt( 10337 resolver, Settings.Global.DEVELOPMENT_FORCE_RTL, 0) != 0; 10338 // Transfer any global setting for forcing RTL layout, into a System Property 10339 SystemProperties.set(Settings.Global.DEVELOPMENT_FORCE_RTL, forceRtl ? "1":"0"); 10340 10341 Configuration configuration = new Configuration(); 10342 Settings.System.getConfiguration(resolver, configuration); 10343 if (forceRtl) { 10344 // This will take care of setting the correct layout direction flags 10345 configuration.setLayoutDirection(configuration.locale); 10346 } 10347 10348 synchronized (this) { 10349 mDebugApp = mOrigDebugApp = debugApp; 10350 mWaitForDebugger = mOrigWaitForDebugger = waitForDebugger; 10351 mAlwaysFinishActivities = alwaysFinishActivities; 10352 // This happens before any activities are started, so we can 10353 // change mConfiguration in-place. 10354 updateConfigurationLocked(configuration, null, false, true); 10355 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Initial config: " + mConfiguration); 10356 } 10357 } 10358 10359 public boolean testIsSystemReady() { 10360 // no need to synchronize(this) just to read & return the value 10361 return mSystemReady; 10362 } 10363 10364 private static File getCalledPreBootReceiversFile() { 10365 File dataDir = Environment.getDataDirectory(); 10366 File systemDir = new File(dataDir, "system"); 10367 File fname = new File(systemDir, CALLED_PRE_BOOTS_FILENAME); 10368 return fname; 10369 } 10370 10371 private static ArrayList<ComponentName> readLastDonePreBootReceivers() { 10372 ArrayList<ComponentName> lastDoneReceivers = new ArrayList<ComponentName>(); 10373 File file = getCalledPreBootReceiversFile(); 10374 FileInputStream fis = null; 10375 try { 10376 fis = new FileInputStream(file); 10377 DataInputStream dis = new DataInputStream(new BufferedInputStream(fis, 2048)); 10378 int fvers = dis.readInt(); 10379 if (fvers == LAST_PREBOOT_DELIVERED_FILE_VERSION) { 10380 String vers = dis.readUTF(); 10381 String codename = dis.readUTF(); 10382 String build = dis.readUTF(); 10383 if (android.os.Build.VERSION.RELEASE.equals(vers) 10384 && android.os.Build.VERSION.CODENAME.equals(codename) 10385 && android.os.Build.VERSION.INCREMENTAL.equals(build)) { 10386 int num = dis.readInt(); 10387 while (num > 0) { 10388 num--; 10389 String pkg = dis.readUTF(); 10390 String cls = dis.readUTF(); 10391 lastDoneReceivers.add(new ComponentName(pkg, cls)); 10392 } 10393 } 10394 } 10395 } catch (FileNotFoundException e) { 10396 } catch (IOException e) { 10397 Slog.w(TAG, "Failure reading last done pre-boot receivers", e); 10398 } finally { 10399 if (fis != null) { 10400 try { 10401 fis.close(); 10402 } catch (IOException e) { 10403 } 10404 } 10405 } 10406 return lastDoneReceivers; 10407 } 10408 10409 private static void writeLastDonePreBootReceivers(ArrayList<ComponentName> list) { 10410 File file = getCalledPreBootReceiversFile(); 10411 FileOutputStream fos = null; 10412 DataOutputStream dos = null; 10413 try { 10414 fos = new FileOutputStream(file); 10415 dos = new DataOutputStream(new BufferedOutputStream(fos, 2048)); 10416 dos.writeInt(LAST_PREBOOT_DELIVERED_FILE_VERSION); 10417 dos.writeUTF(android.os.Build.VERSION.RELEASE); 10418 dos.writeUTF(android.os.Build.VERSION.CODENAME); 10419 dos.writeUTF(android.os.Build.VERSION.INCREMENTAL); 10420 dos.writeInt(list.size()); 10421 for (int i=0; i<list.size(); i++) { 10422 dos.writeUTF(list.get(i).getPackageName()); 10423 dos.writeUTF(list.get(i).getClassName()); 10424 } 10425 } catch (IOException e) { 10426 Slog.w(TAG, "Failure writing last done pre-boot receivers", e); 10427 file.delete(); 10428 } finally { 10429 FileUtils.sync(fos); 10430 if (dos != null) { 10431 try { 10432 dos.close(); 10433 } catch (IOException e) { 10434 // TODO Auto-generated catch block 10435 e.printStackTrace(); 10436 } 10437 } 10438 } 10439 } 10440 10441 private boolean deliverPreBootCompleted(final Runnable onFinishCallback, 10442 ArrayList<ComponentName> doneReceivers, int userId) { 10443 boolean waitingUpdate = false; 10444 Intent intent = new Intent(Intent.ACTION_PRE_BOOT_COMPLETED); 10445 List<ResolveInfo> ris = null; 10446 try { 10447 ris = AppGlobals.getPackageManager().queryIntentReceivers( 10448 intent, null, 0, userId); 10449 } catch (RemoteException e) { 10450 } 10451 if (ris != null) { 10452 for (int i=ris.size()-1; i>=0; i--) { 10453 if ((ris.get(i).activityInfo.applicationInfo.flags 10454 &ApplicationInfo.FLAG_SYSTEM) == 0) { 10455 ris.remove(i); 10456 } 10457 } 10458 intent.addFlags(Intent.FLAG_RECEIVER_BOOT_UPGRADE); 10459 10460 // For User 0, load the version number. When delivering to a new user, deliver 10461 // to all receivers. 10462 if (userId == UserHandle.USER_OWNER) { 10463 ArrayList<ComponentName> lastDoneReceivers = readLastDonePreBootReceivers(); 10464 for (int i=0; i<ris.size(); i++) { 10465 ActivityInfo ai = ris.get(i).activityInfo; 10466 ComponentName comp = new ComponentName(ai.packageName, ai.name); 10467 if (lastDoneReceivers.contains(comp)) { 10468 // We already did the pre boot receiver for this app with the current 10469 // platform version, so don't do it again... 10470 ris.remove(i); 10471 i--; 10472 // ...however, do keep it as one that has been done, so we don't 10473 // forget about it when rewriting the file of last done receivers. 10474 doneReceivers.add(comp); 10475 } 10476 } 10477 } 10478 10479 // If primary user, send broadcast to all available users, else just to userId 10480 final int[] users = userId == UserHandle.USER_OWNER ? getUsersLocked() 10481 : new int[] { userId }; 10482 for (int i = 0; i < ris.size(); i++) { 10483 ActivityInfo ai = ris.get(i).activityInfo; 10484 ComponentName comp = new ComponentName(ai.packageName, ai.name); 10485 doneReceivers.add(comp); 10486 intent.setComponent(comp); 10487 for (int j=0; j<users.length; j++) { 10488 IIntentReceiver finisher = null; 10489 // On last receiver and user, set up a completion callback 10490 if (i == ris.size() - 1 && j == users.length - 1 && onFinishCallback != null) { 10491 finisher = new IIntentReceiver.Stub() { 10492 public void performReceive(Intent intent, int resultCode, 10493 String data, Bundle extras, boolean ordered, 10494 boolean sticky, int sendingUser) { 10495 // The raw IIntentReceiver interface is called 10496 // with the AM lock held, so redispatch to 10497 // execute our code without the lock. 10498 mHandler.post(onFinishCallback); 10499 } 10500 }; 10501 } 10502 Slog.i(TAG, "Sending system update to " + intent.getComponent() 10503 + " for user " + users[j]); 10504 broadcastIntentLocked(null, null, intent, null, finisher, 10505 0, null, null, null, AppOpsManager.OP_NONE, 10506 true, false, MY_PID, Process.SYSTEM_UID, 10507 users[j]); 10508 if (finisher != null) { 10509 waitingUpdate = true; 10510 } 10511 } 10512 } 10513 } 10514 10515 return waitingUpdate; 10516 } 10517 10518 public void systemReady(final Runnable goingCallback) { 10519 synchronized(this) { 10520 if (mSystemReady) { 10521 // If we're done calling all the receivers, run the next "boot phase" passed in 10522 // by the SystemServer 10523 if (goingCallback != null) { 10524 goingCallback.run(); 10525 } 10526 return; 10527 } 10528 10529 // Make sure we have the current profile info, since it is needed for 10530 // security checks. 10531 updateCurrentProfileIdsLocked(); 10532 10533 if (mRecentTasks == null) { 10534 mRecentTasks = mTaskPersister.restoreTasksLocked(); 10535 if (!mRecentTasks.isEmpty()) { 10536 mStackSupervisor.createStackForRestoredTaskHistory(mRecentTasks); 10537 } 10538 mTaskPersister.startPersisting(); 10539 } 10540 10541 // Check to see if there are any update receivers to run. 10542 if (!mDidUpdate) { 10543 if (mWaitingUpdate) { 10544 return; 10545 } 10546 final ArrayList<ComponentName> doneReceivers = new ArrayList<ComponentName>(); 10547 mWaitingUpdate = deliverPreBootCompleted(new Runnable() { 10548 public void run() { 10549 synchronized (ActivityManagerService.this) { 10550 mDidUpdate = true; 10551 } 10552 writeLastDonePreBootReceivers(doneReceivers); 10553 showBootMessage(mContext.getText( 10554 R.string.android_upgrading_complete), 10555 false); 10556 systemReady(goingCallback); 10557 } 10558 }, doneReceivers, UserHandle.USER_OWNER); 10559 10560 if (mWaitingUpdate) { 10561 return; 10562 } 10563 mDidUpdate = true; 10564 } 10565 10566 mAppOpsService.systemReady(); 10567 mSystemReady = true; 10568 } 10569 10570 ArrayList<ProcessRecord> procsToKill = null; 10571 synchronized(mPidsSelfLocked) { 10572 for (int i=mPidsSelfLocked.size()-1; i>=0; i--) { 10573 ProcessRecord proc = mPidsSelfLocked.valueAt(i); 10574 if (!isAllowedWhileBooting(proc.info)){ 10575 if (procsToKill == null) { 10576 procsToKill = new ArrayList<ProcessRecord>(); 10577 } 10578 procsToKill.add(proc); 10579 } 10580 } 10581 } 10582 10583 synchronized(this) { 10584 if (procsToKill != null) { 10585 for (int i=procsToKill.size()-1; i>=0; i--) { 10586 ProcessRecord proc = procsToKill.get(i); 10587 Slog.i(TAG, "Removing system update proc: " + proc); 10588 removeProcessLocked(proc, true, false, "system update done"); 10589 } 10590 } 10591 10592 // Now that we have cleaned up any update processes, we 10593 // are ready to start launching real processes and know that 10594 // we won't trample on them any more. 10595 mProcessesReady = true; 10596 } 10597 10598 Slog.i(TAG, "System now ready"); 10599 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_AMS_READY, 10600 SystemClock.uptimeMillis()); 10601 10602 synchronized(this) { 10603 // Make sure we have no pre-ready processes sitting around. 10604 10605 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) { 10606 ResolveInfo ri = mContext.getPackageManager() 10607 .resolveActivity(new Intent(Intent.ACTION_FACTORY_TEST), 10608 STOCK_PM_FLAGS); 10609 CharSequence errorMsg = null; 10610 if (ri != null) { 10611 ActivityInfo ai = ri.activityInfo; 10612 ApplicationInfo app = ai.applicationInfo; 10613 if ((app.flags&ApplicationInfo.FLAG_SYSTEM) != 0) { 10614 mTopAction = Intent.ACTION_FACTORY_TEST; 10615 mTopData = null; 10616 mTopComponent = new ComponentName(app.packageName, 10617 ai.name); 10618 } else { 10619 errorMsg = mContext.getResources().getText( 10620 com.android.internal.R.string.factorytest_not_system); 10621 } 10622 } else { 10623 errorMsg = mContext.getResources().getText( 10624 com.android.internal.R.string.factorytest_no_action); 10625 } 10626 if (errorMsg != null) { 10627 mTopAction = null; 10628 mTopData = null; 10629 mTopComponent = null; 10630 Message msg = Message.obtain(); 10631 msg.what = SHOW_FACTORY_ERROR_MSG; 10632 msg.getData().putCharSequence("msg", errorMsg); 10633 mHandler.sendMessage(msg); 10634 } 10635 } 10636 } 10637 10638 retrieveSettings(); 10639 10640 synchronized (this) { 10641 readGrantedUriPermissionsLocked(); 10642 } 10643 10644 if (goingCallback != null) goingCallback.run(); 10645 10646 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 10647 Integer.toString(mCurrentUserId), mCurrentUserId); 10648 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 10649 Integer.toString(mCurrentUserId), mCurrentUserId); 10650 mSystemServiceManager.startUser(mCurrentUserId); 10651 10652 synchronized (this) { 10653 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 10654 try { 10655 List apps = AppGlobals.getPackageManager(). 10656 getPersistentApplications(STOCK_PM_FLAGS); 10657 if (apps != null) { 10658 int N = apps.size(); 10659 int i; 10660 for (i=0; i<N; i++) { 10661 ApplicationInfo info 10662 = (ApplicationInfo)apps.get(i); 10663 if (info != null && 10664 !info.packageName.equals("android")) { 10665 addAppLocked(info, false, null /* ABI override */); 10666 } 10667 } 10668 } 10669 } catch (RemoteException ex) { 10670 // pm is in same process, this will never happen. 10671 } 10672 } 10673 10674 // Start up initial activity. 10675 mBooting = true; 10676 10677 try { 10678 if (AppGlobals.getPackageManager().hasSystemUidErrors()) { 10679 Message msg = Message.obtain(); 10680 msg.what = SHOW_UID_ERROR_MSG; 10681 mHandler.sendMessage(msg); 10682 } 10683 } catch (RemoteException e) { 10684 } 10685 10686 long ident = Binder.clearCallingIdentity(); 10687 try { 10688 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 10689 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 10690 | Intent.FLAG_RECEIVER_FOREGROUND); 10691 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 10692 broadcastIntentLocked(null, null, intent, 10693 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 10694 false, false, MY_PID, Process.SYSTEM_UID, mCurrentUserId); 10695 intent = new Intent(Intent.ACTION_USER_STARTING); 10696 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 10697 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 10698 broadcastIntentLocked(null, null, intent, 10699 null, new IIntentReceiver.Stub() { 10700 @Override 10701 public void performReceive(Intent intent, int resultCode, String data, 10702 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 10703 throws RemoteException { 10704 } 10705 }, 0, null, null, 10706 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 10707 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 10708 } catch (Throwable t) { 10709 Slog.wtf(TAG, "Failed sending first user broadcasts", t); 10710 } finally { 10711 Binder.restoreCallingIdentity(ident); 10712 } 10713 mStackSupervisor.resumeTopActivitiesLocked(); 10714 sendUserSwitchBroadcastsLocked(-1, mCurrentUserId); 10715 } 10716 } 10717 10718 private boolean makeAppCrashingLocked(ProcessRecord app, 10719 String shortMsg, String longMsg, String stackTrace) { 10720 app.crashing = true; 10721 app.crashingReport = generateProcessError(app, 10722 ActivityManager.ProcessErrorStateInfo.CRASHED, null, shortMsg, longMsg, stackTrace); 10723 startAppProblemLocked(app); 10724 app.stopFreezingAllLocked(); 10725 return handleAppCrashLocked(app, shortMsg, longMsg, stackTrace); 10726 } 10727 10728 private void makeAppNotRespondingLocked(ProcessRecord app, 10729 String activity, String shortMsg, String longMsg) { 10730 app.notResponding = true; 10731 app.notRespondingReport = generateProcessError(app, 10732 ActivityManager.ProcessErrorStateInfo.NOT_RESPONDING, 10733 activity, shortMsg, longMsg, null); 10734 startAppProblemLocked(app); 10735 app.stopFreezingAllLocked(); 10736 } 10737 10738 /** 10739 * Generate a process error record, suitable for attachment to a ProcessRecord. 10740 * 10741 * @param app The ProcessRecord in which the error occurred. 10742 * @param condition Crashing, Application Not Responding, etc. Values are defined in 10743 * ActivityManager.AppErrorStateInfo 10744 * @param activity The activity associated with the crash, if known. 10745 * @param shortMsg Short message describing the crash. 10746 * @param longMsg Long message describing the crash. 10747 * @param stackTrace Full crash stack trace, may be null. 10748 * 10749 * @return Returns a fully-formed AppErrorStateInfo record. 10750 */ 10751 private ActivityManager.ProcessErrorStateInfo generateProcessError(ProcessRecord app, 10752 int condition, String activity, String shortMsg, String longMsg, String stackTrace) { 10753 ActivityManager.ProcessErrorStateInfo report = new ActivityManager.ProcessErrorStateInfo(); 10754 10755 report.condition = condition; 10756 report.processName = app.processName; 10757 report.pid = app.pid; 10758 report.uid = app.info.uid; 10759 report.tag = activity; 10760 report.shortMsg = shortMsg; 10761 report.longMsg = longMsg; 10762 report.stackTrace = stackTrace; 10763 10764 return report; 10765 } 10766 10767 void killAppAtUsersRequest(ProcessRecord app, Dialog fromDialog) { 10768 synchronized (this) { 10769 app.crashing = false; 10770 app.crashingReport = null; 10771 app.notResponding = false; 10772 app.notRespondingReport = null; 10773 if (app.anrDialog == fromDialog) { 10774 app.anrDialog = null; 10775 } 10776 if (app.waitDialog == fromDialog) { 10777 app.waitDialog = null; 10778 } 10779 if (app.pid > 0 && app.pid != MY_PID) { 10780 handleAppCrashLocked(app, null, null, null); 10781 killUnneededProcessLocked(app, "user request after error"); 10782 } 10783 } 10784 } 10785 10786 private boolean handleAppCrashLocked(ProcessRecord app, String shortMsg, String longMsg, 10787 String stackTrace) { 10788 long now = SystemClock.uptimeMillis(); 10789 10790 Long crashTime; 10791 if (!app.isolated) { 10792 crashTime = mProcessCrashTimes.get(app.info.processName, app.uid); 10793 } else { 10794 crashTime = null; 10795 } 10796 if (crashTime != null && now < crashTime+ProcessList.MIN_CRASH_INTERVAL) { 10797 // This process loses! 10798 Slog.w(TAG, "Process " + app.info.processName 10799 + " has crashed too many times: killing!"); 10800 EventLog.writeEvent(EventLogTags.AM_PROCESS_CRASHED_TOO_MUCH, 10801 app.userId, app.info.processName, app.uid); 10802 mStackSupervisor.handleAppCrashLocked(app); 10803 if (!app.persistent) { 10804 // We don't want to start this process again until the user 10805 // explicitly does so... but for persistent process, we really 10806 // need to keep it running. If a persistent process is actually 10807 // repeatedly crashing, then badness for everyone. 10808 EventLog.writeEvent(EventLogTags.AM_PROC_BAD, app.userId, app.uid, 10809 app.info.processName); 10810 if (!app.isolated) { 10811 // XXX We don't have a way to mark isolated processes 10812 // as bad, since they don't have a peristent identity. 10813 mBadProcesses.put(app.info.processName, app.uid, 10814 new BadProcessInfo(now, shortMsg, longMsg, stackTrace)); 10815 mProcessCrashTimes.remove(app.info.processName, app.uid); 10816 } 10817 app.bad = true; 10818 app.removed = true; 10819 // Don't let services in this process be restarted and potentially 10820 // annoy the user repeatedly. Unless it is persistent, since those 10821 // processes run critical code. 10822 removeProcessLocked(app, false, false, "crash"); 10823 mStackSupervisor.resumeTopActivitiesLocked(); 10824 return false; 10825 } 10826 mStackSupervisor.resumeTopActivitiesLocked(); 10827 } else { 10828 mStackSupervisor.finishTopRunningActivityLocked(app); 10829 } 10830 10831 // Bump up the crash count of any services currently running in the proc. 10832 for (int i=app.services.size()-1; i>=0; i--) { 10833 // Any services running in the application need to be placed 10834 // back in the pending list. 10835 ServiceRecord sr = app.services.valueAt(i); 10836 sr.crashCount++; 10837 } 10838 10839 // If the crashing process is what we consider to be the "home process" and it has been 10840 // replaced by a third-party app, clear the package preferred activities from packages 10841 // with a home activity running in the process to prevent a repeatedly crashing app 10842 // from blocking the user to manually clear the list. 10843 final ArrayList<ActivityRecord> activities = app.activities; 10844 if (app == mHomeProcess && activities.size() > 0 10845 && (mHomeProcess.info.flags & ApplicationInfo.FLAG_SYSTEM) == 0) { 10846 for (int activityNdx = activities.size() - 1; activityNdx >= 0; --activityNdx) { 10847 final ActivityRecord r = activities.get(activityNdx); 10848 if (r.isHomeActivity()) { 10849 Log.i(TAG, "Clearing package preferred activities from " + r.packageName); 10850 try { 10851 ActivityThread.getPackageManager() 10852 .clearPackagePreferredActivities(r.packageName); 10853 } catch (RemoteException c) { 10854 // pm is in same process, this will never happen. 10855 } 10856 } 10857 } 10858 } 10859 10860 if (!app.isolated) { 10861 // XXX Can't keep track of crash times for isolated processes, 10862 // because they don't have a perisistent identity. 10863 mProcessCrashTimes.put(app.info.processName, app.uid, now); 10864 } 10865 10866 if (app.crashHandler != null) mHandler.post(app.crashHandler); 10867 return true; 10868 } 10869 10870 void startAppProblemLocked(ProcessRecord app) { 10871 // If this app is not running under the current user, then we 10872 // can't give it a report button because that would require 10873 // launching the report UI under a different user. 10874 app.errorReportReceiver = null; 10875 10876 for (int userId : mCurrentProfileIds) { 10877 if (app.userId == userId) { 10878 app.errorReportReceiver = ApplicationErrorReport.getErrorReportReceiver( 10879 mContext, app.info.packageName, app.info.flags); 10880 } 10881 } 10882 skipCurrentReceiverLocked(app); 10883 } 10884 10885 void skipCurrentReceiverLocked(ProcessRecord app) { 10886 for (BroadcastQueue queue : mBroadcastQueues) { 10887 queue.skipCurrentReceiverLocked(app); 10888 } 10889 } 10890 10891 /** 10892 * Used by {@link com.android.internal.os.RuntimeInit} to report when an application crashes. 10893 * The application process will exit immediately after this call returns. 10894 * @param app object of the crashing app, null for the system server 10895 * @param crashInfo describing the exception 10896 */ 10897 public void handleApplicationCrash(IBinder app, ApplicationErrorReport.CrashInfo crashInfo) { 10898 ProcessRecord r = findAppProcess(app, "Crash"); 10899 final String processName = app == null ? "system_server" 10900 : (r == null ? "unknown" : r.processName); 10901 10902 handleApplicationCrashInner("crash", r, processName, crashInfo); 10903 } 10904 10905 /* Native crash reporting uses this inner version because it needs to be somewhat 10906 * decoupled from the AM-managed cleanup lifecycle 10907 */ 10908 void handleApplicationCrashInner(String eventType, ProcessRecord r, String processName, 10909 ApplicationErrorReport.CrashInfo crashInfo) { 10910 EventLog.writeEvent(EventLogTags.AM_CRASH, Binder.getCallingPid(), 10911 UserHandle.getUserId(Binder.getCallingUid()), processName, 10912 r == null ? -1 : r.info.flags, 10913 crashInfo.exceptionClassName, 10914 crashInfo.exceptionMessage, 10915 crashInfo.throwFileName, 10916 crashInfo.throwLineNumber); 10917 10918 addErrorToDropBox(eventType, r, processName, null, null, null, null, null, crashInfo); 10919 10920 crashApplication(r, crashInfo); 10921 } 10922 10923 public void handleApplicationStrictModeViolation( 10924 IBinder app, 10925 int violationMask, 10926 StrictMode.ViolationInfo info) { 10927 ProcessRecord r = findAppProcess(app, "StrictMode"); 10928 if (r == null) { 10929 return; 10930 } 10931 10932 if ((violationMask & StrictMode.PENALTY_DROPBOX) != 0) { 10933 Integer stackFingerprint = info.hashCode(); 10934 boolean logIt = true; 10935 synchronized (mAlreadyLoggedViolatedStacks) { 10936 if (mAlreadyLoggedViolatedStacks.contains(stackFingerprint)) { 10937 logIt = false; 10938 // TODO: sub-sample into EventLog for these, with 10939 // the info.durationMillis? Then we'd get 10940 // the relative pain numbers, without logging all 10941 // the stack traces repeatedly. We'd want to do 10942 // likewise in the client code, which also does 10943 // dup suppression, before the Binder call. 10944 } else { 10945 if (mAlreadyLoggedViolatedStacks.size() >= MAX_DUP_SUPPRESSED_STACKS) { 10946 mAlreadyLoggedViolatedStacks.clear(); 10947 } 10948 mAlreadyLoggedViolatedStacks.add(stackFingerprint); 10949 } 10950 } 10951 if (logIt) { 10952 logStrictModeViolationToDropBox(r, info); 10953 } 10954 } 10955 10956 if ((violationMask & StrictMode.PENALTY_DIALOG) != 0) { 10957 AppErrorResult result = new AppErrorResult(); 10958 synchronized (this) { 10959 final long origId = Binder.clearCallingIdentity(); 10960 10961 Message msg = Message.obtain(); 10962 msg.what = SHOW_STRICT_MODE_VIOLATION_MSG; 10963 HashMap<String, Object> data = new HashMap<String, Object>(); 10964 data.put("result", result); 10965 data.put("app", r); 10966 data.put("violationMask", violationMask); 10967 data.put("info", info); 10968 msg.obj = data; 10969 mHandler.sendMessage(msg); 10970 10971 Binder.restoreCallingIdentity(origId); 10972 } 10973 int res = result.get(); 10974 Slog.w(TAG, "handleApplicationStrictModeViolation; res=" + res); 10975 } 10976 } 10977 10978 // Depending on the policy in effect, there could be a bunch of 10979 // these in quick succession so we try to batch these together to 10980 // minimize disk writes, number of dropbox entries, and maximize 10981 // compression, by having more fewer, larger records. 10982 private void logStrictModeViolationToDropBox( 10983 ProcessRecord process, 10984 StrictMode.ViolationInfo info) { 10985 if (info == null) { 10986 return; 10987 } 10988 final boolean isSystemApp = process == null || 10989 (process.info.flags & (ApplicationInfo.FLAG_SYSTEM | 10990 ApplicationInfo.FLAG_UPDATED_SYSTEM_APP)) != 0; 10991 final String processName = process == null ? "unknown" : process.processName; 10992 final String dropboxTag = isSystemApp ? "system_app_strictmode" : "data_app_strictmode"; 10993 final DropBoxManager dbox = (DropBoxManager) 10994 mContext.getSystemService(Context.DROPBOX_SERVICE); 10995 10996 // Exit early if the dropbox isn't configured to accept this report type. 10997 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 10998 10999 boolean bufferWasEmpty; 11000 boolean needsFlush; 11001 final StringBuilder sb = isSystemApp ? mStrictModeBuffer : new StringBuilder(1024); 11002 synchronized (sb) { 11003 bufferWasEmpty = sb.length() == 0; 11004 appendDropBoxProcessHeaders(process, processName, sb); 11005 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 11006 sb.append("System-App: ").append(isSystemApp).append("\n"); 11007 sb.append("Uptime-Millis: ").append(info.violationUptimeMillis).append("\n"); 11008 if (info.violationNumThisLoop != 0) { 11009 sb.append("Loop-Violation-Number: ").append(info.violationNumThisLoop).append("\n"); 11010 } 11011 if (info.numAnimationsRunning != 0) { 11012 sb.append("Animations-Running: ").append(info.numAnimationsRunning).append("\n"); 11013 } 11014 if (info.broadcastIntentAction != null) { 11015 sb.append("Broadcast-Intent-Action: ").append(info.broadcastIntentAction).append("\n"); 11016 } 11017 if (info.durationMillis != -1) { 11018 sb.append("Duration-Millis: ").append(info.durationMillis).append("\n"); 11019 } 11020 if (info.numInstances != -1) { 11021 sb.append("Instance-Count: ").append(info.numInstances).append("\n"); 11022 } 11023 if (info.tags != null) { 11024 for (String tag : info.tags) { 11025 sb.append("Span-Tag: ").append(tag).append("\n"); 11026 } 11027 } 11028 sb.append("\n"); 11029 if (info.crashInfo != null && info.crashInfo.stackTrace != null) { 11030 sb.append(info.crashInfo.stackTrace); 11031 } 11032 sb.append("\n"); 11033 11034 // Only buffer up to ~64k. Various logging bits truncate 11035 // things at 128k. 11036 needsFlush = (sb.length() > 64 * 1024); 11037 } 11038 11039 // Flush immediately if the buffer's grown too large, or this 11040 // is a non-system app. Non-system apps are isolated with a 11041 // different tag & policy and not batched. 11042 // 11043 // Batching is useful during internal testing with 11044 // StrictMode settings turned up high. Without batching, 11045 // thousands of separate files could be created on boot. 11046 if (!isSystemApp || needsFlush) { 11047 new Thread("Error dump: " + dropboxTag) { 11048 @Override 11049 public void run() { 11050 String report; 11051 synchronized (sb) { 11052 report = sb.toString(); 11053 sb.delete(0, sb.length()); 11054 sb.trimToSize(); 11055 } 11056 if (report.length() != 0) { 11057 dbox.addText(dropboxTag, report); 11058 } 11059 } 11060 }.start(); 11061 return; 11062 } 11063 11064 // System app batching: 11065 if (!bufferWasEmpty) { 11066 // An existing dropbox-writing thread is outstanding, so 11067 // we don't need to start it up. The existing thread will 11068 // catch the buffer appends we just did. 11069 return; 11070 } 11071 11072 // Worker thread to both batch writes and to avoid blocking the caller on I/O. 11073 // (After this point, we shouldn't access AMS internal data structures.) 11074 new Thread("Error dump: " + dropboxTag) { 11075 @Override 11076 public void run() { 11077 // 5 second sleep to let stacks arrive and be batched together 11078 try { 11079 Thread.sleep(5000); // 5 seconds 11080 } catch (InterruptedException e) {} 11081 11082 String errorReport; 11083 synchronized (mStrictModeBuffer) { 11084 errorReport = mStrictModeBuffer.toString(); 11085 if (errorReport.length() == 0) { 11086 return; 11087 } 11088 mStrictModeBuffer.delete(0, mStrictModeBuffer.length()); 11089 mStrictModeBuffer.trimToSize(); 11090 } 11091 dbox.addText(dropboxTag, errorReport); 11092 } 11093 }.start(); 11094 } 11095 11096 /** 11097 * Used by {@link Log} via {@link com.android.internal.os.RuntimeInit} to report serious errors. 11098 * @param app object of the crashing app, null for the system server 11099 * @param tag reported by the caller 11100 * @param crashInfo describing the context of the error 11101 * @return true if the process should exit immediately (WTF is fatal) 11102 */ 11103 public boolean handleApplicationWtf(IBinder app, String tag, 11104 ApplicationErrorReport.CrashInfo crashInfo) { 11105 ProcessRecord r = findAppProcess(app, "WTF"); 11106 final String processName = app == null ? "system_server" 11107 : (r == null ? "unknown" : r.processName); 11108 11109 EventLog.writeEvent(EventLogTags.AM_WTF, 11110 UserHandle.getUserId(Binder.getCallingUid()), Binder.getCallingPid(), 11111 processName, 11112 r == null ? -1 : r.info.flags, 11113 tag, crashInfo.exceptionMessage); 11114 11115 addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, crashInfo); 11116 11117 if (r != null && r.pid != Process.myPid() && 11118 Settings.Global.getInt(mContext.getContentResolver(), 11119 Settings.Global.WTF_IS_FATAL, 0) != 0) { 11120 crashApplication(r, crashInfo); 11121 return true; 11122 } else { 11123 return false; 11124 } 11125 } 11126 11127 /** 11128 * @param app object of some object (as stored in {@link com.android.internal.os.RuntimeInit}) 11129 * @return the corresponding {@link ProcessRecord} object, or null if none could be found 11130 */ 11131 private ProcessRecord findAppProcess(IBinder app, String reason) { 11132 if (app == null) { 11133 return null; 11134 } 11135 11136 synchronized (this) { 11137 final int NP = mProcessNames.getMap().size(); 11138 for (int ip=0; ip<NP; ip++) { 11139 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 11140 final int NA = apps.size(); 11141 for (int ia=0; ia<NA; ia++) { 11142 ProcessRecord p = apps.valueAt(ia); 11143 if (p.thread != null && p.thread.asBinder() == app) { 11144 return p; 11145 } 11146 } 11147 } 11148 11149 Slog.w(TAG, "Can't find mystery application for " + reason 11150 + " from pid=" + Binder.getCallingPid() 11151 + " uid=" + Binder.getCallingUid() + ": " + app); 11152 return null; 11153 } 11154 } 11155 11156 /** 11157 * Utility function for addErrorToDropBox and handleStrictModeViolation's logging 11158 * to append various headers to the dropbox log text. 11159 */ 11160 private void appendDropBoxProcessHeaders(ProcessRecord process, String processName, 11161 StringBuilder sb) { 11162 // Watchdog thread ends up invoking this function (with 11163 // a null ProcessRecord) to add the stack file to dropbox. 11164 // Do not acquire a lock on this (am) in such cases, as it 11165 // could cause a potential deadlock, if and when watchdog 11166 // is invoked due to unavailability of lock on am and it 11167 // would prevent watchdog from killing system_server. 11168 if (process == null) { 11169 sb.append("Process: ").append(processName).append("\n"); 11170 return; 11171 } 11172 // Note: ProcessRecord 'process' is guarded by the service 11173 // instance. (notably process.pkgList, which could otherwise change 11174 // concurrently during execution of this method) 11175 synchronized (this) { 11176 sb.append("Process: ").append(processName).append("\n"); 11177 int flags = process.info.flags; 11178 IPackageManager pm = AppGlobals.getPackageManager(); 11179 sb.append("Flags: 0x").append(Integer.toString(flags, 16)).append("\n"); 11180 for (int ip=0; ip<process.pkgList.size(); ip++) { 11181 String pkg = process.pkgList.keyAt(ip); 11182 sb.append("Package: ").append(pkg); 11183 try { 11184 PackageInfo pi = pm.getPackageInfo(pkg, 0, UserHandle.getCallingUserId()); 11185 if (pi != null) { 11186 sb.append(" v").append(pi.versionCode); 11187 if (pi.versionName != null) { 11188 sb.append(" (").append(pi.versionName).append(")"); 11189 } 11190 } 11191 } catch (RemoteException e) { 11192 Slog.e(TAG, "Error getting package info: " + pkg, e); 11193 } 11194 sb.append("\n"); 11195 } 11196 } 11197 } 11198 11199 private static String processClass(ProcessRecord process) { 11200 if (process == null || process.pid == MY_PID) { 11201 return "system_server"; 11202 } else if ((process.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 11203 return "system_app"; 11204 } else { 11205 return "data_app"; 11206 } 11207 } 11208 11209 /** 11210 * Write a description of an error (crash, WTF, ANR) to the drop box. 11211 * @param eventType to include in the drop box tag ("crash", "wtf", etc.) 11212 * @param process which caused the error, null means the system server 11213 * @param activity which triggered the error, null if unknown 11214 * @param parent activity related to the error, null if unknown 11215 * @param subject line related to the error, null if absent 11216 * @param report in long form describing the error, null if absent 11217 * @param logFile to include in the report, null if none 11218 * @param crashInfo giving an application stack trace, null if absent 11219 */ 11220 public void addErrorToDropBox(String eventType, 11221 ProcessRecord process, String processName, ActivityRecord activity, 11222 ActivityRecord parent, String subject, 11223 final String report, final File logFile, 11224 final ApplicationErrorReport.CrashInfo crashInfo) { 11225 // NOTE -- this must never acquire the ActivityManagerService lock, 11226 // otherwise the watchdog may be prevented from resetting the system. 11227 11228 final String dropboxTag = processClass(process) + "_" + eventType; 11229 final DropBoxManager dbox = (DropBoxManager) 11230 mContext.getSystemService(Context.DROPBOX_SERVICE); 11231 11232 // Exit early if the dropbox isn't configured to accept this report type. 11233 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 11234 11235 final StringBuilder sb = new StringBuilder(1024); 11236 appendDropBoxProcessHeaders(process, processName, sb); 11237 if (activity != null) { 11238 sb.append("Activity: ").append(activity.shortComponentName).append("\n"); 11239 } 11240 if (parent != null && parent.app != null && parent.app.pid != process.pid) { 11241 sb.append("Parent-Process: ").append(parent.app.processName).append("\n"); 11242 } 11243 if (parent != null && parent != activity) { 11244 sb.append("Parent-Activity: ").append(parent.shortComponentName).append("\n"); 11245 } 11246 if (subject != null) { 11247 sb.append("Subject: ").append(subject).append("\n"); 11248 } 11249 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 11250 if (Debug.isDebuggerConnected()) { 11251 sb.append("Debugger: Connected\n"); 11252 } 11253 sb.append("\n"); 11254 11255 // Do the rest in a worker thread to avoid blocking the caller on I/O 11256 // (After this point, we shouldn't access AMS internal data structures.) 11257 Thread worker = new Thread("Error dump: " + dropboxTag) { 11258 @Override 11259 public void run() { 11260 if (report != null) { 11261 sb.append(report); 11262 } 11263 if (logFile != null) { 11264 try { 11265 sb.append(FileUtils.readTextFile(logFile, DROPBOX_MAX_SIZE, 11266 "\n\n[[TRUNCATED]]")); 11267 } catch (IOException e) { 11268 Slog.e(TAG, "Error reading " + logFile, e); 11269 } 11270 } 11271 if (crashInfo != null && crashInfo.stackTrace != null) { 11272 sb.append(crashInfo.stackTrace); 11273 } 11274 11275 String setting = Settings.Global.ERROR_LOGCAT_PREFIX + dropboxTag; 11276 int lines = Settings.Global.getInt(mContext.getContentResolver(), setting, 0); 11277 if (lines > 0) { 11278 sb.append("\n"); 11279 11280 // Merge several logcat streams, and take the last N lines 11281 InputStreamReader input = null; 11282 try { 11283 java.lang.Process logcat = new ProcessBuilder("/system/bin/logcat", 11284 "-v", "time", "-b", "events", "-b", "system", "-b", "main", 11285 "-t", String.valueOf(lines)).redirectErrorStream(true).start(); 11286 11287 try { logcat.getOutputStream().close(); } catch (IOException e) {} 11288 try { logcat.getErrorStream().close(); } catch (IOException e) {} 11289 input = new InputStreamReader(logcat.getInputStream()); 11290 11291 int num; 11292 char[] buf = new char[8192]; 11293 while ((num = input.read(buf)) > 0) sb.append(buf, 0, num); 11294 } catch (IOException e) { 11295 Slog.e(TAG, "Error running logcat", e); 11296 } finally { 11297 if (input != null) try { input.close(); } catch (IOException e) {} 11298 } 11299 } 11300 11301 dbox.addText(dropboxTag, sb.toString()); 11302 } 11303 }; 11304 11305 if (process == null) { 11306 // If process is null, we are being called from some internal code 11307 // and may be about to die -- run this synchronously. 11308 worker.run(); 11309 } else { 11310 worker.start(); 11311 } 11312 } 11313 11314 /** 11315 * Bring up the "unexpected error" dialog box for a crashing app. 11316 * Deal with edge cases (intercepts from instrumented applications, 11317 * ActivityController, error intent receivers, that sort of thing). 11318 * @param r the application crashing 11319 * @param crashInfo describing the failure 11320 */ 11321 private void crashApplication(ProcessRecord r, ApplicationErrorReport.CrashInfo crashInfo) { 11322 long timeMillis = System.currentTimeMillis(); 11323 String shortMsg = crashInfo.exceptionClassName; 11324 String longMsg = crashInfo.exceptionMessage; 11325 String stackTrace = crashInfo.stackTrace; 11326 if (shortMsg != null && longMsg != null) { 11327 longMsg = shortMsg + ": " + longMsg; 11328 } else if (shortMsg != null) { 11329 longMsg = shortMsg; 11330 } 11331 11332 AppErrorResult result = new AppErrorResult(); 11333 synchronized (this) { 11334 if (mController != null) { 11335 try { 11336 String name = r != null ? r.processName : null; 11337 int pid = r != null ? r.pid : Binder.getCallingPid(); 11338 int uid = r != null ? r.info.uid : Binder.getCallingUid(); 11339 if (!mController.appCrashed(name, pid, 11340 shortMsg, longMsg, timeMillis, crashInfo.stackTrace)) { 11341 if ("1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")) 11342 && "Native crash".equals(crashInfo.exceptionClassName)) { 11343 Slog.w(TAG, "Skip killing native crashed app " + name 11344 + "(" + pid + ") during testing"); 11345 } else { 11346 Slog.w(TAG, "Force-killing crashed app " + name 11347 + " at watcher's request"); 11348 Process.killProcess(pid); 11349 if (r != null) { 11350 Process.killProcessGroup(uid, pid); 11351 } 11352 } 11353 return; 11354 } 11355 } catch (RemoteException e) { 11356 mController = null; 11357 Watchdog.getInstance().setActivityController(null); 11358 } 11359 } 11360 11361 final long origId = Binder.clearCallingIdentity(); 11362 11363 // If this process is running instrumentation, finish it. 11364 if (r != null && r.instrumentationClass != null) { 11365 Slog.w(TAG, "Error in app " + r.processName 11366 + " running instrumentation " + r.instrumentationClass + ":"); 11367 if (shortMsg != null) Slog.w(TAG, " " + shortMsg); 11368 if (longMsg != null) Slog.w(TAG, " " + longMsg); 11369 Bundle info = new Bundle(); 11370 info.putString("shortMsg", shortMsg); 11371 info.putString("longMsg", longMsg); 11372 finishInstrumentationLocked(r, Activity.RESULT_CANCELED, info); 11373 Binder.restoreCallingIdentity(origId); 11374 return; 11375 } 11376 11377 // If we can't identify the process or it's already exceeded its crash quota, 11378 // quit right away without showing a crash dialog. 11379 if (r == null || !makeAppCrashingLocked(r, shortMsg, longMsg, stackTrace)) { 11380 Binder.restoreCallingIdentity(origId); 11381 return; 11382 } 11383 11384 Message msg = Message.obtain(); 11385 msg.what = SHOW_ERROR_MSG; 11386 HashMap data = new HashMap(); 11387 data.put("result", result); 11388 data.put("app", r); 11389 msg.obj = data; 11390 mHandler.sendMessage(msg); 11391 11392 Binder.restoreCallingIdentity(origId); 11393 } 11394 11395 int res = result.get(); 11396 11397 Intent appErrorIntent = null; 11398 synchronized (this) { 11399 if (r != null && !r.isolated) { 11400 // XXX Can't keep track of crash time for isolated processes, 11401 // since they don't have a persistent identity. 11402 mProcessCrashTimes.put(r.info.processName, r.uid, 11403 SystemClock.uptimeMillis()); 11404 } 11405 if (res == AppErrorDialog.FORCE_QUIT_AND_REPORT) { 11406 appErrorIntent = createAppErrorIntentLocked(r, timeMillis, crashInfo); 11407 } 11408 } 11409 11410 if (appErrorIntent != null) { 11411 try { 11412 mContext.startActivityAsUser(appErrorIntent, new UserHandle(r.userId)); 11413 } catch (ActivityNotFoundException e) { 11414 Slog.w(TAG, "bug report receiver dissappeared", e); 11415 } 11416 } 11417 } 11418 11419 Intent createAppErrorIntentLocked(ProcessRecord r, 11420 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 11421 ApplicationErrorReport report = createAppErrorReportLocked(r, timeMillis, crashInfo); 11422 if (report == null) { 11423 return null; 11424 } 11425 Intent result = new Intent(Intent.ACTION_APP_ERROR); 11426 result.setComponent(r.errorReportReceiver); 11427 result.putExtra(Intent.EXTRA_BUG_REPORT, report); 11428 result.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 11429 return result; 11430 } 11431 11432 private ApplicationErrorReport createAppErrorReportLocked(ProcessRecord r, 11433 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 11434 if (r.errorReportReceiver == null) { 11435 return null; 11436 } 11437 11438 if (!r.crashing && !r.notResponding && !r.forceCrashReport) { 11439 return null; 11440 } 11441 11442 ApplicationErrorReport report = new ApplicationErrorReport(); 11443 report.packageName = r.info.packageName; 11444 report.installerPackageName = r.errorReportReceiver.getPackageName(); 11445 report.processName = r.processName; 11446 report.time = timeMillis; 11447 report.systemApp = (r.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0; 11448 11449 if (r.crashing || r.forceCrashReport) { 11450 report.type = ApplicationErrorReport.TYPE_CRASH; 11451 report.crashInfo = crashInfo; 11452 } else if (r.notResponding) { 11453 report.type = ApplicationErrorReport.TYPE_ANR; 11454 report.anrInfo = new ApplicationErrorReport.AnrInfo(); 11455 11456 report.anrInfo.activity = r.notRespondingReport.tag; 11457 report.anrInfo.cause = r.notRespondingReport.shortMsg; 11458 report.anrInfo.info = r.notRespondingReport.longMsg; 11459 } 11460 11461 return report; 11462 } 11463 11464 public List<ActivityManager.ProcessErrorStateInfo> getProcessesInErrorState() { 11465 enforceNotIsolatedCaller("getProcessesInErrorState"); 11466 // assume our apps are happy - lazy create the list 11467 List<ActivityManager.ProcessErrorStateInfo> errList = null; 11468 11469 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 11470 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 11471 int userId = UserHandle.getUserId(Binder.getCallingUid()); 11472 11473 synchronized (this) { 11474 11475 // iterate across all processes 11476 for (int i=mLruProcesses.size()-1; i>=0; i--) { 11477 ProcessRecord app = mLruProcesses.get(i); 11478 if (!allUsers && app.userId != userId) { 11479 continue; 11480 } 11481 if ((app.thread != null) && (app.crashing || app.notResponding)) { 11482 // This one's in trouble, so we'll generate a report for it 11483 // crashes are higher priority (in case there's a crash *and* an anr) 11484 ActivityManager.ProcessErrorStateInfo report = null; 11485 if (app.crashing) { 11486 report = app.crashingReport; 11487 } else if (app.notResponding) { 11488 report = app.notRespondingReport; 11489 } 11490 11491 if (report != null) { 11492 if (errList == null) { 11493 errList = new ArrayList<ActivityManager.ProcessErrorStateInfo>(1); 11494 } 11495 errList.add(report); 11496 } else { 11497 Slog.w(TAG, "Missing app error report, app = " + app.processName + 11498 " crashing = " + app.crashing + 11499 " notResponding = " + app.notResponding); 11500 } 11501 } 11502 } 11503 } 11504 11505 return errList; 11506 } 11507 11508 static int procStateToImportance(int procState, int memAdj, 11509 ActivityManager.RunningAppProcessInfo currApp) { 11510 int imp = ActivityManager.RunningAppProcessInfo.procStateToImportance(procState); 11511 if (imp == ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND) { 11512 currApp.lru = memAdj; 11513 } else { 11514 currApp.lru = 0; 11515 } 11516 return imp; 11517 } 11518 11519 private void fillInProcMemInfo(ProcessRecord app, 11520 ActivityManager.RunningAppProcessInfo outInfo) { 11521 outInfo.pid = app.pid; 11522 outInfo.uid = app.info.uid; 11523 if (mHeavyWeightProcess == app) { 11524 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_CANT_SAVE_STATE; 11525 } 11526 if (app.persistent) { 11527 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_PERSISTENT; 11528 } 11529 if (app.activities.size() > 0) { 11530 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_HAS_ACTIVITIES; 11531 } 11532 outInfo.lastTrimLevel = app.trimMemoryLevel; 11533 int adj = app.curAdj; 11534 int procState = app.curProcState; 11535 outInfo.importance = procStateToImportance(procState, adj, outInfo); 11536 outInfo.importanceReasonCode = app.adjTypeCode; 11537 outInfo.processState = app.curProcState; 11538 } 11539 11540 public List<ActivityManager.RunningAppProcessInfo> getRunningAppProcesses() { 11541 enforceNotIsolatedCaller("getRunningAppProcesses"); 11542 // Lazy instantiation of list 11543 List<ActivityManager.RunningAppProcessInfo> runList = null; 11544 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 11545 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 11546 int userId = UserHandle.getUserId(Binder.getCallingUid()); 11547 synchronized (this) { 11548 // Iterate across all processes 11549 for (int i=mLruProcesses.size()-1; i>=0; i--) { 11550 ProcessRecord app = mLruProcesses.get(i); 11551 if (!allUsers && app.userId != userId) { 11552 continue; 11553 } 11554 if ((app.thread != null) && (!app.crashing && !app.notResponding)) { 11555 // Generate process state info for running application 11556 ActivityManager.RunningAppProcessInfo currApp = 11557 new ActivityManager.RunningAppProcessInfo(app.processName, 11558 app.pid, app.getPackageList()); 11559 fillInProcMemInfo(app, currApp); 11560 if (app.adjSource instanceof ProcessRecord) { 11561 currApp.importanceReasonPid = ((ProcessRecord)app.adjSource).pid; 11562 currApp.importanceReasonImportance = 11563 ActivityManager.RunningAppProcessInfo.procStateToImportance( 11564 app.adjSourceProcState); 11565 } else if (app.adjSource instanceof ActivityRecord) { 11566 ActivityRecord r = (ActivityRecord)app.adjSource; 11567 if (r.app != null) currApp.importanceReasonPid = r.app.pid; 11568 } 11569 if (app.adjTarget instanceof ComponentName) { 11570 currApp.importanceReasonComponent = (ComponentName)app.adjTarget; 11571 } 11572 //Slog.v(TAG, "Proc " + app.processName + ": imp=" + currApp.importance 11573 // + " lru=" + currApp.lru); 11574 if (runList == null) { 11575 runList = new ArrayList<ActivityManager.RunningAppProcessInfo>(); 11576 } 11577 runList.add(currApp); 11578 } 11579 } 11580 } 11581 return runList; 11582 } 11583 11584 public List<ApplicationInfo> getRunningExternalApplications() { 11585 enforceNotIsolatedCaller("getRunningExternalApplications"); 11586 List<ActivityManager.RunningAppProcessInfo> runningApps = getRunningAppProcesses(); 11587 List<ApplicationInfo> retList = new ArrayList<ApplicationInfo>(); 11588 if (runningApps != null && runningApps.size() > 0) { 11589 Set<String> extList = new HashSet<String>(); 11590 for (ActivityManager.RunningAppProcessInfo app : runningApps) { 11591 if (app.pkgList != null) { 11592 for (String pkg : app.pkgList) { 11593 extList.add(pkg); 11594 } 11595 } 11596 } 11597 IPackageManager pm = AppGlobals.getPackageManager(); 11598 for (String pkg : extList) { 11599 try { 11600 ApplicationInfo info = pm.getApplicationInfo(pkg, 0, UserHandle.getCallingUserId()); 11601 if ((info.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0) { 11602 retList.add(info); 11603 } 11604 } catch (RemoteException e) { 11605 } 11606 } 11607 } 11608 return retList; 11609 } 11610 11611 @Override 11612 public void getMyMemoryState(ActivityManager.RunningAppProcessInfo outInfo) { 11613 enforceNotIsolatedCaller("getMyMemoryState"); 11614 synchronized (this) { 11615 ProcessRecord proc; 11616 synchronized (mPidsSelfLocked) { 11617 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 11618 } 11619 fillInProcMemInfo(proc, outInfo); 11620 } 11621 } 11622 11623 @Override 11624 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 11625 if (checkCallingPermission(android.Manifest.permission.DUMP) 11626 != PackageManager.PERMISSION_GRANTED) { 11627 pw.println("Permission Denial: can't dump ActivityManager from from pid=" 11628 + Binder.getCallingPid() 11629 + ", uid=" + Binder.getCallingUid() 11630 + " without permission " 11631 + android.Manifest.permission.DUMP); 11632 return; 11633 } 11634 11635 boolean dumpAll = false; 11636 boolean dumpClient = false; 11637 String dumpPackage = null; 11638 11639 int opti = 0; 11640 while (opti < args.length) { 11641 String opt = args[opti]; 11642 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 11643 break; 11644 } 11645 opti++; 11646 if ("-a".equals(opt)) { 11647 dumpAll = true; 11648 } else if ("-c".equals(opt)) { 11649 dumpClient = true; 11650 } else if ("-h".equals(opt)) { 11651 pw.println("Activity manager dump options:"); 11652 pw.println(" [-a] [-c] [-h] [cmd] ..."); 11653 pw.println(" cmd may be one of:"); 11654 pw.println(" a[ctivities]: activity stack state"); 11655 pw.println(" r[recents]: recent activities state"); 11656 pw.println(" b[roadcasts] [PACKAGE_NAME] [history [-s]]: broadcast state"); 11657 pw.println(" i[ntents] [PACKAGE_NAME]: pending intent state"); 11658 pw.println(" p[rocesses] [PACKAGE_NAME]: process state"); 11659 pw.println(" o[om]: out of memory management"); 11660 pw.println(" prov[iders] [COMP_SPEC ...]: content provider state"); 11661 pw.println(" provider [COMP_SPEC]: provider client-side state"); 11662 pw.println(" s[ervices] [COMP_SPEC ...]: service state"); 11663 pw.println(" service [COMP_SPEC]: service client-side state"); 11664 pw.println(" package [PACKAGE_NAME]: all state related to given package"); 11665 pw.println(" all: dump all activities"); 11666 pw.println(" top: dump the top activity"); 11667 pw.println(" cmd may also be a COMP_SPEC to dump activities."); 11668 pw.println(" COMP_SPEC may be a component name (com.foo/.myApp),"); 11669 pw.println(" a partial substring in a component name, a"); 11670 pw.println(" hex object identifier."); 11671 pw.println(" -a: include all available server state."); 11672 pw.println(" -c: include client state."); 11673 return; 11674 } else { 11675 pw.println("Unknown argument: " + opt + "; use -h for help"); 11676 } 11677 } 11678 11679 long origId = Binder.clearCallingIdentity(); 11680 boolean more = false; 11681 // Is the caller requesting to dump a particular piece of data? 11682 if (opti < args.length) { 11683 String cmd = args[opti]; 11684 opti++; 11685 if ("activities".equals(cmd) || "a".equals(cmd)) { 11686 synchronized (this) { 11687 dumpActivitiesLocked(fd, pw, args, opti, true, dumpClient, null); 11688 } 11689 } else if ("recents".equals(cmd) || "r".equals(cmd)) { 11690 synchronized (this) { 11691 dumpRecentsLocked(fd, pw, args, opti, true, null); 11692 } 11693 } else if ("broadcasts".equals(cmd) || "b".equals(cmd)) { 11694 String[] newArgs; 11695 String name; 11696 if (opti >= args.length) { 11697 name = null; 11698 newArgs = EMPTY_STRING_ARRAY; 11699 } else { 11700 name = args[opti]; 11701 opti++; 11702 newArgs = new String[args.length - opti]; 11703 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11704 args.length - opti); 11705 } 11706 synchronized (this) { 11707 dumpBroadcastsLocked(fd, pw, args, opti, true, name); 11708 } 11709 } else if ("intents".equals(cmd) || "i".equals(cmd)) { 11710 String[] newArgs; 11711 String name; 11712 if (opti >= args.length) { 11713 name = null; 11714 newArgs = EMPTY_STRING_ARRAY; 11715 } else { 11716 name = args[opti]; 11717 opti++; 11718 newArgs = new String[args.length - opti]; 11719 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11720 args.length - opti); 11721 } 11722 synchronized (this) { 11723 dumpPendingIntentsLocked(fd, pw, args, opti, true, name); 11724 } 11725 } else if ("processes".equals(cmd) || "p".equals(cmd)) { 11726 String[] newArgs; 11727 String name; 11728 if (opti >= args.length) { 11729 name = null; 11730 newArgs = EMPTY_STRING_ARRAY; 11731 } else { 11732 name = args[opti]; 11733 opti++; 11734 newArgs = new String[args.length - opti]; 11735 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11736 args.length - opti); 11737 } 11738 synchronized (this) { 11739 dumpProcessesLocked(fd, pw, args, opti, true, name); 11740 } 11741 } else if ("oom".equals(cmd) || "o".equals(cmd)) { 11742 synchronized (this) { 11743 dumpOomLocked(fd, pw, args, opti, true); 11744 } 11745 } else if ("provider".equals(cmd)) { 11746 String[] newArgs; 11747 String name; 11748 if (opti >= args.length) { 11749 name = null; 11750 newArgs = EMPTY_STRING_ARRAY; 11751 } else { 11752 name = args[opti]; 11753 opti++; 11754 newArgs = new String[args.length - opti]; 11755 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, args.length - opti); 11756 } 11757 if (!dumpProvider(fd, pw, name, newArgs, 0, dumpAll)) { 11758 pw.println("No providers match: " + name); 11759 pw.println("Use -h for help."); 11760 } 11761 } else if ("providers".equals(cmd) || "prov".equals(cmd)) { 11762 synchronized (this) { 11763 dumpProvidersLocked(fd, pw, args, opti, true, null); 11764 } 11765 } else if ("service".equals(cmd)) { 11766 String[] newArgs; 11767 String name; 11768 if (opti >= args.length) { 11769 name = null; 11770 newArgs = EMPTY_STRING_ARRAY; 11771 } else { 11772 name = args[opti]; 11773 opti++; 11774 newArgs = new String[args.length - opti]; 11775 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11776 args.length - opti); 11777 } 11778 if (!mServices.dumpService(fd, pw, name, newArgs, 0, dumpAll)) { 11779 pw.println("No services match: " + name); 11780 pw.println("Use -h for help."); 11781 } 11782 } else if ("package".equals(cmd)) { 11783 String[] newArgs; 11784 if (opti >= args.length) { 11785 pw.println("package: no package name specified"); 11786 pw.println("Use -h for help."); 11787 } else { 11788 dumpPackage = args[opti]; 11789 opti++; 11790 newArgs = new String[args.length - opti]; 11791 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11792 args.length - opti); 11793 args = newArgs; 11794 opti = 0; 11795 more = true; 11796 } 11797 } else if ("services".equals(cmd) || "s".equals(cmd)) { 11798 synchronized (this) { 11799 mServices.dumpServicesLocked(fd, pw, args, opti, true, dumpClient, null); 11800 } 11801 } else { 11802 // Dumping a single activity? 11803 if (!dumpActivity(fd, pw, cmd, args, opti, dumpAll)) { 11804 pw.println("Bad activity command, or no activities match: " + cmd); 11805 pw.println("Use -h for help."); 11806 } 11807 } 11808 if (!more) { 11809 Binder.restoreCallingIdentity(origId); 11810 return; 11811 } 11812 } 11813 11814 // No piece of data specified, dump everything. 11815 synchronized (this) { 11816 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11817 pw.println(); 11818 if (dumpAll) { 11819 pw.println("-------------------------------------------------------------------------------"); 11820 } 11821 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11822 pw.println(); 11823 if (dumpAll) { 11824 pw.println("-------------------------------------------------------------------------------"); 11825 } 11826 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11827 pw.println(); 11828 if (dumpAll) { 11829 pw.println("-------------------------------------------------------------------------------"); 11830 } 11831 mServices.dumpServicesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 11832 pw.println(); 11833 if (dumpAll) { 11834 pw.println("-------------------------------------------------------------------------------"); 11835 } 11836 dumpRecentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11837 pw.println(); 11838 if (dumpAll) { 11839 pw.println("-------------------------------------------------------------------------------"); 11840 } 11841 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 11842 pw.println(); 11843 if (dumpAll) { 11844 pw.println("-------------------------------------------------------------------------------"); 11845 } 11846 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11847 } 11848 Binder.restoreCallingIdentity(origId); 11849 } 11850 11851 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11852 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) { 11853 pw.println("ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)"); 11854 11855 boolean printedAnything = mStackSupervisor.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient, 11856 dumpPackage); 11857 boolean needSep = printedAnything; 11858 11859 boolean printed = ActivityStackSupervisor.printThisActivity(pw, mFocusedActivity, 11860 dumpPackage, needSep, " mFocusedActivity: "); 11861 if (printed) { 11862 printedAnything = true; 11863 needSep = false; 11864 } 11865 11866 if (dumpPackage == null) { 11867 if (needSep) { 11868 pw.println(); 11869 } 11870 needSep = true; 11871 printedAnything = true; 11872 mStackSupervisor.dump(pw, " "); 11873 } 11874 11875 if (!printedAnything) { 11876 pw.println(" (nothing)"); 11877 } 11878 } 11879 11880 void dumpRecentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11881 int opti, boolean dumpAll, String dumpPackage) { 11882 pw.println("ACTIVITY MANAGER RECENT ACTIVITIES (dumpsys activity recents)"); 11883 11884 boolean printedAnything = false; 11885 11886 if (mRecentTasks.size() > 0) { 11887 boolean printedHeader = false; 11888 11889 final int N = mRecentTasks.size(); 11890 for (int i=0; i<N; i++) { 11891 TaskRecord tr = mRecentTasks.get(i); 11892 if (dumpPackage != null) { 11893 if (tr.realActivity == null || 11894 !dumpPackage.equals(tr.realActivity)) { 11895 continue; 11896 } 11897 } 11898 if (!printedHeader) { 11899 pw.println(" Recent tasks:"); 11900 printedHeader = true; 11901 printedAnything = true; 11902 } 11903 pw.print(" * Recent #"); pw.print(i); pw.print(": "); 11904 pw.println(tr); 11905 if (dumpAll) { 11906 mRecentTasks.get(i).dump(pw, " "); 11907 } 11908 } 11909 } 11910 11911 if (!printedAnything) { 11912 pw.println(" (nothing)"); 11913 } 11914 } 11915 11916 void dumpProcessesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11917 int opti, boolean dumpAll, String dumpPackage) { 11918 boolean needSep = false; 11919 boolean printedAnything = false; 11920 int numPers = 0; 11921 11922 pw.println("ACTIVITY MANAGER RUNNING PROCESSES (dumpsys activity processes)"); 11923 11924 if (dumpAll) { 11925 final int NP = mProcessNames.getMap().size(); 11926 for (int ip=0; ip<NP; ip++) { 11927 SparseArray<ProcessRecord> procs = mProcessNames.getMap().valueAt(ip); 11928 final int NA = procs.size(); 11929 for (int ia=0; ia<NA; ia++) { 11930 ProcessRecord r = procs.valueAt(ia); 11931 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11932 continue; 11933 } 11934 if (!needSep) { 11935 pw.println(" All known processes:"); 11936 needSep = true; 11937 printedAnything = true; 11938 } 11939 pw.print(r.persistent ? " *PERS*" : " *APP*"); 11940 pw.print(" UID "); pw.print(procs.keyAt(ia)); 11941 pw.print(" "); pw.println(r); 11942 r.dump(pw, " "); 11943 if (r.persistent) { 11944 numPers++; 11945 } 11946 } 11947 } 11948 } 11949 11950 if (mIsolatedProcesses.size() > 0) { 11951 boolean printed = false; 11952 for (int i=0; i<mIsolatedProcesses.size(); i++) { 11953 ProcessRecord r = mIsolatedProcesses.valueAt(i); 11954 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11955 continue; 11956 } 11957 if (!printed) { 11958 if (needSep) { 11959 pw.println(); 11960 } 11961 pw.println(" Isolated process list (sorted by uid):"); 11962 printedAnything = true; 11963 printed = true; 11964 needSep = true; 11965 } 11966 pw.println(String.format("%sIsolated #%2d: %s", 11967 " ", i, r.toString())); 11968 } 11969 } 11970 11971 if (mLruProcesses.size() > 0) { 11972 if (needSep) { 11973 pw.println(); 11974 } 11975 pw.print(" Process LRU list (sorted by oom_adj, "); pw.print(mLruProcesses.size()); 11976 pw.print(" total, non-act at "); 11977 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 11978 pw.print(", non-svc at "); 11979 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 11980 pw.println("):"); 11981 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", false, dumpPackage); 11982 needSep = true; 11983 printedAnything = true; 11984 } 11985 11986 if (dumpAll || dumpPackage != null) { 11987 synchronized (mPidsSelfLocked) { 11988 boolean printed = false; 11989 for (int i=0; i<mPidsSelfLocked.size(); i++) { 11990 ProcessRecord r = mPidsSelfLocked.valueAt(i); 11991 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11992 continue; 11993 } 11994 if (!printed) { 11995 if (needSep) pw.println(); 11996 needSep = true; 11997 pw.println(" PID mappings:"); 11998 printed = true; 11999 printedAnything = true; 12000 } 12001 pw.print(" PID #"); pw.print(mPidsSelfLocked.keyAt(i)); 12002 pw.print(": "); pw.println(mPidsSelfLocked.valueAt(i)); 12003 } 12004 } 12005 } 12006 12007 if (mForegroundProcesses.size() > 0) { 12008 synchronized (mPidsSelfLocked) { 12009 boolean printed = false; 12010 for (int i=0; i<mForegroundProcesses.size(); i++) { 12011 ProcessRecord r = mPidsSelfLocked.get( 12012 mForegroundProcesses.valueAt(i).pid); 12013 if (dumpPackage != null && (r == null 12014 || !r.pkgList.containsKey(dumpPackage))) { 12015 continue; 12016 } 12017 if (!printed) { 12018 if (needSep) pw.println(); 12019 needSep = true; 12020 pw.println(" Foreground Processes:"); 12021 printed = true; 12022 printedAnything = true; 12023 } 12024 pw.print(" PID #"); pw.print(mForegroundProcesses.keyAt(i)); 12025 pw.print(": "); pw.println(mForegroundProcesses.valueAt(i)); 12026 } 12027 } 12028 } 12029 12030 if (mPersistentStartingProcesses.size() > 0) { 12031 if (needSep) pw.println(); 12032 needSep = true; 12033 printedAnything = true; 12034 pw.println(" Persisent processes that are starting:"); 12035 dumpProcessList(pw, this, mPersistentStartingProcesses, " ", 12036 "Starting Norm", "Restarting PERS", dumpPackage); 12037 } 12038 12039 if (mRemovedProcesses.size() > 0) { 12040 if (needSep) pw.println(); 12041 needSep = true; 12042 printedAnything = true; 12043 pw.println(" Processes that are being removed:"); 12044 dumpProcessList(pw, this, mRemovedProcesses, " ", 12045 "Removed Norm", "Removed PERS", dumpPackage); 12046 } 12047 12048 if (mProcessesOnHold.size() > 0) { 12049 if (needSep) pw.println(); 12050 needSep = true; 12051 printedAnything = true; 12052 pw.println(" Processes that are on old until the system is ready:"); 12053 dumpProcessList(pw, this, mProcessesOnHold, " ", 12054 "OnHold Norm", "OnHold PERS", dumpPackage); 12055 } 12056 12057 needSep = dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, dumpPackage); 12058 12059 if (mProcessCrashTimes.getMap().size() > 0) { 12060 boolean printed = false; 12061 long now = SystemClock.uptimeMillis(); 12062 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 12063 final int NP = pmap.size(); 12064 for (int ip=0; ip<NP; ip++) { 12065 String pname = pmap.keyAt(ip); 12066 SparseArray<Long> uids = pmap.valueAt(ip); 12067 final int N = uids.size(); 12068 for (int i=0; i<N; i++) { 12069 int puid = uids.keyAt(i); 12070 ProcessRecord r = mProcessNames.get(pname, puid); 12071 if (dumpPackage != null && (r == null 12072 || !r.pkgList.containsKey(dumpPackage))) { 12073 continue; 12074 } 12075 if (!printed) { 12076 if (needSep) pw.println(); 12077 needSep = true; 12078 pw.println(" Time since processes crashed:"); 12079 printed = true; 12080 printedAnything = true; 12081 } 12082 pw.print(" Process "); pw.print(pname); 12083 pw.print(" uid "); pw.print(puid); 12084 pw.print(": last crashed "); 12085 TimeUtils.formatDuration(now-uids.valueAt(i), pw); 12086 pw.println(" ago"); 12087 } 12088 } 12089 } 12090 12091 if (mBadProcesses.getMap().size() > 0) { 12092 boolean printed = false; 12093 final ArrayMap<String, SparseArray<BadProcessInfo>> pmap = mBadProcesses.getMap(); 12094 final int NP = pmap.size(); 12095 for (int ip=0; ip<NP; ip++) { 12096 String pname = pmap.keyAt(ip); 12097 SparseArray<BadProcessInfo> uids = pmap.valueAt(ip); 12098 final int N = uids.size(); 12099 for (int i=0; i<N; i++) { 12100 int puid = uids.keyAt(i); 12101 ProcessRecord r = mProcessNames.get(pname, puid); 12102 if (dumpPackage != null && (r == null 12103 || !r.pkgList.containsKey(dumpPackage))) { 12104 continue; 12105 } 12106 if (!printed) { 12107 if (needSep) pw.println(); 12108 needSep = true; 12109 pw.println(" Bad processes:"); 12110 printedAnything = true; 12111 } 12112 BadProcessInfo info = uids.valueAt(i); 12113 pw.print(" Bad process "); pw.print(pname); 12114 pw.print(" uid "); pw.print(puid); 12115 pw.print(": crashed at time "); pw.println(info.time); 12116 if (info.shortMsg != null) { 12117 pw.print(" Short msg: "); pw.println(info.shortMsg); 12118 } 12119 if (info.longMsg != null) { 12120 pw.print(" Long msg: "); pw.println(info.longMsg); 12121 } 12122 if (info.stack != null) { 12123 pw.println(" Stack:"); 12124 int lastPos = 0; 12125 for (int pos=0; pos<info.stack.length(); pos++) { 12126 if (info.stack.charAt(pos) == '\n') { 12127 pw.print(" "); 12128 pw.write(info.stack, lastPos, pos-lastPos); 12129 pw.println(); 12130 lastPos = pos+1; 12131 } 12132 } 12133 if (lastPos < info.stack.length()) { 12134 pw.print(" "); 12135 pw.write(info.stack, lastPos, info.stack.length()-lastPos); 12136 pw.println(); 12137 } 12138 } 12139 } 12140 } 12141 } 12142 12143 if (dumpPackage == null) { 12144 pw.println(); 12145 needSep = false; 12146 pw.println(" mStartedUsers:"); 12147 for (int i=0; i<mStartedUsers.size(); i++) { 12148 UserStartedState uss = mStartedUsers.valueAt(i); 12149 pw.print(" User #"); pw.print(uss.mHandle.getIdentifier()); 12150 pw.print(": "); uss.dump("", pw); 12151 } 12152 pw.print(" mStartedUserArray: ["); 12153 for (int i=0; i<mStartedUserArray.length; i++) { 12154 if (i > 0) pw.print(", "); 12155 pw.print(mStartedUserArray[i]); 12156 } 12157 pw.println("]"); 12158 pw.print(" mUserLru: ["); 12159 for (int i=0; i<mUserLru.size(); i++) { 12160 if (i > 0) pw.print(", "); 12161 pw.print(mUserLru.get(i)); 12162 } 12163 pw.println("]"); 12164 if (dumpAll) { 12165 pw.print(" mStartedUserArray: "); pw.println(Arrays.toString(mStartedUserArray)); 12166 } 12167 synchronized (mUserProfileGroupIdsSelfLocked) { 12168 if (mUserProfileGroupIdsSelfLocked.size() > 0) { 12169 pw.println(" mUserProfileGroupIds:"); 12170 for (int i=0; i<mUserProfileGroupIdsSelfLocked.size(); i++) { 12171 pw.print(" User #"); 12172 pw.print(mUserProfileGroupIdsSelfLocked.keyAt(i)); 12173 pw.print(" -> profile #"); 12174 pw.println(mUserProfileGroupIdsSelfLocked.valueAt(i)); 12175 } 12176 } 12177 } 12178 } 12179 if (mHomeProcess != null && (dumpPackage == null 12180 || mHomeProcess.pkgList.containsKey(dumpPackage))) { 12181 if (needSep) { 12182 pw.println(); 12183 needSep = false; 12184 } 12185 pw.println(" mHomeProcess: " + mHomeProcess); 12186 } 12187 if (mPreviousProcess != null && (dumpPackage == null 12188 || mPreviousProcess.pkgList.containsKey(dumpPackage))) { 12189 if (needSep) { 12190 pw.println(); 12191 needSep = false; 12192 } 12193 pw.println(" mPreviousProcess: " + mPreviousProcess); 12194 } 12195 if (dumpAll) { 12196 StringBuilder sb = new StringBuilder(128); 12197 sb.append(" mPreviousProcessVisibleTime: "); 12198 TimeUtils.formatDuration(mPreviousProcessVisibleTime, sb); 12199 pw.println(sb); 12200 } 12201 if (mHeavyWeightProcess != null && (dumpPackage == null 12202 || mHeavyWeightProcess.pkgList.containsKey(dumpPackage))) { 12203 if (needSep) { 12204 pw.println(); 12205 needSep = false; 12206 } 12207 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 12208 } 12209 if (dumpPackage == null) { 12210 pw.println(" mConfiguration: " + mConfiguration); 12211 } 12212 if (dumpAll) { 12213 pw.println(" mConfigWillChange: " + getFocusedStack().mConfigWillChange); 12214 if (mCompatModePackages.getPackages().size() > 0) { 12215 boolean printed = false; 12216 for (Map.Entry<String, Integer> entry 12217 : mCompatModePackages.getPackages().entrySet()) { 12218 String pkg = entry.getKey(); 12219 int mode = entry.getValue(); 12220 if (dumpPackage != null && !dumpPackage.equals(pkg)) { 12221 continue; 12222 } 12223 if (!printed) { 12224 pw.println(" mScreenCompatPackages:"); 12225 printed = true; 12226 } 12227 pw.print(" "); pw.print(pkg); pw.print(": "); 12228 pw.print(mode); pw.println(); 12229 } 12230 } 12231 } 12232 if (dumpPackage == null) { 12233 if (mSleeping || mWentToSleep || mLockScreenShown) { 12234 pw.println(" mSleeping=" + mSleeping + " mWentToSleep=" + mWentToSleep 12235 + " mLockScreenShown " + mLockScreenShown); 12236 } 12237 if (mShuttingDown || mRunningVoice) { 12238 pw.print(" mShuttingDown=" + mShuttingDown + " mRunningVoice=" + mRunningVoice); 12239 } 12240 } 12241 if (mDebugApp != null || mOrigDebugApp != null || mDebugTransient 12242 || mOrigWaitForDebugger) { 12243 if (dumpPackage == null || dumpPackage.equals(mDebugApp) 12244 || dumpPackage.equals(mOrigDebugApp)) { 12245 if (needSep) { 12246 pw.println(); 12247 needSep = false; 12248 } 12249 pw.println(" mDebugApp=" + mDebugApp + "/orig=" + mOrigDebugApp 12250 + " mDebugTransient=" + mDebugTransient 12251 + " mOrigWaitForDebugger=" + mOrigWaitForDebugger); 12252 } 12253 } 12254 if (mOpenGlTraceApp != null) { 12255 if (dumpPackage == null || dumpPackage.equals(mOpenGlTraceApp)) { 12256 if (needSep) { 12257 pw.println(); 12258 needSep = false; 12259 } 12260 pw.println(" mOpenGlTraceApp=" + mOpenGlTraceApp); 12261 } 12262 } 12263 if (mProfileApp != null || mProfileProc != null || mProfileFile != null 12264 || mProfileFd != null) { 12265 if (dumpPackage == null || dumpPackage.equals(mProfileApp)) { 12266 if (needSep) { 12267 pw.println(); 12268 needSep = false; 12269 } 12270 pw.println(" mProfileApp=" + mProfileApp + " mProfileProc=" + mProfileProc); 12271 pw.println(" mProfileFile=" + mProfileFile + " mProfileFd=" + mProfileFd); 12272 pw.println(" mProfileType=" + mProfileType + " mAutoStopProfiler=" 12273 + mAutoStopProfiler); 12274 } 12275 } 12276 if (dumpPackage == null) { 12277 if (mAlwaysFinishActivities || mController != null) { 12278 pw.println(" mAlwaysFinishActivities=" + mAlwaysFinishActivities 12279 + " mController=" + mController); 12280 } 12281 if (dumpAll) { 12282 pw.println(" Total persistent processes: " + numPers); 12283 pw.println(" mProcessesReady=" + mProcessesReady 12284 + " mSystemReady=" + mSystemReady); 12285 pw.println(" mBooting=" + mBooting 12286 + " mBooted=" + mBooted 12287 + " mFactoryTest=" + mFactoryTest); 12288 pw.print(" mLastPowerCheckRealtime="); 12289 TimeUtils.formatDuration(mLastPowerCheckRealtime, pw); 12290 pw.println(""); 12291 pw.print(" mLastPowerCheckUptime="); 12292 TimeUtils.formatDuration(mLastPowerCheckUptime, pw); 12293 pw.println(""); 12294 pw.println(" mGoingToSleep=" + mStackSupervisor.mGoingToSleep); 12295 pw.println(" mLaunchingActivity=" + mStackSupervisor.mLaunchingActivity); 12296 pw.println(" mAdjSeq=" + mAdjSeq + " mLruSeq=" + mLruSeq); 12297 pw.println(" mNumNonCachedProcs=" + mNumNonCachedProcs 12298 + " (" + mLruProcesses.size() + " total)" 12299 + " mNumCachedHiddenProcs=" + mNumCachedHiddenProcs 12300 + " mNumServiceProcs=" + mNumServiceProcs 12301 + " mNewNumServiceProcs=" + mNewNumServiceProcs); 12302 pw.println(" mAllowLowerMemLevel=" + mAllowLowerMemLevel 12303 + " mLastMemoryLevel" + mLastMemoryLevel 12304 + " mLastNumProcesses" + mLastNumProcesses); 12305 long now = SystemClock.uptimeMillis(); 12306 pw.print(" mLastIdleTime="); 12307 TimeUtils.formatDuration(now, mLastIdleTime, pw); 12308 pw.print(" mLowRamSinceLastIdle="); 12309 TimeUtils.formatDuration(getLowRamTimeSinceIdle(now), pw); 12310 pw.println(); 12311 } 12312 } 12313 12314 if (!printedAnything) { 12315 pw.println(" (nothing)"); 12316 } 12317 } 12318 12319 boolean dumpProcessesToGc(FileDescriptor fd, PrintWriter pw, String[] args, 12320 int opti, boolean needSep, boolean dumpAll, String dumpPackage) { 12321 if (mProcessesToGc.size() > 0) { 12322 boolean printed = false; 12323 long now = SystemClock.uptimeMillis(); 12324 for (int i=0; i<mProcessesToGc.size(); i++) { 12325 ProcessRecord proc = mProcessesToGc.get(i); 12326 if (dumpPackage != null && !dumpPackage.equals(proc.info.packageName)) { 12327 continue; 12328 } 12329 if (!printed) { 12330 if (needSep) pw.println(); 12331 needSep = true; 12332 pw.println(" Processes that are waiting to GC:"); 12333 printed = true; 12334 } 12335 pw.print(" Process "); pw.println(proc); 12336 pw.print(" lowMem="); pw.print(proc.reportLowMemory); 12337 pw.print(", last gced="); 12338 pw.print(now-proc.lastRequestedGc); 12339 pw.print(" ms ago, last lowMem="); 12340 pw.print(now-proc.lastLowMemory); 12341 pw.println(" ms ago"); 12342 12343 } 12344 } 12345 return needSep; 12346 } 12347 12348 void printOomLevel(PrintWriter pw, String name, int adj) { 12349 pw.print(" "); 12350 if (adj >= 0) { 12351 pw.print(' '); 12352 if (adj < 10) pw.print(' '); 12353 } else { 12354 if (adj > -10) pw.print(' '); 12355 } 12356 pw.print(adj); 12357 pw.print(": "); 12358 pw.print(name); 12359 pw.print(" ("); 12360 pw.print(mProcessList.getMemLevel(adj)/1024); 12361 pw.println(" kB)"); 12362 } 12363 12364 boolean dumpOomLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12365 int opti, boolean dumpAll) { 12366 boolean needSep = false; 12367 12368 if (mLruProcesses.size() > 0) { 12369 if (needSep) pw.println(); 12370 needSep = true; 12371 pw.println(" OOM levels:"); 12372 printOomLevel(pw, "SYSTEM_ADJ", ProcessList.SYSTEM_ADJ); 12373 printOomLevel(pw, "PERSISTENT_PROC_ADJ", ProcessList.PERSISTENT_PROC_ADJ); 12374 printOomLevel(pw, "FOREGROUND_APP_ADJ", ProcessList.FOREGROUND_APP_ADJ); 12375 printOomLevel(pw, "VISIBLE_APP_ADJ", ProcessList.VISIBLE_APP_ADJ); 12376 printOomLevel(pw, "PERCEPTIBLE_APP_ADJ", ProcessList.PERCEPTIBLE_APP_ADJ); 12377 printOomLevel(pw, "BACKUP_APP_ADJ", ProcessList.BACKUP_APP_ADJ); 12378 printOomLevel(pw, "HEAVY_WEIGHT_APP_ADJ", ProcessList.HEAVY_WEIGHT_APP_ADJ); 12379 printOomLevel(pw, "SERVICE_ADJ", ProcessList.SERVICE_ADJ); 12380 printOomLevel(pw, "HOME_APP_ADJ", ProcessList.HOME_APP_ADJ); 12381 printOomLevel(pw, "PREVIOUS_APP_ADJ", ProcessList.PREVIOUS_APP_ADJ); 12382 printOomLevel(pw, "SERVICE_B_ADJ", ProcessList.SERVICE_B_ADJ); 12383 printOomLevel(pw, "CACHED_APP_MIN_ADJ", ProcessList.CACHED_APP_MIN_ADJ); 12384 printOomLevel(pw, "CACHED_APP_MAX_ADJ", ProcessList.CACHED_APP_MAX_ADJ); 12385 12386 if (needSep) pw.println(); 12387 pw.print(" Process OOM control ("); pw.print(mLruProcesses.size()); 12388 pw.print(" total, non-act at "); 12389 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 12390 pw.print(", non-svc at "); 12391 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 12392 pw.println("):"); 12393 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", true, null); 12394 needSep = true; 12395 } 12396 12397 dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, null); 12398 12399 pw.println(); 12400 pw.println(" mHomeProcess: " + mHomeProcess); 12401 pw.println(" mPreviousProcess: " + mPreviousProcess); 12402 if (mHeavyWeightProcess != null) { 12403 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 12404 } 12405 12406 return true; 12407 } 12408 12409 /** 12410 * There are three ways to call this: 12411 * - no provider specified: dump all the providers 12412 * - a flattened component name that matched an existing provider was specified as the 12413 * first arg: dump that one provider 12414 * - the first arg isn't the flattened component name of an existing provider: 12415 * dump all providers whose component contains the first arg as a substring 12416 */ 12417 protected boolean dumpProvider(FileDescriptor fd, PrintWriter pw, String name, String[] args, 12418 int opti, boolean dumpAll) { 12419 return mProviderMap.dumpProvider(fd, pw, name, args, opti, dumpAll); 12420 } 12421 12422 static class ItemMatcher { 12423 ArrayList<ComponentName> components; 12424 ArrayList<String> strings; 12425 ArrayList<Integer> objects; 12426 boolean all; 12427 12428 ItemMatcher() { 12429 all = true; 12430 } 12431 12432 void build(String name) { 12433 ComponentName componentName = ComponentName.unflattenFromString(name); 12434 if (componentName != null) { 12435 if (components == null) { 12436 components = new ArrayList<ComponentName>(); 12437 } 12438 components.add(componentName); 12439 all = false; 12440 } else { 12441 int objectId = 0; 12442 // Not a '/' separated full component name; maybe an object ID? 12443 try { 12444 objectId = Integer.parseInt(name, 16); 12445 if (objects == null) { 12446 objects = new ArrayList<Integer>(); 12447 } 12448 objects.add(objectId); 12449 all = false; 12450 } catch (RuntimeException e) { 12451 // Not an integer; just do string match. 12452 if (strings == null) { 12453 strings = new ArrayList<String>(); 12454 } 12455 strings.add(name); 12456 all = false; 12457 } 12458 } 12459 } 12460 12461 int build(String[] args, int opti) { 12462 for (; opti<args.length; opti++) { 12463 String name = args[opti]; 12464 if ("--".equals(name)) { 12465 return opti+1; 12466 } 12467 build(name); 12468 } 12469 return opti; 12470 } 12471 12472 boolean match(Object object, ComponentName comp) { 12473 if (all) { 12474 return true; 12475 } 12476 if (components != null) { 12477 for (int i=0; i<components.size(); i++) { 12478 if (components.get(i).equals(comp)) { 12479 return true; 12480 } 12481 } 12482 } 12483 if (objects != null) { 12484 for (int i=0; i<objects.size(); i++) { 12485 if (System.identityHashCode(object) == objects.get(i)) { 12486 return true; 12487 } 12488 } 12489 } 12490 if (strings != null) { 12491 String flat = comp.flattenToString(); 12492 for (int i=0; i<strings.size(); i++) { 12493 if (flat.contains(strings.get(i))) { 12494 return true; 12495 } 12496 } 12497 } 12498 return false; 12499 } 12500 } 12501 12502 /** 12503 * There are three things that cmd can be: 12504 * - a flattened component name that matches an existing activity 12505 * - the cmd arg isn't the flattened component name of an existing activity: 12506 * dump all activity whose component contains the cmd as a substring 12507 * - A hex number of the ActivityRecord object instance. 12508 */ 12509 protected boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name, String[] args, 12510 int opti, boolean dumpAll) { 12511 ArrayList<ActivityRecord> activities; 12512 12513 synchronized (this) { 12514 activities = mStackSupervisor.getDumpActivitiesLocked(name); 12515 } 12516 12517 if (activities.size() <= 0) { 12518 return false; 12519 } 12520 12521 String[] newArgs = new String[args.length - opti]; 12522 System.arraycopy(args, opti, newArgs, 0, args.length - opti); 12523 12524 TaskRecord lastTask = null; 12525 boolean needSep = false; 12526 for (int i=activities.size()-1; i>=0; i--) { 12527 ActivityRecord r = activities.get(i); 12528 if (needSep) { 12529 pw.println(); 12530 } 12531 needSep = true; 12532 synchronized (this) { 12533 if (lastTask != r.task) { 12534 lastTask = r.task; 12535 pw.print("TASK "); pw.print(lastTask.affinity); 12536 pw.print(" id="); pw.println(lastTask.taskId); 12537 if (dumpAll) { 12538 lastTask.dump(pw, " "); 12539 } 12540 } 12541 } 12542 dumpActivity(" ", fd, pw, activities.get(i), newArgs, dumpAll); 12543 } 12544 return true; 12545 } 12546 12547 /** 12548 * Invokes IApplicationThread.dumpActivity() on the thread of the specified activity if 12549 * there is a thread associated with the activity. 12550 */ 12551 private void dumpActivity(String prefix, FileDescriptor fd, PrintWriter pw, 12552 final ActivityRecord r, String[] args, boolean dumpAll) { 12553 String innerPrefix = prefix + " "; 12554 synchronized (this) { 12555 pw.print(prefix); pw.print("ACTIVITY "); pw.print(r.shortComponentName); 12556 pw.print(" "); pw.print(Integer.toHexString(System.identityHashCode(r))); 12557 pw.print(" pid="); 12558 if (r.app != null) pw.println(r.app.pid); 12559 else pw.println("(not running)"); 12560 if (dumpAll) { 12561 r.dump(pw, innerPrefix); 12562 } 12563 } 12564 if (r.app != null && r.app.thread != null) { 12565 // flush anything that is already in the PrintWriter since the thread is going 12566 // to write to the file descriptor directly 12567 pw.flush(); 12568 try { 12569 TransferPipe tp = new TransferPipe(); 12570 try { 12571 r.app.thread.dumpActivity(tp.getWriteFd().getFileDescriptor(), 12572 r.appToken, innerPrefix, args); 12573 tp.go(fd); 12574 } finally { 12575 tp.kill(); 12576 } 12577 } catch (IOException e) { 12578 pw.println(innerPrefix + "Failure while dumping the activity: " + e); 12579 } catch (RemoteException e) { 12580 pw.println(innerPrefix + "Got a RemoteException while dumping the activity"); 12581 } 12582 } 12583 } 12584 12585 void dumpBroadcastsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12586 int opti, boolean dumpAll, String dumpPackage) { 12587 boolean needSep = false; 12588 boolean onlyHistory = false; 12589 boolean printedAnything = false; 12590 12591 if ("history".equals(dumpPackage)) { 12592 if (opti < args.length && "-s".equals(args[opti])) { 12593 dumpAll = false; 12594 } 12595 onlyHistory = true; 12596 dumpPackage = null; 12597 } 12598 12599 pw.println("ACTIVITY MANAGER BROADCAST STATE (dumpsys activity broadcasts)"); 12600 if (!onlyHistory && dumpAll) { 12601 if (mRegisteredReceivers.size() > 0) { 12602 boolean printed = false; 12603 Iterator it = mRegisteredReceivers.values().iterator(); 12604 while (it.hasNext()) { 12605 ReceiverList r = (ReceiverList)it.next(); 12606 if (dumpPackage != null && (r.app == null || 12607 !dumpPackage.equals(r.app.info.packageName))) { 12608 continue; 12609 } 12610 if (!printed) { 12611 pw.println(" Registered Receivers:"); 12612 needSep = true; 12613 printed = true; 12614 printedAnything = true; 12615 } 12616 pw.print(" * "); pw.println(r); 12617 r.dump(pw, " "); 12618 } 12619 } 12620 12621 if (mReceiverResolver.dump(pw, needSep ? 12622 "\n Receiver Resolver Table:" : " Receiver Resolver Table:", 12623 " ", dumpPackage, false)) { 12624 needSep = true; 12625 printedAnything = true; 12626 } 12627 } 12628 12629 for (BroadcastQueue q : mBroadcastQueues) { 12630 needSep = q.dumpLocked(fd, pw, args, opti, dumpAll, dumpPackage, needSep); 12631 printedAnything |= needSep; 12632 } 12633 12634 needSep = true; 12635 12636 if (!onlyHistory && mStickyBroadcasts != null && dumpPackage == null) { 12637 for (int user=0; user<mStickyBroadcasts.size(); user++) { 12638 if (needSep) { 12639 pw.println(); 12640 } 12641 needSep = true; 12642 printedAnything = true; 12643 pw.print(" Sticky broadcasts for user "); 12644 pw.print(mStickyBroadcasts.keyAt(user)); pw.println(":"); 12645 StringBuilder sb = new StringBuilder(128); 12646 for (Map.Entry<String, ArrayList<Intent>> ent 12647 : mStickyBroadcasts.valueAt(user).entrySet()) { 12648 pw.print(" * Sticky action "); pw.print(ent.getKey()); 12649 if (dumpAll) { 12650 pw.println(":"); 12651 ArrayList<Intent> intents = ent.getValue(); 12652 final int N = intents.size(); 12653 for (int i=0; i<N; i++) { 12654 sb.setLength(0); 12655 sb.append(" Intent: "); 12656 intents.get(i).toShortString(sb, false, true, false, false); 12657 pw.println(sb.toString()); 12658 Bundle bundle = intents.get(i).getExtras(); 12659 if (bundle != null) { 12660 pw.print(" "); 12661 pw.println(bundle.toString()); 12662 } 12663 } 12664 } else { 12665 pw.println(""); 12666 } 12667 } 12668 } 12669 } 12670 12671 if (!onlyHistory && dumpAll) { 12672 pw.println(); 12673 for (BroadcastQueue queue : mBroadcastQueues) { 12674 pw.println(" mBroadcastsScheduled [" + queue.mQueueName + "]=" 12675 + queue.mBroadcastsScheduled); 12676 } 12677 pw.println(" mHandler:"); 12678 mHandler.dump(new PrintWriterPrinter(pw), " "); 12679 needSep = true; 12680 printedAnything = true; 12681 } 12682 12683 if (!printedAnything) { 12684 pw.println(" (nothing)"); 12685 } 12686 } 12687 12688 void dumpProvidersLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12689 int opti, boolean dumpAll, String dumpPackage) { 12690 boolean needSep; 12691 boolean printedAnything = false; 12692 12693 ItemMatcher matcher = new ItemMatcher(); 12694 matcher.build(args, opti); 12695 12696 pw.println("ACTIVITY MANAGER CONTENT PROVIDERS (dumpsys activity providers)"); 12697 12698 needSep = mProviderMap.dumpProvidersLocked(pw, dumpAll, dumpPackage); 12699 printedAnything |= needSep; 12700 12701 if (mLaunchingProviders.size() > 0) { 12702 boolean printed = false; 12703 for (int i=mLaunchingProviders.size()-1; i>=0; i--) { 12704 ContentProviderRecord r = mLaunchingProviders.get(i); 12705 if (dumpPackage != null && !dumpPackage.equals(r.name.getPackageName())) { 12706 continue; 12707 } 12708 if (!printed) { 12709 if (needSep) pw.println(); 12710 needSep = true; 12711 pw.println(" Launching content providers:"); 12712 printed = true; 12713 printedAnything = true; 12714 } 12715 pw.print(" Launching #"); pw.print(i); pw.print(": "); 12716 pw.println(r); 12717 } 12718 } 12719 12720 if (mGrantedUriPermissions.size() > 0) { 12721 boolean printed = false; 12722 int dumpUid = -2; 12723 if (dumpPackage != null) { 12724 try { 12725 dumpUid = mContext.getPackageManager().getPackageUid(dumpPackage, 0); 12726 } catch (NameNotFoundException e) { 12727 dumpUid = -1; 12728 } 12729 } 12730 for (int i=0; i<mGrantedUriPermissions.size(); i++) { 12731 int uid = mGrantedUriPermissions.keyAt(i); 12732 if (dumpUid >= -1 && UserHandle.getAppId(uid) != dumpUid) { 12733 continue; 12734 } 12735 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 12736 if (!printed) { 12737 if (needSep) pw.println(); 12738 needSep = true; 12739 pw.println(" Granted Uri Permissions:"); 12740 printed = true; 12741 printedAnything = true; 12742 } 12743 pw.print(" * UID "); pw.print(uid); pw.println(" holds:"); 12744 for (UriPermission perm : perms.values()) { 12745 pw.print(" "); pw.println(perm); 12746 if (dumpAll) { 12747 perm.dump(pw, " "); 12748 } 12749 } 12750 } 12751 } 12752 12753 if (!printedAnything) { 12754 pw.println(" (nothing)"); 12755 } 12756 } 12757 12758 void dumpPendingIntentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12759 int opti, boolean dumpAll, String dumpPackage) { 12760 boolean printed = false; 12761 12762 pw.println("ACTIVITY MANAGER PENDING INTENTS (dumpsys activity intents)"); 12763 12764 if (mIntentSenderRecords.size() > 0) { 12765 Iterator<WeakReference<PendingIntentRecord>> it 12766 = mIntentSenderRecords.values().iterator(); 12767 while (it.hasNext()) { 12768 WeakReference<PendingIntentRecord> ref = it.next(); 12769 PendingIntentRecord rec = ref != null ? ref.get(): null; 12770 if (dumpPackage != null && (rec == null 12771 || !dumpPackage.equals(rec.key.packageName))) { 12772 continue; 12773 } 12774 printed = true; 12775 if (rec != null) { 12776 pw.print(" * "); pw.println(rec); 12777 if (dumpAll) { 12778 rec.dump(pw, " "); 12779 } 12780 } else { 12781 pw.print(" * "); pw.println(ref); 12782 } 12783 } 12784 } 12785 12786 if (!printed) { 12787 pw.println(" (nothing)"); 12788 } 12789 } 12790 12791 private static final int dumpProcessList(PrintWriter pw, 12792 ActivityManagerService service, List list, 12793 String prefix, String normalLabel, String persistentLabel, 12794 String dumpPackage) { 12795 int numPers = 0; 12796 final int N = list.size()-1; 12797 for (int i=N; i>=0; i--) { 12798 ProcessRecord r = (ProcessRecord)list.get(i); 12799 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 12800 continue; 12801 } 12802 pw.println(String.format("%s%s #%2d: %s", 12803 prefix, (r.persistent ? persistentLabel : normalLabel), 12804 i, r.toString())); 12805 if (r.persistent) { 12806 numPers++; 12807 } 12808 } 12809 return numPers; 12810 } 12811 12812 private static final boolean dumpProcessOomList(PrintWriter pw, 12813 ActivityManagerService service, List<ProcessRecord> origList, 12814 String prefix, String normalLabel, String persistentLabel, 12815 boolean inclDetails, String dumpPackage) { 12816 12817 ArrayList<Pair<ProcessRecord, Integer>> list 12818 = new ArrayList<Pair<ProcessRecord, Integer>>(origList.size()); 12819 for (int i=0; i<origList.size(); i++) { 12820 ProcessRecord r = origList.get(i); 12821 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 12822 continue; 12823 } 12824 list.add(new Pair<ProcessRecord, Integer>(origList.get(i), i)); 12825 } 12826 12827 if (list.size() <= 0) { 12828 return false; 12829 } 12830 12831 Comparator<Pair<ProcessRecord, Integer>> comparator 12832 = new Comparator<Pair<ProcessRecord, Integer>>() { 12833 @Override 12834 public int compare(Pair<ProcessRecord, Integer> object1, 12835 Pair<ProcessRecord, Integer> object2) { 12836 if (object1.first.setAdj != object2.first.setAdj) { 12837 return object1.first.setAdj > object2.first.setAdj ? -1 : 1; 12838 } 12839 if (object1.second.intValue() != object2.second.intValue()) { 12840 return object1.second.intValue() > object2.second.intValue() ? -1 : 1; 12841 } 12842 return 0; 12843 } 12844 }; 12845 12846 Collections.sort(list, comparator); 12847 12848 final long curRealtime = SystemClock.elapsedRealtime(); 12849 final long realtimeSince = curRealtime - service.mLastPowerCheckRealtime; 12850 final long curUptime = SystemClock.uptimeMillis(); 12851 final long uptimeSince = curUptime - service.mLastPowerCheckUptime; 12852 12853 for (int i=list.size()-1; i>=0; i--) { 12854 ProcessRecord r = list.get(i).first; 12855 String oomAdj = ProcessList.makeOomAdjString(r.setAdj); 12856 char schedGroup; 12857 switch (r.setSchedGroup) { 12858 case Process.THREAD_GROUP_BG_NONINTERACTIVE: 12859 schedGroup = 'B'; 12860 break; 12861 case Process.THREAD_GROUP_DEFAULT: 12862 schedGroup = 'F'; 12863 break; 12864 default: 12865 schedGroup = '?'; 12866 break; 12867 } 12868 char foreground; 12869 if (r.foregroundActivities) { 12870 foreground = 'A'; 12871 } else if (r.foregroundServices) { 12872 foreground = 'S'; 12873 } else { 12874 foreground = ' '; 12875 } 12876 String procState = ProcessList.makeProcStateString(r.curProcState); 12877 pw.print(prefix); 12878 pw.print(r.persistent ? persistentLabel : normalLabel); 12879 pw.print(" #"); 12880 int num = (origList.size()-1)-list.get(i).second; 12881 if (num < 10) pw.print(' '); 12882 pw.print(num); 12883 pw.print(": "); 12884 pw.print(oomAdj); 12885 pw.print(' '); 12886 pw.print(schedGroup); 12887 pw.print('/'); 12888 pw.print(foreground); 12889 pw.print('/'); 12890 pw.print(procState); 12891 pw.print(" trm:"); 12892 if (r.trimMemoryLevel < 10) pw.print(' '); 12893 pw.print(r.trimMemoryLevel); 12894 pw.print(' '); 12895 pw.print(r.toShortString()); 12896 pw.print(" ("); 12897 pw.print(r.adjType); 12898 pw.println(')'); 12899 if (r.adjSource != null || r.adjTarget != null) { 12900 pw.print(prefix); 12901 pw.print(" "); 12902 if (r.adjTarget instanceof ComponentName) { 12903 pw.print(((ComponentName)r.adjTarget).flattenToShortString()); 12904 } else if (r.adjTarget != null) { 12905 pw.print(r.adjTarget.toString()); 12906 } else { 12907 pw.print("{null}"); 12908 } 12909 pw.print("<="); 12910 if (r.adjSource instanceof ProcessRecord) { 12911 pw.print("Proc{"); 12912 pw.print(((ProcessRecord)r.adjSource).toShortString()); 12913 pw.println("}"); 12914 } else if (r.adjSource != null) { 12915 pw.println(r.adjSource.toString()); 12916 } else { 12917 pw.println("{null}"); 12918 } 12919 } 12920 if (inclDetails) { 12921 pw.print(prefix); 12922 pw.print(" "); 12923 pw.print("oom: max="); pw.print(r.maxAdj); 12924 pw.print(" curRaw="); pw.print(r.curRawAdj); 12925 pw.print(" setRaw="); pw.print(r.setRawAdj); 12926 pw.print(" cur="); pw.print(r.curAdj); 12927 pw.print(" set="); pw.println(r.setAdj); 12928 pw.print(prefix); 12929 pw.print(" "); 12930 pw.print("state: cur="); pw.print(ProcessList.makeProcStateString(r.curProcState)); 12931 pw.print(" set="); pw.print(ProcessList.makeProcStateString(r.setProcState)); 12932 pw.print(" lastPss="); pw.print(r.lastPss); 12933 pw.print(" lastCachedPss="); pw.println(r.lastCachedPss); 12934 pw.print(prefix); 12935 pw.print(" "); 12936 pw.print("cached="); pw.print(r.cached); 12937 pw.print(" empty="); pw.print(r.empty); 12938 pw.print(" hasAboveClient="); pw.println(r.hasAboveClient); 12939 12940 if (r.setProcState >= ActivityManager.PROCESS_STATE_SERVICE) { 12941 if (r.lastWakeTime != 0) { 12942 long wtime; 12943 BatteryStatsImpl stats = service.mBatteryStatsService.getActiveStatistics(); 12944 synchronized (stats) { 12945 wtime = stats.getProcessWakeTime(r.info.uid, 12946 r.pid, curRealtime); 12947 } 12948 long timeUsed = wtime - r.lastWakeTime; 12949 pw.print(prefix); 12950 pw.print(" "); 12951 pw.print("keep awake over "); 12952 TimeUtils.formatDuration(realtimeSince, pw); 12953 pw.print(" used "); 12954 TimeUtils.formatDuration(timeUsed, pw); 12955 pw.print(" ("); 12956 pw.print((timeUsed*100)/realtimeSince); 12957 pw.println("%)"); 12958 } 12959 if (r.lastCpuTime != 0) { 12960 long timeUsed = r.curCpuTime - r.lastCpuTime; 12961 pw.print(prefix); 12962 pw.print(" "); 12963 pw.print("run cpu over "); 12964 TimeUtils.formatDuration(uptimeSince, pw); 12965 pw.print(" used "); 12966 TimeUtils.formatDuration(timeUsed, pw); 12967 pw.print(" ("); 12968 pw.print((timeUsed*100)/uptimeSince); 12969 pw.println("%)"); 12970 } 12971 } 12972 } 12973 } 12974 return true; 12975 } 12976 12977 ArrayList<ProcessRecord> collectProcesses(PrintWriter pw, int start, String[] args) { 12978 ArrayList<ProcessRecord> procs; 12979 synchronized (this) { 12980 if (args != null && args.length > start 12981 && args[start].charAt(0) != '-') { 12982 procs = new ArrayList<ProcessRecord>(); 12983 int pid = -1; 12984 try { 12985 pid = Integer.parseInt(args[start]); 12986 } catch (NumberFormatException e) { 12987 } 12988 for (int i=mLruProcesses.size()-1; i>=0; i--) { 12989 ProcessRecord proc = mLruProcesses.get(i); 12990 if (proc.pid == pid) { 12991 procs.add(proc); 12992 } else if (proc.processName.equals(args[start])) { 12993 procs.add(proc); 12994 } 12995 } 12996 if (procs.size() <= 0) { 12997 return null; 12998 } 12999 } else { 13000 procs = new ArrayList<ProcessRecord>(mLruProcesses); 13001 } 13002 } 13003 return procs; 13004 } 13005 13006 final void dumpGraphicsHardwareUsage(FileDescriptor fd, 13007 PrintWriter pw, String[] args) { 13008 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 13009 if (procs == null) { 13010 pw.println("No process found for: " + args[0]); 13011 return; 13012 } 13013 13014 long uptime = SystemClock.uptimeMillis(); 13015 long realtime = SystemClock.elapsedRealtime(); 13016 pw.println("Applications Graphics Acceleration Info:"); 13017 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 13018 13019 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 13020 ProcessRecord r = procs.get(i); 13021 if (r.thread != null) { 13022 pw.println("\n** Graphics info for pid " + r.pid + " [" + r.processName + "] **"); 13023 pw.flush(); 13024 try { 13025 TransferPipe tp = new TransferPipe(); 13026 try { 13027 r.thread.dumpGfxInfo(tp.getWriteFd().getFileDescriptor(), args); 13028 tp.go(fd); 13029 } finally { 13030 tp.kill(); 13031 } 13032 } catch (IOException e) { 13033 pw.println("Failure while dumping the app: " + r); 13034 pw.flush(); 13035 } catch (RemoteException e) { 13036 pw.println("Got a RemoteException while dumping the app " + r); 13037 pw.flush(); 13038 } 13039 } 13040 } 13041 } 13042 13043 final void dumpDbInfo(FileDescriptor fd, PrintWriter pw, String[] args) { 13044 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 13045 if (procs == null) { 13046 pw.println("No process found for: " + args[0]); 13047 return; 13048 } 13049 13050 pw.println("Applications Database Info:"); 13051 13052 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 13053 ProcessRecord r = procs.get(i); 13054 if (r.thread != null) { 13055 pw.println("\n** Database info for pid " + r.pid + " [" + r.processName + "] **"); 13056 pw.flush(); 13057 try { 13058 TransferPipe tp = new TransferPipe(); 13059 try { 13060 r.thread.dumpDbInfo(tp.getWriteFd().getFileDescriptor(), args); 13061 tp.go(fd); 13062 } finally { 13063 tp.kill(); 13064 } 13065 } catch (IOException e) { 13066 pw.println("Failure while dumping the app: " + r); 13067 pw.flush(); 13068 } catch (RemoteException e) { 13069 pw.println("Got a RemoteException while dumping the app " + r); 13070 pw.flush(); 13071 } 13072 } 13073 } 13074 } 13075 13076 final static class MemItem { 13077 final boolean isProc; 13078 final String label; 13079 final String shortLabel; 13080 final long pss; 13081 final int id; 13082 final boolean hasActivities; 13083 ArrayList<MemItem> subitems; 13084 13085 public MemItem(String _label, String _shortLabel, long _pss, int _id, 13086 boolean _hasActivities) { 13087 isProc = true; 13088 label = _label; 13089 shortLabel = _shortLabel; 13090 pss = _pss; 13091 id = _id; 13092 hasActivities = _hasActivities; 13093 } 13094 13095 public MemItem(String _label, String _shortLabel, long _pss, int _id) { 13096 isProc = false; 13097 label = _label; 13098 shortLabel = _shortLabel; 13099 pss = _pss; 13100 id = _id; 13101 hasActivities = false; 13102 } 13103 } 13104 13105 static final void dumpMemItems(PrintWriter pw, String prefix, String tag, 13106 ArrayList<MemItem> items, boolean sort, boolean isCompact) { 13107 if (sort && !isCompact) { 13108 Collections.sort(items, new Comparator<MemItem>() { 13109 @Override 13110 public int compare(MemItem lhs, MemItem rhs) { 13111 if (lhs.pss < rhs.pss) { 13112 return 1; 13113 } else if (lhs.pss > rhs.pss) { 13114 return -1; 13115 } 13116 return 0; 13117 } 13118 }); 13119 } 13120 13121 for (int i=0; i<items.size(); i++) { 13122 MemItem mi = items.get(i); 13123 if (!isCompact) { 13124 pw.print(prefix); pw.printf("%7d kB: ", mi.pss); pw.println(mi.label); 13125 } else if (mi.isProc) { 13126 pw.print("proc,"); pw.print(tag); pw.print(","); pw.print(mi.shortLabel); 13127 pw.print(","); pw.print(mi.id); pw.print(","); pw.print(mi.pss); 13128 pw.println(mi.hasActivities ? ",a" : ",e"); 13129 } else { 13130 pw.print(tag); pw.print(","); pw.print(mi.shortLabel); pw.print(","); 13131 pw.println(mi.pss); 13132 } 13133 if (mi.subitems != null) { 13134 dumpMemItems(pw, prefix + " ", mi.shortLabel, mi.subitems, 13135 true, isCompact); 13136 } 13137 } 13138 } 13139 13140 // These are in KB. 13141 static final long[] DUMP_MEM_BUCKETS = new long[] { 13142 5*1024, 7*1024, 10*1024, 15*1024, 20*1024, 30*1024, 40*1024, 80*1024, 13143 120*1024, 160*1024, 200*1024, 13144 250*1024, 300*1024, 350*1024, 400*1024, 500*1024, 600*1024, 800*1024, 13145 1*1024*1024, 2*1024*1024, 5*1024*1024, 10*1024*1024, 20*1024*1024 13146 }; 13147 13148 static final void appendMemBucket(StringBuilder out, long memKB, String label, 13149 boolean stackLike) { 13150 int start = label.lastIndexOf('.'); 13151 if (start >= 0) start++; 13152 else start = 0; 13153 int end = label.length(); 13154 for (int i=0; i<DUMP_MEM_BUCKETS.length; i++) { 13155 if (DUMP_MEM_BUCKETS[i] >= memKB) { 13156 long bucket = DUMP_MEM_BUCKETS[i]/1024; 13157 out.append(bucket); 13158 out.append(stackLike ? "MB." : "MB "); 13159 out.append(label, start, end); 13160 return; 13161 } 13162 } 13163 out.append(memKB/1024); 13164 out.append(stackLike ? "MB." : "MB "); 13165 out.append(label, start, end); 13166 } 13167 13168 static final int[] DUMP_MEM_OOM_ADJ = new int[] { 13169 ProcessList.NATIVE_ADJ, 13170 ProcessList.SYSTEM_ADJ, ProcessList.PERSISTENT_PROC_ADJ, ProcessList.FOREGROUND_APP_ADJ, 13171 ProcessList.VISIBLE_APP_ADJ, ProcessList.PERCEPTIBLE_APP_ADJ, 13172 ProcessList.BACKUP_APP_ADJ, ProcessList.HEAVY_WEIGHT_APP_ADJ, 13173 ProcessList.SERVICE_ADJ, ProcessList.HOME_APP_ADJ, 13174 ProcessList.PREVIOUS_APP_ADJ, ProcessList.SERVICE_B_ADJ, ProcessList.CACHED_APP_MAX_ADJ 13175 }; 13176 static final String[] DUMP_MEM_OOM_LABEL = new String[] { 13177 "Native", 13178 "System", "Persistent", "Foreground", 13179 "Visible", "Perceptible", 13180 "Heavy Weight", "Backup", 13181 "A Services", "Home", 13182 "Previous", "B Services", "Cached" 13183 }; 13184 static final String[] DUMP_MEM_OOM_COMPACT_LABEL = new String[] { 13185 "native", 13186 "sys", "pers", "fore", 13187 "vis", "percept", 13188 "heavy", "backup", 13189 "servicea", "home", 13190 "prev", "serviceb", "cached" 13191 }; 13192 13193 private final void dumpApplicationMemoryUsageHeader(PrintWriter pw, long uptime, 13194 long realtime, boolean isCheckinRequest, boolean isCompact) { 13195 if (isCheckinRequest || isCompact) { 13196 // short checkin version 13197 pw.print("time,"); pw.print(uptime); pw.print(","); pw.println(realtime); 13198 } else { 13199 pw.println("Applications Memory Usage (kB):"); 13200 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 13201 } 13202 } 13203 13204 final void dumpApplicationMemoryUsage(FileDescriptor fd, 13205 PrintWriter pw, String prefix, String[] args, boolean brief, PrintWriter categoryPw) { 13206 boolean dumpDetails = false; 13207 boolean dumpFullDetails = false; 13208 boolean dumpDalvik = false; 13209 boolean oomOnly = false; 13210 boolean isCompact = false; 13211 boolean localOnly = false; 13212 13213 int opti = 0; 13214 while (opti < args.length) { 13215 String opt = args[opti]; 13216 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 13217 break; 13218 } 13219 opti++; 13220 if ("-a".equals(opt)) { 13221 dumpDetails = true; 13222 dumpFullDetails = true; 13223 dumpDalvik = true; 13224 } else if ("-d".equals(opt)) { 13225 dumpDalvik = true; 13226 } else if ("-c".equals(opt)) { 13227 isCompact = true; 13228 } else if ("--oom".equals(opt)) { 13229 oomOnly = true; 13230 } else if ("--local".equals(opt)) { 13231 localOnly = true; 13232 } else if ("-h".equals(opt)) { 13233 pw.println("meminfo dump options: [-a] [-d] [-c] [--oom] [process]"); 13234 pw.println(" -a: include all available information for each process."); 13235 pw.println(" -d: include dalvik details when dumping process details."); 13236 pw.println(" -c: dump in a compact machine-parseable representation."); 13237 pw.println(" --oom: only show processes organized by oom adj."); 13238 pw.println(" --local: only collect details locally, don't call process."); 13239 pw.println("If [process] is specified it can be the name or "); 13240 pw.println("pid of a specific process to dump."); 13241 return; 13242 } else { 13243 pw.println("Unknown argument: " + opt + "; use -h for help"); 13244 } 13245 } 13246 13247 final boolean isCheckinRequest = scanArgs(args, "--checkin"); 13248 long uptime = SystemClock.uptimeMillis(); 13249 long realtime = SystemClock.elapsedRealtime(); 13250 final long[] tmpLong = new long[1]; 13251 13252 ArrayList<ProcessRecord> procs = collectProcesses(pw, opti, args); 13253 if (procs == null) { 13254 // No Java processes. Maybe they want to print a native process. 13255 if (args != null && args.length > opti 13256 && args[opti].charAt(0) != '-') { 13257 ArrayList<ProcessCpuTracker.Stats> nativeProcs 13258 = new ArrayList<ProcessCpuTracker.Stats>(); 13259 updateCpuStatsNow(); 13260 int findPid = -1; 13261 try { 13262 findPid = Integer.parseInt(args[opti]); 13263 } catch (NumberFormatException e) { 13264 } 13265 synchronized (mProcessCpuThread) { 13266 final int N = mProcessCpuTracker.countStats(); 13267 for (int i=0; i<N; i++) { 13268 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 13269 if (st.pid == findPid || (st.baseName != null 13270 && st.baseName.equals(args[opti]))) { 13271 nativeProcs.add(st); 13272 } 13273 } 13274 } 13275 if (nativeProcs.size() > 0) { 13276 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, 13277 isCompact); 13278 Debug.MemoryInfo mi = null; 13279 for (int i = nativeProcs.size() - 1 ; i >= 0 ; i--) { 13280 final ProcessCpuTracker.Stats r = nativeProcs.get(i); 13281 final int pid = r.pid; 13282 if (!isCheckinRequest && dumpDetails) { 13283 pw.println("\n** MEMINFO in pid " + pid + " [" + r.baseName + "] **"); 13284 } 13285 if (mi == null) { 13286 mi = new Debug.MemoryInfo(); 13287 } 13288 if (dumpDetails || (!brief && !oomOnly)) { 13289 Debug.getMemoryInfo(pid, mi); 13290 } else { 13291 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 13292 mi.dalvikPrivateDirty = (int)tmpLong[0]; 13293 } 13294 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 13295 dumpDalvik, pid, r.baseName, 0, 0, 0, 0, 0, 0); 13296 if (isCheckinRequest) { 13297 pw.println(); 13298 } 13299 } 13300 return; 13301 } 13302 } 13303 pw.println("No process found for: " + args[opti]); 13304 return; 13305 } 13306 13307 if (!brief && !oomOnly && (procs.size() == 1 || isCheckinRequest)) { 13308 dumpDetails = true; 13309 } 13310 13311 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, isCompact); 13312 13313 String[] innerArgs = new String[args.length-opti]; 13314 System.arraycopy(args, opti, innerArgs, 0, args.length-opti); 13315 13316 ArrayList<MemItem> procMems = new ArrayList<MemItem>(); 13317 final SparseArray<MemItem> procMemsMap = new SparseArray<MemItem>(); 13318 long nativePss=0, dalvikPss=0, otherPss=0; 13319 long[] miscPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 13320 13321 long oomPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 13322 ArrayList<MemItem>[] oomProcs = (ArrayList<MemItem>[]) 13323 new ArrayList[DUMP_MEM_OOM_LABEL.length]; 13324 13325 long totalPss = 0; 13326 long cachedPss = 0; 13327 13328 Debug.MemoryInfo mi = null; 13329 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 13330 final ProcessRecord r = procs.get(i); 13331 final IApplicationThread thread; 13332 final int pid; 13333 final int oomAdj; 13334 final boolean hasActivities; 13335 synchronized (this) { 13336 thread = r.thread; 13337 pid = r.pid; 13338 oomAdj = r.getSetAdjWithServices(); 13339 hasActivities = r.activities.size() > 0; 13340 } 13341 if (thread != null) { 13342 if (!isCheckinRequest && dumpDetails) { 13343 pw.println("\n** MEMINFO in pid " + pid + " [" + r.processName + "] **"); 13344 } 13345 if (mi == null) { 13346 mi = new Debug.MemoryInfo(); 13347 } 13348 if (dumpDetails || (!brief && !oomOnly)) { 13349 Debug.getMemoryInfo(pid, mi); 13350 } else { 13351 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 13352 mi.dalvikPrivateDirty = (int)tmpLong[0]; 13353 } 13354 if (dumpDetails) { 13355 if (localOnly) { 13356 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 13357 dumpDalvik, pid, r.processName, 0, 0, 0, 0, 0, 0); 13358 if (isCheckinRequest) { 13359 pw.println(); 13360 } 13361 } else { 13362 try { 13363 pw.flush(); 13364 thread.dumpMemInfo(fd, mi, isCheckinRequest, dumpFullDetails, 13365 dumpDalvik, innerArgs); 13366 } catch (RemoteException e) { 13367 if (!isCheckinRequest) { 13368 pw.println("Got RemoteException!"); 13369 pw.flush(); 13370 } 13371 } 13372 } 13373 } 13374 13375 final long myTotalPss = mi.getTotalPss(); 13376 final long myTotalUss = mi.getTotalUss(); 13377 13378 synchronized (this) { 13379 if (r.thread != null && oomAdj == r.getSetAdjWithServices()) { 13380 // Record this for posterity if the process has been stable. 13381 r.baseProcessTracker.addPss(myTotalPss, myTotalUss, true, r.pkgList); 13382 } 13383 } 13384 13385 if (!isCheckinRequest && mi != null) { 13386 totalPss += myTotalPss; 13387 MemItem pssItem = new MemItem(r.processName + " (pid " + pid + 13388 (hasActivities ? " / activities)" : ")"), 13389 r.processName, myTotalPss, pid, hasActivities); 13390 procMems.add(pssItem); 13391 procMemsMap.put(pid, pssItem); 13392 13393 nativePss += mi.nativePss; 13394 dalvikPss += mi.dalvikPss; 13395 otherPss += mi.otherPss; 13396 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 13397 long mem = mi.getOtherPss(j); 13398 miscPss[j] += mem; 13399 otherPss -= mem; 13400 } 13401 13402 if (oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 13403 cachedPss += myTotalPss; 13404 } 13405 13406 for (int oomIndex=0; oomIndex<oomPss.length; oomIndex++) { 13407 if (oomAdj <= DUMP_MEM_OOM_ADJ[oomIndex] 13408 || oomIndex == (oomPss.length-1)) { 13409 oomPss[oomIndex] += myTotalPss; 13410 if (oomProcs[oomIndex] == null) { 13411 oomProcs[oomIndex] = new ArrayList<MemItem>(); 13412 } 13413 oomProcs[oomIndex].add(pssItem); 13414 break; 13415 } 13416 } 13417 } 13418 } 13419 } 13420 13421 long nativeProcTotalPss = 0; 13422 13423 if (!isCheckinRequest && procs.size() > 1) { 13424 // If we are showing aggregations, also look for native processes to 13425 // include so that our aggregations are more accurate. 13426 updateCpuStatsNow(); 13427 synchronized (mProcessCpuThread) { 13428 final int N = mProcessCpuTracker.countStats(); 13429 for (int i=0; i<N; i++) { 13430 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 13431 if (st.vsize > 0 && procMemsMap.indexOfKey(st.pid) < 0) { 13432 if (mi == null) { 13433 mi = new Debug.MemoryInfo(); 13434 } 13435 if (!brief && !oomOnly) { 13436 Debug.getMemoryInfo(st.pid, mi); 13437 } else { 13438 mi.nativePss = (int)Debug.getPss(st.pid, tmpLong); 13439 mi.nativePrivateDirty = (int)tmpLong[0]; 13440 } 13441 13442 final long myTotalPss = mi.getTotalPss(); 13443 totalPss += myTotalPss; 13444 nativeProcTotalPss += myTotalPss; 13445 13446 MemItem pssItem = new MemItem(st.name + " (pid " + st.pid + ")", 13447 st.name, myTotalPss, st.pid, false); 13448 procMems.add(pssItem); 13449 13450 nativePss += mi.nativePss; 13451 dalvikPss += mi.dalvikPss; 13452 otherPss += mi.otherPss; 13453 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 13454 long mem = mi.getOtherPss(j); 13455 miscPss[j] += mem; 13456 otherPss -= mem; 13457 } 13458 oomPss[0] += myTotalPss; 13459 if (oomProcs[0] == null) { 13460 oomProcs[0] = new ArrayList<MemItem>(); 13461 } 13462 oomProcs[0].add(pssItem); 13463 } 13464 } 13465 } 13466 13467 ArrayList<MemItem> catMems = new ArrayList<MemItem>(); 13468 13469 catMems.add(new MemItem("Native", "Native", nativePss, -1)); 13470 catMems.add(new MemItem("Dalvik", "Dalvik", dalvikPss, -2)); 13471 catMems.add(new MemItem("Unknown", "Unknown", otherPss, -3)); 13472 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 13473 String label = Debug.MemoryInfo.getOtherLabel(j); 13474 catMems.add(new MemItem(label, label, miscPss[j], j)); 13475 } 13476 13477 ArrayList<MemItem> oomMems = new ArrayList<MemItem>(); 13478 for (int j=0; j<oomPss.length; j++) { 13479 if (oomPss[j] != 0) { 13480 String label = isCompact ? DUMP_MEM_OOM_COMPACT_LABEL[j] 13481 : DUMP_MEM_OOM_LABEL[j]; 13482 MemItem item = new MemItem(label, label, oomPss[j], 13483 DUMP_MEM_OOM_ADJ[j]); 13484 item.subitems = oomProcs[j]; 13485 oomMems.add(item); 13486 } 13487 } 13488 13489 if (!brief && !oomOnly && !isCompact) { 13490 pw.println(); 13491 pw.println("Total PSS by process:"); 13492 dumpMemItems(pw, " ", "proc", procMems, true, isCompact); 13493 pw.println(); 13494 } 13495 if (!isCompact) { 13496 pw.println("Total PSS by OOM adjustment:"); 13497 } 13498 dumpMemItems(pw, " ", "oom", oomMems, false, isCompact); 13499 if (!brief && !oomOnly) { 13500 PrintWriter out = categoryPw != null ? categoryPw : pw; 13501 if (!isCompact) { 13502 out.println(); 13503 out.println("Total PSS by category:"); 13504 } 13505 dumpMemItems(out, " ", "cat", catMems, true, isCompact); 13506 } 13507 if (!isCompact) { 13508 pw.println(); 13509 } 13510 MemInfoReader memInfo = new MemInfoReader(); 13511 memInfo.readMemInfo(); 13512 if (nativeProcTotalPss > 0) { 13513 synchronized (this) { 13514 mProcessStats.addSysMemUsageLocked(memInfo.getCachedSizeKb(), 13515 memInfo.getFreeSizeKb(), memInfo.getZramTotalSizeKb(), 13516 memInfo.getBuffersSizeKb()+memInfo.getShmemSizeKb()+memInfo.getSlabSizeKb(), 13517 nativeProcTotalPss); 13518 } 13519 } 13520 if (!brief) { 13521 if (!isCompact) { 13522 pw.print("Total RAM: "); pw.print(memInfo.getTotalSizeKb()); 13523 pw.print(" kB (status "); 13524 switch (mLastMemoryLevel) { 13525 case ProcessStats.ADJ_MEM_FACTOR_NORMAL: 13526 pw.println("normal)"); 13527 break; 13528 case ProcessStats.ADJ_MEM_FACTOR_MODERATE: 13529 pw.println("moderate)"); 13530 break; 13531 case ProcessStats.ADJ_MEM_FACTOR_LOW: 13532 pw.println("low)"); 13533 break; 13534 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 13535 pw.println("critical)"); 13536 break; 13537 default: 13538 pw.print(mLastMemoryLevel); 13539 pw.println(")"); 13540 break; 13541 } 13542 pw.print(" Free RAM: "); pw.print(cachedPss + memInfo.getCachedSizeKb() 13543 + memInfo.getFreeSizeKb()); pw.print(" kB ("); 13544 pw.print(cachedPss); pw.print(" cached pss + "); 13545 pw.print(memInfo.getCachedSizeKb()); pw.print(" cached + "); 13546 pw.print(memInfo.getFreeSizeKb()); pw.println(" free)"); 13547 } else { 13548 pw.print("ram,"); pw.print(memInfo.getTotalSizeKb()); pw.print(","); 13549 pw.print(cachedPss + memInfo.getCachedSizeKb() 13550 + memInfo.getFreeSizeKb()); pw.print(","); 13551 pw.println(totalPss - cachedPss); 13552 } 13553 } 13554 if (!isCompact) { 13555 pw.print(" Used RAM: "); pw.print(totalPss - cachedPss 13556 + memInfo.getBuffersSizeKb() + memInfo.getShmemSizeKb() 13557 + memInfo.getSlabSizeKb()); pw.print(" kB ("); 13558 pw.print(totalPss - cachedPss); pw.print(" used pss + "); 13559 pw.print(memInfo.getBuffersSizeKb()); pw.print(" buffers + "); 13560 pw.print(memInfo.getShmemSizeKb()); pw.print(" shmem + "); 13561 pw.print(memInfo.getSlabSizeKb()); pw.println(" slab)"); 13562 pw.print(" Lost RAM: "); pw.print(memInfo.getTotalSizeKb() 13563 - totalPss - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 13564 - memInfo.getBuffersSizeKb() - memInfo.getShmemSizeKb() 13565 - memInfo.getSlabSizeKb()); pw.println(" kB"); 13566 } 13567 if (!brief) { 13568 if (memInfo.getZramTotalSizeKb() != 0) { 13569 if (!isCompact) { 13570 pw.print(" ZRAM: "); pw.print(memInfo.getZramTotalSizeKb()); 13571 pw.print(" kB physical used for "); 13572 pw.print(memInfo.getSwapTotalSizeKb() 13573 - memInfo.getSwapFreeSizeKb()); 13574 pw.print(" kB in swap ("); 13575 pw.print(memInfo.getSwapTotalSizeKb()); 13576 pw.println(" kB total swap)"); 13577 } else { 13578 pw.print("zram,"); pw.print(memInfo.getZramTotalSizeKb()); pw.print(","); 13579 pw.print(memInfo.getSwapTotalSizeKb()); pw.print(","); 13580 pw.println(memInfo.getSwapFreeSizeKb()); 13581 } 13582 } 13583 final int[] SINGLE_LONG_FORMAT = new int[] { 13584 Process.PROC_SPACE_TERM|Process.PROC_OUT_LONG 13585 }; 13586 long[] longOut = new long[1]; 13587 Process.readProcFile("/sys/kernel/mm/ksm/pages_shared", 13588 SINGLE_LONG_FORMAT, null, longOut, null); 13589 long shared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13590 longOut[0] = 0; 13591 Process.readProcFile("/sys/kernel/mm/ksm/pages_sharing", 13592 SINGLE_LONG_FORMAT, null, longOut, null); 13593 long sharing = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13594 longOut[0] = 0; 13595 Process.readProcFile("/sys/kernel/mm/ksm/pages_unshared", 13596 SINGLE_LONG_FORMAT, null, longOut, null); 13597 long unshared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13598 longOut[0] = 0; 13599 Process.readProcFile("/sys/kernel/mm/ksm/pages_volatile", 13600 SINGLE_LONG_FORMAT, null, longOut, null); 13601 long voltile = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13602 if (!isCompact) { 13603 if (sharing != 0 || shared != 0 || unshared != 0 || voltile != 0) { 13604 pw.print(" KSM: "); pw.print(sharing); 13605 pw.print(" kB saved from shared "); 13606 pw.print(shared); pw.println(" kB"); 13607 pw.print(" "); pw.print(unshared); pw.print(" kB unshared; "); 13608 pw.print(voltile); pw.println(" kB volatile"); 13609 } 13610 pw.print(" Tuning: "); 13611 pw.print(ActivityManager.staticGetMemoryClass()); 13612 pw.print(" (large "); 13613 pw.print(ActivityManager.staticGetLargeMemoryClass()); 13614 pw.print("), oom "); 13615 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 13616 pw.print(" kB"); 13617 pw.print(", restore limit "); 13618 pw.print(mProcessList.getCachedRestoreThresholdKb()); 13619 pw.print(" kB"); 13620 if (ActivityManager.isLowRamDeviceStatic()) { 13621 pw.print(" (low-ram)"); 13622 } 13623 if (ActivityManager.isHighEndGfx()) { 13624 pw.print(" (high-end-gfx)"); 13625 } 13626 pw.println(); 13627 } else { 13628 pw.print("ksm,"); pw.print(sharing); pw.print(","); 13629 pw.print(shared); pw.print(","); pw.print(unshared); pw.print(","); 13630 pw.println(voltile); 13631 pw.print("tuning,"); 13632 pw.print(ActivityManager.staticGetMemoryClass()); 13633 pw.print(','); 13634 pw.print(ActivityManager.staticGetLargeMemoryClass()); 13635 pw.print(','); 13636 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 13637 if (ActivityManager.isLowRamDeviceStatic()) { 13638 pw.print(",low-ram"); 13639 } 13640 if (ActivityManager.isHighEndGfx()) { 13641 pw.print(",high-end-gfx"); 13642 } 13643 pw.println(); 13644 } 13645 } 13646 } 13647 } 13648 13649 /** 13650 * Searches array of arguments for the specified string 13651 * @param args array of argument strings 13652 * @param value value to search for 13653 * @return true if the value is contained in the array 13654 */ 13655 private static boolean scanArgs(String[] args, String value) { 13656 if (args != null) { 13657 for (String arg : args) { 13658 if (value.equals(arg)) { 13659 return true; 13660 } 13661 } 13662 } 13663 return false; 13664 } 13665 13666 private final boolean removeDyingProviderLocked(ProcessRecord proc, 13667 ContentProviderRecord cpr, boolean always) { 13668 final boolean inLaunching = mLaunchingProviders.contains(cpr); 13669 13670 if (!inLaunching || always) { 13671 synchronized (cpr) { 13672 cpr.launchingApp = null; 13673 cpr.notifyAll(); 13674 } 13675 mProviderMap.removeProviderByClass(cpr.name, UserHandle.getUserId(cpr.uid)); 13676 String names[] = cpr.info.authority.split(";"); 13677 for (int j = 0; j < names.length; j++) { 13678 mProviderMap.removeProviderByName(names[j], UserHandle.getUserId(cpr.uid)); 13679 } 13680 } 13681 13682 for (int i=0; i<cpr.connections.size(); i++) { 13683 ContentProviderConnection conn = cpr.connections.get(i); 13684 if (conn.waiting) { 13685 // If this connection is waiting for the provider, then we don't 13686 // need to mess with its process unless we are always removing 13687 // or for some reason the provider is not currently launching. 13688 if (inLaunching && !always) { 13689 continue; 13690 } 13691 } 13692 ProcessRecord capp = conn.client; 13693 conn.dead = true; 13694 if (conn.stableCount > 0) { 13695 if (!capp.persistent && capp.thread != null 13696 && capp.pid != 0 13697 && capp.pid != MY_PID) { 13698 killUnneededProcessLocked(capp, "depends on provider " 13699 + cpr.name.flattenToShortString() 13700 + " in dying proc " + (proc != null ? proc.processName : "??")); 13701 } 13702 } else if (capp.thread != null && conn.provider.provider != null) { 13703 try { 13704 capp.thread.unstableProviderDied(conn.provider.provider.asBinder()); 13705 } catch (RemoteException e) { 13706 } 13707 // In the protocol here, we don't expect the client to correctly 13708 // clean up this connection, we'll just remove it. 13709 cpr.connections.remove(i); 13710 conn.client.conProviders.remove(conn); 13711 } 13712 } 13713 13714 if (inLaunching && always) { 13715 mLaunchingProviders.remove(cpr); 13716 } 13717 return inLaunching; 13718 } 13719 13720 /** 13721 * Main code for cleaning up a process when it has gone away. This is 13722 * called both as a result of the process dying, or directly when stopping 13723 * a process when running in single process mode. 13724 */ 13725 private final void cleanUpApplicationRecordLocked(ProcessRecord app, 13726 boolean restarting, boolean allowRestart, int index) { 13727 if (index >= 0) { 13728 removeLruProcessLocked(app); 13729 ProcessList.remove(app.pid); 13730 } 13731 13732 mProcessesToGc.remove(app); 13733 mPendingPssProcesses.remove(app); 13734 13735 // Dismiss any open dialogs. 13736 if (app.crashDialog != null && !app.forceCrashReport) { 13737 app.crashDialog.dismiss(); 13738 app.crashDialog = null; 13739 } 13740 if (app.anrDialog != null) { 13741 app.anrDialog.dismiss(); 13742 app.anrDialog = null; 13743 } 13744 if (app.waitDialog != null) { 13745 app.waitDialog.dismiss(); 13746 app.waitDialog = null; 13747 } 13748 13749 app.crashing = false; 13750 app.notResponding = false; 13751 13752 app.resetPackageList(mProcessStats); 13753 app.unlinkDeathRecipient(); 13754 app.makeInactive(mProcessStats); 13755 app.waitingToKill = null; 13756 app.forcingToForeground = null; 13757 updateProcessForegroundLocked(app, false, false); 13758 app.foregroundActivities = false; 13759 app.hasShownUi = false; 13760 app.treatLikeActivity = false; 13761 app.hasAboveClient = false; 13762 app.hasClientActivities = false; 13763 13764 mServices.killServicesLocked(app, allowRestart); 13765 13766 boolean restart = false; 13767 13768 // Remove published content providers. 13769 for (int i=app.pubProviders.size()-1; i>=0; i--) { 13770 ContentProviderRecord cpr = app.pubProviders.valueAt(i); 13771 final boolean always = app.bad || !allowRestart; 13772 if (removeDyingProviderLocked(app, cpr, always) || always) { 13773 // We left the provider in the launching list, need to 13774 // restart it. 13775 restart = true; 13776 } 13777 13778 cpr.provider = null; 13779 cpr.proc = null; 13780 } 13781 app.pubProviders.clear(); 13782 13783 // Take care of any launching providers waiting for this process. 13784 if (checkAppInLaunchingProvidersLocked(app, false)) { 13785 restart = true; 13786 } 13787 13788 // Unregister from connected content providers. 13789 if (!app.conProviders.isEmpty()) { 13790 for (int i=0; i<app.conProviders.size(); i++) { 13791 ContentProviderConnection conn = app.conProviders.get(i); 13792 conn.provider.connections.remove(conn); 13793 } 13794 app.conProviders.clear(); 13795 } 13796 13797 // At this point there may be remaining entries in mLaunchingProviders 13798 // where we were the only one waiting, so they are no longer of use. 13799 // Look for these and clean up if found. 13800 // XXX Commented out for now. Trying to figure out a way to reproduce 13801 // the actual situation to identify what is actually going on. 13802 if (false) { 13803 for (int i=0; i<mLaunchingProviders.size(); i++) { 13804 ContentProviderRecord cpr = (ContentProviderRecord) 13805 mLaunchingProviders.get(i); 13806 if (cpr.connections.size() <= 0 && !cpr.hasExternalProcessHandles()) { 13807 synchronized (cpr) { 13808 cpr.launchingApp = null; 13809 cpr.notifyAll(); 13810 } 13811 } 13812 } 13813 } 13814 13815 skipCurrentReceiverLocked(app); 13816 13817 // Unregister any receivers. 13818 for (int i=app.receivers.size()-1; i>=0; i--) { 13819 removeReceiverLocked(app.receivers.valueAt(i)); 13820 } 13821 app.receivers.clear(); 13822 13823 // If the app is undergoing backup, tell the backup manager about it 13824 if (mBackupTarget != null && app.pid == mBackupTarget.app.pid) { 13825 if (DEBUG_BACKUP || DEBUG_CLEANUP) Slog.d(TAG, "App " 13826 + mBackupTarget.appInfo + " died during backup"); 13827 try { 13828 IBackupManager bm = IBackupManager.Stub.asInterface( 13829 ServiceManager.getService(Context.BACKUP_SERVICE)); 13830 bm.agentDisconnected(app.info.packageName); 13831 } catch (RemoteException e) { 13832 // can't happen; backup manager is local 13833 } 13834 } 13835 13836 for (int i = mPendingProcessChanges.size()-1; i>=0; i--) { 13837 ProcessChangeItem item = mPendingProcessChanges.get(i); 13838 if (item.pid == app.pid) { 13839 mPendingProcessChanges.remove(i); 13840 mAvailProcessChanges.add(item); 13841 } 13842 } 13843 mHandler.obtainMessage(DISPATCH_PROCESS_DIED, app.pid, app.info.uid, null).sendToTarget(); 13844 13845 // If the caller is restarting this app, then leave it in its 13846 // current lists and let the caller take care of it. 13847 if (restarting) { 13848 return; 13849 } 13850 13851 if (!app.persistent || app.isolated) { 13852 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, 13853 "Removing non-persistent process during cleanup: " + app); 13854 mProcessNames.remove(app.processName, app.uid); 13855 mIsolatedProcesses.remove(app.uid); 13856 if (mHeavyWeightProcess == app) { 13857 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 13858 mHeavyWeightProcess.userId, 0)); 13859 mHeavyWeightProcess = null; 13860 } 13861 } else if (!app.removed) { 13862 // This app is persistent, so we need to keep its record around. 13863 // If it is not already on the pending app list, add it there 13864 // and start a new process for it. 13865 if (mPersistentStartingProcesses.indexOf(app) < 0) { 13866 mPersistentStartingProcesses.add(app); 13867 restart = true; 13868 } 13869 } 13870 if ((DEBUG_PROCESSES || DEBUG_CLEANUP) && mProcessesOnHold.contains(app)) Slog.v(TAG, 13871 "Clean-up removing on hold: " + app); 13872 mProcessesOnHold.remove(app); 13873 13874 if (app == mHomeProcess) { 13875 mHomeProcess = null; 13876 } 13877 if (app == mPreviousProcess) { 13878 mPreviousProcess = null; 13879 } 13880 13881 if (restart && !app.isolated) { 13882 // We have components that still need to be running in the 13883 // process, so re-launch it. 13884 mProcessNames.put(app.processName, app.uid, app); 13885 startProcessLocked(app, "restart", app.processName); 13886 } else if (app.pid > 0 && app.pid != MY_PID) { 13887 // Goodbye! 13888 boolean removed; 13889 synchronized (mPidsSelfLocked) { 13890 mPidsSelfLocked.remove(app.pid); 13891 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 13892 } 13893 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 13894 if (app.isolated) { 13895 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 13896 } 13897 app.setPid(0); 13898 } 13899 } 13900 13901 boolean checkAppInLaunchingProvidersLocked(ProcessRecord app, boolean alwaysBad) { 13902 // Look through the content providers we are waiting to have launched, 13903 // and if any run in this process then either schedule a restart of 13904 // the process or kill the client waiting for it if this process has 13905 // gone bad. 13906 int NL = mLaunchingProviders.size(); 13907 boolean restart = false; 13908 for (int i=0; i<NL; i++) { 13909 ContentProviderRecord cpr = mLaunchingProviders.get(i); 13910 if (cpr.launchingApp == app) { 13911 if (!alwaysBad && !app.bad) { 13912 restart = true; 13913 } else { 13914 removeDyingProviderLocked(app, cpr, true); 13915 // cpr should have been removed from mLaunchingProviders 13916 NL = mLaunchingProviders.size(); 13917 i--; 13918 } 13919 } 13920 } 13921 return restart; 13922 } 13923 13924 // ========================================================= 13925 // SERVICES 13926 // ========================================================= 13927 13928 @Override 13929 public List<ActivityManager.RunningServiceInfo> getServices(int maxNum, 13930 int flags) { 13931 enforceNotIsolatedCaller("getServices"); 13932 synchronized (this) { 13933 return mServices.getRunningServiceInfoLocked(maxNum, flags); 13934 } 13935 } 13936 13937 @Override 13938 public PendingIntent getRunningServiceControlPanel(ComponentName name) { 13939 enforceNotIsolatedCaller("getRunningServiceControlPanel"); 13940 synchronized (this) { 13941 return mServices.getRunningServiceControlPanelLocked(name); 13942 } 13943 } 13944 13945 @Override 13946 public ComponentName startService(IApplicationThread caller, Intent service, 13947 String resolvedType, int userId) { 13948 enforceNotIsolatedCaller("startService"); 13949 // Refuse possible leaked file descriptors 13950 if (service != null && service.hasFileDescriptors() == true) { 13951 throw new IllegalArgumentException("File descriptors passed in Intent"); 13952 } 13953 13954 if (DEBUG_SERVICE) 13955 Slog.v(TAG, "startService: " + service + " type=" + resolvedType); 13956 synchronized(this) { 13957 final int callingPid = Binder.getCallingPid(); 13958 final int callingUid = Binder.getCallingUid(); 13959 final long origId = Binder.clearCallingIdentity(); 13960 ComponentName res = mServices.startServiceLocked(caller, service, 13961 resolvedType, callingPid, callingUid, userId); 13962 Binder.restoreCallingIdentity(origId); 13963 return res; 13964 } 13965 } 13966 13967 ComponentName startServiceInPackage(int uid, 13968 Intent service, String resolvedType, int userId) { 13969 synchronized(this) { 13970 if (DEBUG_SERVICE) 13971 Slog.v(TAG, "startServiceInPackage: " + service + " type=" + resolvedType); 13972 final long origId = Binder.clearCallingIdentity(); 13973 ComponentName res = mServices.startServiceLocked(null, service, 13974 resolvedType, -1, uid, userId); 13975 Binder.restoreCallingIdentity(origId); 13976 return res; 13977 } 13978 } 13979 13980 @Override 13981 public int stopService(IApplicationThread caller, Intent service, 13982 String resolvedType, int userId) { 13983 enforceNotIsolatedCaller("stopService"); 13984 // Refuse possible leaked file descriptors 13985 if (service != null && service.hasFileDescriptors() == true) { 13986 throw new IllegalArgumentException("File descriptors passed in Intent"); 13987 } 13988 13989 synchronized(this) { 13990 return mServices.stopServiceLocked(caller, service, resolvedType, userId); 13991 } 13992 } 13993 13994 @Override 13995 public IBinder peekService(Intent service, String resolvedType) { 13996 enforceNotIsolatedCaller("peekService"); 13997 // Refuse possible leaked file descriptors 13998 if (service != null && service.hasFileDescriptors() == true) { 13999 throw new IllegalArgumentException("File descriptors passed in Intent"); 14000 } 14001 synchronized(this) { 14002 return mServices.peekServiceLocked(service, resolvedType); 14003 } 14004 } 14005 14006 @Override 14007 public boolean stopServiceToken(ComponentName className, IBinder token, 14008 int startId) { 14009 synchronized(this) { 14010 return mServices.stopServiceTokenLocked(className, token, startId); 14011 } 14012 } 14013 14014 @Override 14015 public void setServiceForeground(ComponentName className, IBinder token, 14016 int id, Notification notification, boolean removeNotification) { 14017 synchronized(this) { 14018 mServices.setServiceForegroundLocked(className, token, id, notification, 14019 removeNotification); 14020 } 14021 } 14022 14023 @Override 14024 public int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 14025 boolean requireFull, String name, String callerPackage) { 14026 return handleIncomingUser(callingPid, callingUid, userId, allowAll, 14027 requireFull ? ALLOW_FULL_ONLY : ALLOW_NON_FULL, name, callerPackage); 14028 } 14029 14030 int unsafeConvertIncomingUser(int userId) { 14031 return (userId == UserHandle.USER_CURRENT || userId == UserHandle.USER_CURRENT_OR_SELF) 14032 ? mCurrentUserId : userId; 14033 } 14034 14035 int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 14036 int allowMode, String name, String callerPackage) { 14037 final int callingUserId = UserHandle.getUserId(callingUid); 14038 if (callingUserId == userId) { 14039 return userId; 14040 } 14041 14042 // Note that we may be accessing mCurrentUserId outside of a lock... 14043 // shouldn't be a big deal, if this is being called outside 14044 // of a locked context there is intrinsically a race with 14045 // the value the caller will receive and someone else changing it. 14046 // We assume that USER_CURRENT_OR_SELF will use the current user; later 14047 // we will switch to the calling user if access to the current user fails. 14048 int targetUserId = unsafeConvertIncomingUser(userId); 14049 14050 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 14051 final boolean allow; 14052 if (checkComponentPermission(INTERACT_ACROSS_USERS_FULL, callingPid, 14053 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED) { 14054 // If the caller has this permission, they always pass go. And collect $200. 14055 allow = true; 14056 } else if (allowMode == ALLOW_FULL_ONLY) { 14057 // We require full access, sucks to be you. 14058 allow = false; 14059 } else if (checkComponentPermission(INTERACT_ACROSS_USERS, callingPid, 14060 callingUid, -1, true) != PackageManager.PERMISSION_GRANTED) { 14061 // If the caller does not have either permission, they are always doomed. 14062 allow = false; 14063 } else if (allowMode == ALLOW_NON_FULL) { 14064 // We are blanket allowing non-full access, you lucky caller! 14065 allow = true; 14066 } else if (allowMode == ALLOW_NON_FULL_IN_PROFILE) { 14067 // We may or may not allow this depending on whether the two users are 14068 // in the same profile. 14069 synchronized (mUserProfileGroupIdsSelfLocked) { 14070 int callingProfile = mUserProfileGroupIdsSelfLocked.get(callingUserId, 14071 UserInfo.NO_PROFILE_GROUP_ID); 14072 int targetProfile = mUserProfileGroupIdsSelfLocked.get(targetUserId, 14073 UserInfo.NO_PROFILE_GROUP_ID); 14074 allow = callingProfile != UserInfo.NO_PROFILE_GROUP_ID 14075 && callingProfile == targetProfile; 14076 } 14077 } else { 14078 throw new IllegalArgumentException("Unknown mode: " + allowMode); 14079 } 14080 if (!allow) { 14081 if (userId == UserHandle.USER_CURRENT_OR_SELF) { 14082 // In this case, they would like to just execute as their 14083 // owner user instead of failing. 14084 targetUserId = callingUserId; 14085 } else { 14086 StringBuilder builder = new StringBuilder(128); 14087 builder.append("Permission Denial: "); 14088 builder.append(name); 14089 if (callerPackage != null) { 14090 builder.append(" from "); 14091 builder.append(callerPackage); 14092 } 14093 builder.append(" asks to run as user "); 14094 builder.append(userId); 14095 builder.append(" but is calling from user "); 14096 builder.append(UserHandle.getUserId(callingUid)); 14097 builder.append("; this requires "); 14098 builder.append(INTERACT_ACROSS_USERS_FULL); 14099 if (allowMode != ALLOW_FULL_ONLY) { 14100 builder.append(" or "); 14101 builder.append(INTERACT_ACROSS_USERS); 14102 } 14103 String msg = builder.toString(); 14104 Slog.w(TAG, msg); 14105 throw new SecurityException(msg); 14106 } 14107 } 14108 } 14109 if (!allowAll && targetUserId < 0) { 14110 throw new IllegalArgumentException( 14111 "Call does not support special user #" + targetUserId); 14112 } 14113 return targetUserId; 14114 } 14115 14116 boolean isSingleton(String componentProcessName, ApplicationInfo aInfo, 14117 String className, int flags) { 14118 boolean result = false; 14119 // For apps that don't have pre-defined UIDs, check for permission 14120 if (UserHandle.getAppId(aInfo.uid) >= Process.FIRST_APPLICATION_UID) { 14121 if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 14122 if (ActivityManager.checkUidPermission( 14123 INTERACT_ACROSS_USERS, 14124 aInfo.uid) != PackageManager.PERMISSION_GRANTED) { 14125 ComponentName comp = new ComponentName(aInfo.packageName, className); 14126 String msg = "Permission Denial: Component " + comp.flattenToShortString() 14127 + " requests FLAG_SINGLE_USER, but app does not hold " 14128 + INTERACT_ACROSS_USERS; 14129 Slog.w(TAG, msg); 14130 throw new SecurityException(msg); 14131 } 14132 // Permission passed 14133 result = true; 14134 } 14135 } else if ("system".equals(componentProcessName)) { 14136 result = true; 14137 } else if (UserHandle.isSameApp(aInfo.uid, Process.PHONE_UID) 14138 && (flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 14139 // Phone app is allowed to export singleuser providers. 14140 result = true; 14141 } else { 14142 // App with pre-defined UID, check if it's a persistent app 14143 result = (aInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0; 14144 } 14145 if (DEBUG_MU) { 14146 Slog.v(TAG, "isSingleton(" + componentProcessName + ", " + aInfo 14147 + ", " + className + ", 0x" + Integer.toHexString(flags) + ") = " + result); 14148 } 14149 return result; 14150 } 14151 14152 /** 14153 * Checks to see if the caller is in the same app as the singleton 14154 * component, or the component is in a special app. It allows special apps 14155 * to export singleton components but prevents exporting singleton 14156 * components for regular apps. 14157 */ 14158 boolean isValidSingletonCall(int callingUid, int componentUid) { 14159 int componentAppId = UserHandle.getAppId(componentUid); 14160 return UserHandle.isSameApp(callingUid, componentUid) 14161 || componentAppId == Process.SYSTEM_UID 14162 || componentAppId == Process.PHONE_UID 14163 || ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, componentUid) 14164 == PackageManager.PERMISSION_GRANTED; 14165 } 14166 14167 public int bindService(IApplicationThread caller, IBinder token, 14168 Intent service, String resolvedType, 14169 IServiceConnection connection, int flags, int userId) { 14170 enforceNotIsolatedCaller("bindService"); 14171 // Refuse possible leaked file descriptors 14172 if (service != null && service.hasFileDescriptors() == true) { 14173 throw new IllegalArgumentException("File descriptors passed in Intent"); 14174 } 14175 14176 synchronized(this) { 14177 return mServices.bindServiceLocked(caller, token, service, resolvedType, 14178 connection, flags, userId); 14179 } 14180 } 14181 14182 public boolean unbindService(IServiceConnection connection) { 14183 synchronized (this) { 14184 return mServices.unbindServiceLocked(connection); 14185 } 14186 } 14187 14188 public void publishService(IBinder token, Intent intent, IBinder service) { 14189 // Refuse possible leaked file descriptors 14190 if (intent != null && intent.hasFileDescriptors() == true) { 14191 throw new IllegalArgumentException("File descriptors passed in Intent"); 14192 } 14193 14194 synchronized(this) { 14195 if (!(token instanceof ServiceRecord)) { 14196 throw new IllegalArgumentException("Invalid service token"); 14197 } 14198 mServices.publishServiceLocked((ServiceRecord)token, intent, service); 14199 } 14200 } 14201 14202 public void unbindFinished(IBinder token, Intent intent, boolean doRebind) { 14203 // Refuse possible leaked file descriptors 14204 if (intent != null && intent.hasFileDescriptors() == true) { 14205 throw new IllegalArgumentException("File descriptors passed in Intent"); 14206 } 14207 14208 synchronized(this) { 14209 mServices.unbindFinishedLocked((ServiceRecord)token, intent, doRebind); 14210 } 14211 } 14212 14213 public void serviceDoneExecuting(IBinder token, int type, int startId, int res) { 14214 synchronized(this) { 14215 if (!(token instanceof ServiceRecord)) { 14216 throw new IllegalArgumentException("Invalid service token"); 14217 } 14218 mServices.serviceDoneExecutingLocked((ServiceRecord)token, type, startId, res); 14219 } 14220 } 14221 14222 // ========================================================= 14223 // BACKUP AND RESTORE 14224 // ========================================================= 14225 14226 // Cause the target app to be launched if necessary and its backup agent 14227 // instantiated. The backup agent will invoke backupAgentCreated() on the 14228 // activity manager to announce its creation. 14229 public boolean bindBackupAgent(ApplicationInfo app, int backupMode) { 14230 if (DEBUG_BACKUP) Slog.v(TAG, "bindBackupAgent: app=" + app + " mode=" + backupMode); 14231 enforceCallingPermission("android.permission.CONFIRM_FULL_BACKUP", "bindBackupAgent"); 14232 14233 synchronized(this) { 14234 // !!! TODO: currently no check here that we're already bound 14235 BatteryStatsImpl.Uid.Pkg.Serv ss = null; 14236 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 14237 synchronized (stats) { 14238 ss = stats.getServiceStatsLocked(app.uid, app.packageName, app.name); 14239 } 14240 14241 // Backup agent is now in use, its package can't be stopped. 14242 try { 14243 AppGlobals.getPackageManager().setPackageStoppedState( 14244 app.packageName, false, UserHandle.getUserId(app.uid)); 14245 } catch (RemoteException e) { 14246 } catch (IllegalArgumentException e) { 14247 Slog.w(TAG, "Failed trying to unstop package " 14248 + app.packageName + ": " + e); 14249 } 14250 14251 BackupRecord r = new BackupRecord(ss, app, backupMode); 14252 ComponentName hostingName = (backupMode == IApplicationThread.BACKUP_MODE_INCREMENTAL) 14253 ? new ComponentName(app.packageName, app.backupAgentName) 14254 : new ComponentName("android", "FullBackupAgent"); 14255 // startProcessLocked() returns existing proc's record if it's already running 14256 ProcessRecord proc = startProcessLocked(app.processName, app, 14257 false, 0, "backup", hostingName, false, false, false); 14258 if (proc == null) { 14259 Slog.e(TAG, "Unable to start backup agent process " + r); 14260 return false; 14261 } 14262 14263 r.app = proc; 14264 mBackupTarget = r; 14265 mBackupAppName = app.packageName; 14266 14267 // Try not to kill the process during backup 14268 updateOomAdjLocked(proc); 14269 14270 // If the process is already attached, schedule the creation of the backup agent now. 14271 // If it is not yet live, this will be done when it attaches to the framework. 14272 if (proc.thread != null) { 14273 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc already running: " + proc); 14274 try { 14275 proc.thread.scheduleCreateBackupAgent(app, 14276 compatibilityInfoForPackageLocked(app), backupMode); 14277 } catch (RemoteException e) { 14278 // Will time out on the backup manager side 14279 } 14280 } else { 14281 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc not running, waiting for attach"); 14282 } 14283 // Invariants: at this point, the target app process exists and the application 14284 // is either already running or in the process of coming up. mBackupTarget and 14285 // mBackupAppName describe the app, so that when it binds back to the AM we 14286 // know that it's scheduled for a backup-agent operation. 14287 } 14288 14289 return true; 14290 } 14291 14292 @Override 14293 public void clearPendingBackup() { 14294 if (DEBUG_BACKUP) Slog.v(TAG, "clearPendingBackup"); 14295 enforceCallingPermission("android.permission.BACKUP", "clearPendingBackup"); 14296 14297 synchronized (this) { 14298 mBackupTarget = null; 14299 mBackupAppName = null; 14300 } 14301 } 14302 14303 // A backup agent has just come up 14304 public void backupAgentCreated(String agentPackageName, IBinder agent) { 14305 if (DEBUG_BACKUP) Slog.v(TAG, "backupAgentCreated: " + agentPackageName 14306 + " = " + agent); 14307 14308 synchronized(this) { 14309 if (!agentPackageName.equals(mBackupAppName)) { 14310 Slog.e(TAG, "Backup agent created for " + agentPackageName + " but not requested!"); 14311 return; 14312 } 14313 } 14314 14315 long oldIdent = Binder.clearCallingIdentity(); 14316 try { 14317 IBackupManager bm = IBackupManager.Stub.asInterface( 14318 ServiceManager.getService(Context.BACKUP_SERVICE)); 14319 bm.agentConnected(agentPackageName, agent); 14320 } catch (RemoteException e) { 14321 // can't happen; the backup manager service is local 14322 } catch (Exception e) { 14323 Slog.w(TAG, "Exception trying to deliver BackupAgent binding: "); 14324 e.printStackTrace(); 14325 } finally { 14326 Binder.restoreCallingIdentity(oldIdent); 14327 } 14328 } 14329 14330 // done with this agent 14331 public void unbindBackupAgent(ApplicationInfo appInfo) { 14332 if (DEBUG_BACKUP) Slog.v(TAG, "unbindBackupAgent: " + appInfo); 14333 if (appInfo == null) { 14334 Slog.w(TAG, "unbind backup agent for null app"); 14335 return; 14336 } 14337 14338 synchronized(this) { 14339 try { 14340 if (mBackupAppName == null) { 14341 Slog.w(TAG, "Unbinding backup agent with no active backup"); 14342 return; 14343 } 14344 14345 if (!mBackupAppName.equals(appInfo.packageName)) { 14346 Slog.e(TAG, "Unbind of " + appInfo + " but is not the current backup target"); 14347 return; 14348 } 14349 14350 // Not backing this app up any more; reset its OOM adjustment 14351 final ProcessRecord proc = mBackupTarget.app; 14352 updateOomAdjLocked(proc); 14353 14354 // If the app crashed during backup, 'thread' will be null here 14355 if (proc.thread != null) { 14356 try { 14357 proc.thread.scheduleDestroyBackupAgent(appInfo, 14358 compatibilityInfoForPackageLocked(appInfo)); 14359 } catch (Exception e) { 14360 Slog.e(TAG, "Exception when unbinding backup agent:"); 14361 e.printStackTrace(); 14362 } 14363 } 14364 } finally { 14365 mBackupTarget = null; 14366 mBackupAppName = null; 14367 } 14368 } 14369 } 14370 // ========================================================= 14371 // BROADCASTS 14372 // ========================================================= 14373 14374 private final List getStickiesLocked(String action, IntentFilter filter, 14375 List cur, int userId) { 14376 final ContentResolver resolver = mContext.getContentResolver(); 14377 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 14378 if (stickies == null) { 14379 return cur; 14380 } 14381 final ArrayList<Intent> list = stickies.get(action); 14382 if (list == null) { 14383 return cur; 14384 } 14385 int N = list.size(); 14386 for (int i=0; i<N; i++) { 14387 Intent intent = list.get(i); 14388 if (filter.match(resolver, intent, true, TAG) >= 0) { 14389 if (cur == null) { 14390 cur = new ArrayList<Intent>(); 14391 } 14392 cur.add(intent); 14393 } 14394 } 14395 return cur; 14396 } 14397 14398 boolean isPendingBroadcastProcessLocked(int pid) { 14399 return mFgBroadcastQueue.isPendingBroadcastProcessLocked(pid) 14400 || mBgBroadcastQueue.isPendingBroadcastProcessLocked(pid); 14401 } 14402 14403 void skipPendingBroadcastLocked(int pid) { 14404 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 14405 for (BroadcastQueue queue : mBroadcastQueues) { 14406 queue.skipPendingBroadcastLocked(pid); 14407 } 14408 } 14409 14410 // The app just attached; send any pending broadcasts that it should receive 14411 boolean sendPendingBroadcastsLocked(ProcessRecord app) { 14412 boolean didSomething = false; 14413 for (BroadcastQueue queue : mBroadcastQueues) { 14414 didSomething |= queue.sendPendingBroadcastsLocked(app); 14415 } 14416 return didSomething; 14417 } 14418 14419 public Intent registerReceiver(IApplicationThread caller, String callerPackage, 14420 IIntentReceiver receiver, IntentFilter filter, String permission, int userId) { 14421 enforceNotIsolatedCaller("registerReceiver"); 14422 int callingUid; 14423 int callingPid; 14424 synchronized(this) { 14425 ProcessRecord callerApp = null; 14426 if (caller != null) { 14427 callerApp = getRecordForAppLocked(caller); 14428 if (callerApp == null) { 14429 throw new SecurityException( 14430 "Unable to find app for caller " + caller 14431 + " (pid=" + Binder.getCallingPid() 14432 + ") when registering receiver " + receiver); 14433 } 14434 if (callerApp.info.uid != Process.SYSTEM_UID && 14435 !callerApp.pkgList.containsKey(callerPackage) && 14436 !"android".equals(callerPackage)) { 14437 throw new SecurityException("Given caller package " + callerPackage 14438 + " is not running in process " + callerApp); 14439 } 14440 callingUid = callerApp.info.uid; 14441 callingPid = callerApp.pid; 14442 } else { 14443 callerPackage = null; 14444 callingUid = Binder.getCallingUid(); 14445 callingPid = Binder.getCallingPid(); 14446 } 14447 14448 userId = this.handleIncomingUser(callingPid, callingUid, userId, 14449 true, ALLOW_FULL_ONLY, "registerReceiver", callerPackage); 14450 14451 List allSticky = null; 14452 14453 // Look for any matching sticky broadcasts... 14454 Iterator actions = filter.actionsIterator(); 14455 if (actions != null) { 14456 while (actions.hasNext()) { 14457 String action = (String)actions.next(); 14458 allSticky = getStickiesLocked(action, filter, allSticky, 14459 UserHandle.USER_ALL); 14460 allSticky = getStickiesLocked(action, filter, allSticky, 14461 UserHandle.getUserId(callingUid)); 14462 } 14463 } else { 14464 allSticky = getStickiesLocked(null, filter, allSticky, 14465 UserHandle.USER_ALL); 14466 allSticky = getStickiesLocked(null, filter, allSticky, 14467 UserHandle.getUserId(callingUid)); 14468 } 14469 14470 // The first sticky in the list is returned directly back to 14471 // the client. 14472 Intent sticky = allSticky != null ? (Intent)allSticky.get(0) : null; 14473 14474 if (DEBUG_BROADCAST) Slog.v(TAG, "Register receiver " + filter 14475 + ": " + sticky); 14476 14477 if (receiver == null) { 14478 return sticky; 14479 } 14480 14481 ReceiverList rl 14482 = (ReceiverList)mRegisteredReceivers.get(receiver.asBinder()); 14483 if (rl == null) { 14484 rl = new ReceiverList(this, callerApp, callingPid, callingUid, 14485 userId, receiver); 14486 if (rl.app != null) { 14487 rl.app.receivers.add(rl); 14488 } else { 14489 try { 14490 receiver.asBinder().linkToDeath(rl, 0); 14491 } catch (RemoteException e) { 14492 return sticky; 14493 } 14494 rl.linkedToDeath = true; 14495 } 14496 mRegisteredReceivers.put(receiver.asBinder(), rl); 14497 } else if (rl.uid != callingUid) { 14498 throw new IllegalArgumentException( 14499 "Receiver requested to register for uid " + callingUid 14500 + " was previously registered for uid " + rl.uid); 14501 } else if (rl.pid != callingPid) { 14502 throw new IllegalArgumentException( 14503 "Receiver requested to register for pid " + callingPid 14504 + " was previously registered for pid " + rl.pid); 14505 } else if (rl.userId != userId) { 14506 throw new IllegalArgumentException( 14507 "Receiver requested to register for user " + userId 14508 + " was previously registered for user " + rl.userId); 14509 } 14510 BroadcastFilter bf = new BroadcastFilter(filter, rl, callerPackage, 14511 permission, callingUid, userId); 14512 rl.add(bf); 14513 if (!bf.debugCheck()) { 14514 Slog.w(TAG, "==> For Dynamic broadast"); 14515 } 14516 mReceiverResolver.addFilter(bf); 14517 14518 // Enqueue broadcasts for all existing stickies that match 14519 // this filter. 14520 if (allSticky != null) { 14521 ArrayList receivers = new ArrayList(); 14522 receivers.add(bf); 14523 14524 int N = allSticky.size(); 14525 for (int i=0; i<N; i++) { 14526 Intent intent = (Intent)allSticky.get(i); 14527 BroadcastQueue queue = broadcastQueueForIntent(intent); 14528 BroadcastRecord r = new BroadcastRecord(queue, intent, null, 14529 null, -1, -1, null, null, AppOpsManager.OP_NONE, receivers, null, 0, 14530 null, null, false, true, true, -1); 14531 queue.enqueueParallelBroadcastLocked(r); 14532 queue.scheduleBroadcastsLocked(); 14533 } 14534 } 14535 14536 return sticky; 14537 } 14538 } 14539 14540 public void unregisterReceiver(IIntentReceiver receiver) { 14541 if (DEBUG_BROADCAST) Slog.v(TAG, "Unregister receiver: " + receiver); 14542 14543 final long origId = Binder.clearCallingIdentity(); 14544 try { 14545 boolean doTrim = false; 14546 14547 synchronized(this) { 14548 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder()); 14549 if (rl != null) { 14550 if (rl.curBroadcast != null) { 14551 BroadcastRecord r = rl.curBroadcast; 14552 final boolean doNext = finishReceiverLocked( 14553 receiver.asBinder(), r.resultCode, r.resultData, 14554 r.resultExtras, r.resultAbort); 14555 if (doNext) { 14556 doTrim = true; 14557 r.queue.processNextBroadcast(false); 14558 } 14559 } 14560 14561 if (rl.app != null) { 14562 rl.app.receivers.remove(rl); 14563 } 14564 removeReceiverLocked(rl); 14565 if (rl.linkedToDeath) { 14566 rl.linkedToDeath = false; 14567 rl.receiver.asBinder().unlinkToDeath(rl, 0); 14568 } 14569 } 14570 } 14571 14572 // If we actually concluded any broadcasts, we might now be able 14573 // to trim the recipients' apps from our working set 14574 if (doTrim) { 14575 trimApplications(); 14576 return; 14577 } 14578 14579 } finally { 14580 Binder.restoreCallingIdentity(origId); 14581 } 14582 } 14583 14584 void removeReceiverLocked(ReceiverList rl) { 14585 mRegisteredReceivers.remove(rl.receiver.asBinder()); 14586 int N = rl.size(); 14587 for (int i=0; i<N; i++) { 14588 mReceiverResolver.removeFilter(rl.get(i)); 14589 } 14590 } 14591 14592 private final void sendPackageBroadcastLocked(int cmd, String[] packages, int userId) { 14593 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 14594 ProcessRecord r = mLruProcesses.get(i); 14595 if (r.thread != null && (userId == UserHandle.USER_ALL || r.userId == userId)) { 14596 try { 14597 r.thread.dispatchPackageBroadcast(cmd, packages); 14598 } catch (RemoteException ex) { 14599 } 14600 } 14601 } 14602 } 14603 14604 private List<ResolveInfo> collectReceiverComponents(Intent intent, String resolvedType, 14605 int[] users) { 14606 List<ResolveInfo> receivers = null; 14607 try { 14608 HashSet<ComponentName> singleUserReceivers = null; 14609 boolean scannedFirstReceivers = false; 14610 for (int user : users) { 14611 List<ResolveInfo> newReceivers = AppGlobals.getPackageManager() 14612 .queryIntentReceivers(intent, resolvedType, STOCK_PM_FLAGS, user); 14613 if (user != 0 && newReceivers != null) { 14614 // If this is not the primary user, we need to check for 14615 // any receivers that should be filtered out. 14616 for (int i=0; i<newReceivers.size(); i++) { 14617 ResolveInfo ri = newReceivers.get(i); 14618 if ((ri.activityInfo.flags&ActivityInfo.FLAG_PRIMARY_USER_ONLY) != 0) { 14619 newReceivers.remove(i); 14620 i--; 14621 } 14622 } 14623 } 14624 if (newReceivers != null && newReceivers.size() == 0) { 14625 newReceivers = null; 14626 } 14627 if (receivers == null) { 14628 receivers = newReceivers; 14629 } else if (newReceivers != null) { 14630 // We need to concatenate the additional receivers 14631 // found with what we have do far. This would be easy, 14632 // but we also need to de-dup any receivers that are 14633 // singleUser. 14634 if (!scannedFirstReceivers) { 14635 // Collect any single user receivers we had already retrieved. 14636 scannedFirstReceivers = true; 14637 for (int i=0; i<receivers.size(); i++) { 14638 ResolveInfo ri = receivers.get(i); 14639 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 14640 ComponentName cn = new ComponentName( 14641 ri.activityInfo.packageName, ri.activityInfo.name); 14642 if (singleUserReceivers == null) { 14643 singleUserReceivers = new HashSet<ComponentName>(); 14644 } 14645 singleUserReceivers.add(cn); 14646 } 14647 } 14648 } 14649 // Add the new results to the existing results, tracking 14650 // and de-dupping single user receivers. 14651 for (int i=0; i<newReceivers.size(); i++) { 14652 ResolveInfo ri = newReceivers.get(i); 14653 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 14654 ComponentName cn = new ComponentName( 14655 ri.activityInfo.packageName, ri.activityInfo.name); 14656 if (singleUserReceivers == null) { 14657 singleUserReceivers = new HashSet<ComponentName>(); 14658 } 14659 if (!singleUserReceivers.contains(cn)) { 14660 singleUserReceivers.add(cn); 14661 receivers.add(ri); 14662 } 14663 } else { 14664 receivers.add(ri); 14665 } 14666 } 14667 } 14668 } 14669 } catch (RemoteException ex) { 14670 // pm is in same process, this will never happen. 14671 } 14672 return receivers; 14673 } 14674 14675 private final int broadcastIntentLocked(ProcessRecord callerApp, 14676 String callerPackage, Intent intent, String resolvedType, 14677 IIntentReceiver resultTo, int resultCode, String resultData, 14678 Bundle map, String requiredPermission, int appOp, 14679 boolean ordered, boolean sticky, int callingPid, int callingUid, 14680 int userId) { 14681 intent = new Intent(intent); 14682 14683 // By default broadcasts do not go to stopped apps. 14684 intent.addFlags(Intent.FLAG_EXCLUDE_STOPPED_PACKAGES); 14685 14686 if (DEBUG_BROADCAST_LIGHT) Slog.v( 14687 TAG, (sticky ? "Broadcast sticky: ": "Broadcast: ") + intent 14688 + " ordered=" + ordered + " userid=" + userId); 14689 if ((resultTo != null) && !ordered) { 14690 Slog.w(TAG, "Broadcast " + intent + " not ordered but result callback requested!"); 14691 } 14692 14693 userId = handleIncomingUser(callingPid, callingUid, userId, 14694 true, ALLOW_NON_FULL, "broadcast", callerPackage); 14695 14696 // Make sure that the user who is receiving this broadcast is started. 14697 // If not, we will just skip it. 14698 14699 14700 if (userId != UserHandle.USER_ALL && mStartedUsers.get(userId) == null) { 14701 if (callingUid != Process.SYSTEM_UID || (intent.getFlags() 14702 & Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) { 14703 Slog.w(TAG, "Skipping broadcast of " + intent 14704 + ": user " + userId + " is stopped"); 14705 return ActivityManager.BROADCAST_SUCCESS; 14706 } 14707 } 14708 14709 /* 14710 * Prevent non-system code (defined here to be non-persistent 14711 * processes) from sending protected broadcasts. 14712 */ 14713 int callingAppId = UserHandle.getAppId(callingUid); 14714 if (callingAppId == Process.SYSTEM_UID || callingAppId == Process.PHONE_UID 14715 || callingAppId == Process.SHELL_UID || callingAppId == Process.BLUETOOTH_UID 14716 || callingAppId == Process.NFC_UID || callingUid == 0) { 14717 // Always okay. 14718 } else if (callerApp == null || !callerApp.persistent) { 14719 try { 14720 if (AppGlobals.getPackageManager().isProtectedBroadcast( 14721 intent.getAction())) { 14722 String msg = "Permission Denial: not allowed to send broadcast " 14723 + intent.getAction() + " from pid=" 14724 + callingPid + ", uid=" + callingUid; 14725 Slog.w(TAG, msg); 14726 throw new SecurityException(msg); 14727 } else if (AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(intent.getAction())) { 14728 // Special case for compatibility: we don't want apps to send this, 14729 // but historically it has not been protected and apps may be using it 14730 // to poke their own app widget. So, instead of making it protected, 14731 // just limit it to the caller. 14732 if (callerApp == null) { 14733 String msg = "Permission Denial: not allowed to send broadcast " 14734 + intent.getAction() + " from unknown caller."; 14735 Slog.w(TAG, msg); 14736 throw new SecurityException(msg); 14737 } else if (intent.getComponent() != null) { 14738 // They are good enough to send to an explicit component... verify 14739 // it is being sent to the calling app. 14740 if (!intent.getComponent().getPackageName().equals( 14741 callerApp.info.packageName)) { 14742 String msg = "Permission Denial: not allowed to send broadcast " 14743 + intent.getAction() + " to " 14744 + intent.getComponent().getPackageName() + " from " 14745 + callerApp.info.packageName; 14746 Slog.w(TAG, msg); 14747 throw new SecurityException(msg); 14748 } 14749 } else { 14750 // Limit broadcast to their own package. 14751 intent.setPackage(callerApp.info.packageName); 14752 } 14753 } 14754 } catch (RemoteException e) { 14755 Slog.w(TAG, "Remote exception", e); 14756 return ActivityManager.BROADCAST_SUCCESS; 14757 } 14758 } 14759 14760 // Handle special intents: if this broadcast is from the package 14761 // manager about a package being removed, we need to remove all of 14762 // its activities from the history stack. 14763 final boolean uidRemoved = Intent.ACTION_UID_REMOVED.equals( 14764 intent.getAction()); 14765 if (Intent.ACTION_PACKAGE_REMOVED.equals(intent.getAction()) 14766 || Intent.ACTION_PACKAGE_CHANGED.equals(intent.getAction()) 14767 || Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction()) 14768 || uidRemoved) { 14769 if (checkComponentPermission( 14770 android.Manifest.permission.BROADCAST_PACKAGE_REMOVED, 14771 callingPid, callingUid, -1, true) 14772 == PackageManager.PERMISSION_GRANTED) { 14773 if (uidRemoved) { 14774 final Bundle intentExtras = intent.getExtras(); 14775 final int uid = intentExtras != null 14776 ? intentExtras.getInt(Intent.EXTRA_UID) : -1; 14777 if (uid >= 0) { 14778 BatteryStatsImpl bs = mBatteryStatsService.getActiveStatistics(); 14779 synchronized (bs) { 14780 bs.removeUidStatsLocked(uid); 14781 } 14782 mAppOpsService.uidRemoved(uid); 14783 } 14784 } else { 14785 // If resources are unavailable just force stop all 14786 // those packages and flush the attribute cache as well. 14787 if (Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction())) { 14788 String list[] = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 14789 if (list != null && (list.length > 0)) { 14790 for (String pkg : list) { 14791 forceStopPackageLocked(pkg, -1, false, true, true, false, false, userId, 14792 "storage unmount"); 14793 } 14794 sendPackageBroadcastLocked( 14795 IApplicationThread.EXTERNAL_STORAGE_UNAVAILABLE, list, userId); 14796 } 14797 } else { 14798 Uri data = intent.getData(); 14799 String ssp; 14800 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 14801 boolean removed = Intent.ACTION_PACKAGE_REMOVED.equals( 14802 intent.getAction()); 14803 boolean fullUninstall = removed && 14804 !intent.getBooleanExtra(Intent.EXTRA_REPLACING, false); 14805 if (!intent.getBooleanExtra(Intent.EXTRA_DONT_KILL_APP, false)) { 14806 forceStopPackageLocked(ssp, UserHandle.getAppId( 14807 intent.getIntExtra(Intent.EXTRA_UID, -1)), false, true, true, 14808 false, fullUninstall, userId, 14809 removed ? "pkg removed" : "pkg changed"); 14810 } 14811 if (removed) { 14812 sendPackageBroadcastLocked(IApplicationThread.PACKAGE_REMOVED, 14813 new String[] {ssp}, userId); 14814 if (!intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)) { 14815 mAppOpsService.packageRemoved( 14816 intent.getIntExtra(Intent.EXTRA_UID, -1), ssp); 14817 14818 // Remove all permissions granted from/to this package 14819 removeUriPermissionsForPackageLocked(ssp, userId, true); 14820 } 14821 } 14822 } 14823 } 14824 } 14825 } else { 14826 String msg = "Permission Denial: " + intent.getAction() 14827 + " broadcast from " + callerPackage + " (pid=" + callingPid 14828 + ", uid=" + callingUid + ")" 14829 + " requires " 14830 + android.Manifest.permission.BROADCAST_PACKAGE_REMOVED; 14831 Slog.w(TAG, msg); 14832 throw new SecurityException(msg); 14833 } 14834 14835 // Special case for adding a package: by default turn on compatibility 14836 // mode. 14837 } else if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction())) { 14838 Uri data = intent.getData(); 14839 String ssp; 14840 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 14841 mCompatModePackages.handlePackageAddedLocked(ssp, 14842 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)); 14843 } 14844 } 14845 14846 /* 14847 * If this is the time zone changed action, queue up a message that will reset the timezone 14848 * of all currently running processes. This message will get queued up before the broadcast 14849 * happens. 14850 */ 14851 if (Intent.ACTION_TIMEZONE_CHANGED.equals(intent.getAction())) { 14852 mHandler.sendEmptyMessage(UPDATE_TIME_ZONE); 14853 } 14854 14855 /* 14856 * If the user set the time, let all running processes know. 14857 */ 14858 if (Intent.ACTION_TIME_CHANGED.equals(intent.getAction())) { 14859 final int is24Hour = intent.getBooleanExtra( 14860 Intent.EXTRA_TIME_PREF_24_HOUR_FORMAT, false) ? 1 : 0; 14861 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_TIME, is24Hour, 0)); 14862 } 14863 14864 if (Intent.ACTION_CLEAR_DNS_CACHE.equals(intent.getAction())) { 14865 mHandler.sendEmptyMessage(CLEAR_DNS_CACHE_MSG); 14866 } 14867 14868 if (Proxy.PROXY_CHANGE_ACTION.equals(intent.getAction())) { 14869 ProxyInfo proxy = intent.getParcelableExtra(Proxy.EXTRA_PROXY_INFO); 14870 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_HTTP_PROXY_MSG, proxy)); 14871 } 14872 14873 // Add to the sticky list if requested. 14874 if (sticky) { 14875 if (checkPermission(android.Manifest.permission.BROADCAST_STICKY, 14876 callingPid, callingUid) 14877 != PackageManager.PERMISSION_GRANTED) { 14878 String msg = "Permission Denial: broadcastIntent() requesting a sticky broadcast from pid=" 14879 + callingPid + ", uid=" + callingUid 14880 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 14881 Slog.w(TAG, msg); 14882 throw new SecurityException(msg); 14883 } 14884 if (requiredPermission != null) { 14885 Slog.w(TAG, "Can't broadcast sticky intent " + intent 14886 + " and enforce permission " + requiredPermission); 14887 return ActivityManager.BROADCAST_STICKY_CANT_HAVE_PERMISSION; 14888 } 14889 if (intent.getComponent() != null) { 14890 throw new SecurityException( 14891 "Sticky broadcasts can't target a specific component"); 14892 } 14893 // We use userId directly here, since the "all" target is maintained 14894 // as a separate set of sticky broadcasts. 14895 if (userId != UserHandle.USER_ALL) { 14896 // But first, if this is not a broadcast to all users, then 14897 // make sure it doesn't conflict with an existing broadcast to 14898 // all users. 14899 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get( 14900 UserHandle.USER_ALL); 14901 if (stickies != null) { 14902 ArrayList<Intent> list = stickies.get(intent.getAction()); 14903 if (list != null) { 14904 int N = list.size(); 14905 int i; 14906 for (i=0; i<N; i++) { 14907 if (intent.filterEquals(list.get(i))) { 14908 throw new IllegalArgumentException( 14909 "Sticky broadcast " + intent + " for user " 14910 + userId + " conflicts with existing global broadcast"); 14911 } 14912 } 14913 } 14914 } 14915 } 14916 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 14917 if (stickies == null) { 14918 stickies = new ArrayMap<String, ArrayList<Intent>>(); 14919 mStickyBroadcasts.put(userId, stickies); 14920 } 14921 ArrayList<Intent> list = stickies.get(intent.getAction()); 14922 if (list == null) { 14923 list = new ArrayList<Intent>(); 14924 stickies.put(intent.getAction(), list); 14925 } 14926 int N = list.size(); 14927 int i; 14928 for (i=0; i<N; i++) { 14929 if (intent.filterEquals(list.get(i))) { 14930 // This sticky already exists, replace it. 14931 list.set(i, new Intent(intent)); 14932 break; 14933 } 14934 } 14935 if (i >= N) { 14936 list.add(new Intent(intent)); 14937 } 14938 } 14939 14940 int[] users; 14941 if (userId == UserHandle.USER_ALL) { 14942 // Caller wants broadcast to go to all started users. 14943 users = mStartedUserArray; 14944 } else { 14945 // Caller wants broadcast to go to one specific user. 14946 users = new int[] {userId}; 14947 } 14948 14949 // Figure out who all will receive this broadcast. 14950 List receivers = null; 14951 List<BroadcastFilter> registeredReceivers = null; 14952 // Need to resolve the intent to interested receivers... 14953 if ((intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) 14954 == 0) { 14955 receivers = collectReceiverComponents(intent, resolvedType, users); 14956 } 14957 if (intent.getComponent() == null) { 14958 registeredReceivers = mReceiverResolver.queryIntent(intent, 14959 resolvedType, false, userId); 14960 } 14961 14962 final boolean replacePending = 14963 (intent.getFlags()&Intent.FLAG_RECEIVER_REPLACE_PENDING) != 0; 14964 14965 if (DEBUG_BROADCAST) Slog.v(TAG, "Enqueing broadcast: " + intent.getAction() 14966 + " replacePending=" + replacePending); 14967 14968 int NR = registeredReceivers != null ? registeredReceivers.size() : 0; 14969 if (!ordered && NR > 0) { 14970 // If we are not serializing this broadcast, then send the 14971 // registered receivers separately so they don't wait for the 14972 // components to be launched. 14973 final BroadcastQueue queue = broadcastQueueForIntent(intent); 14974 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 14975 callerPackage, callingPid, callingUid, resolvedType, requiredPermission, 14976 appOp, registeredReceivers, resultTo, resultCode, resultData, map, 14977 ordered, sticky, false, userId); 14978 if (DEBUG_BROADCAST) Slog.v( 14979 TAG, "Enqueueing parallel broadcast " + r); 14980 final boolean replaced = replacePending && queue.replaceParallelBroadcastLocked(r); 14981 if (!replaced) { 14982 queue.enqueueParallelBroadcastLocked(r); 14983 queue.scheduleBroadcastsLocked(); 14984 } 14985 registeredReceivers = null; 14986 NR = 0; 14987 } 14988 14989 // Merge into one list. 14990 int ir = 0; 14991 if (receivers != null) { 14992 // A special case for PACKAGE_ADDED: do not allow the package 14993 // being added to see this broadcast. This prevents them from 14994 // using this as a back door to get run as soon as they are 14995 // installed. Maybe in the future we want to have a special install 14996 // broadcast or such for apps, but we'd like to deliberately make 14997 // this decision. 14998 String skipPackages[] = null; 14999 if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction()) 15000 || Intent.ACTION_PACKAGE_RESTARTED.equals(intent.getAction()) 15001 || Intent.ACTION_PACKAGE_DATA_CLEARED.equals(intent.getAction())) { 15002 Uri data = intent.getData(); 15003 if (data != null) { 15004 String pkgName = data.getSchemeSpecificPart(); 15005 if (pkgName != null) { 15006 skipPackages = new String[] { pkgName }; 15007 } 15008 } 15009 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction())) { 15010 skipPackages = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 15011 } 15012 if (skipPackages != null && (skipPackages.length > 0)) { 15013 for (String skipPackage : skipPackages) { 15014 if (skipPackage != null) { 15015 int NT = receivers.size(); 15016 for (int it=0; it<NT; it++) { 15017 ResolveInfo curt = (ResolveInfo)receivers.get(it); 15018 if (curt.activityInfo.packageName.equals(skipPackage)) { 15019 receivers.remove(it); 15020 it--; 15021 NT--; 15022 } 15023 } 15024 } 15025 } 15026 } 15027 15028 int NT = receivers != null ? receivers.size() : 0; 15029 int it = 0; 15030 ResolveInfo curt = null; 15031 BroadcastFilter curr = null; 15032 while (it < NT && ir < NR) { 15033 if (curt == null) { 15034 curt = (ResolveInfo)receivers.get(it); 15035 } 15036 if (curr == null) { 15037 curr = registeredReceivers.get(ir); 15038 } 15039 if (curr.getPriority() >= curt.priority) { 15040 // Insert this broadcast record into the final list. 15041 receivers.add(it, curr); 15042 ir++; 15043 curr = null; 15044 it++; 15045 NT++; 15046 } else { 15047 // Skip to the next ResolveInfo in the final list. 15048 it++; 15049 curt = null; 15050 } 15051 } 15052 } 15053 while (ir < NR) { 15054 if (receivers == null) { 15055 receivers = new ArrayList(); 15056 } 15057 receivers.add(registeredReceivers.get(ir)); 15058 ir++; 15059 } 15060 15061 if ((receivers != null && receivers.size() > 0) 15062 || resultTo != null) { 15063 BroadcastQueue queue = broadcastQueueForIntent(intent); 15064 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 15065 callerPackage, callingPid, callingUid, resolvedType, 15066 requiredPermission, appOp, receivers, resultTo, resultCode, 15067 resultData, map, ordered, sticky, false, userId); 15068 if (DEBUG_BROADCAST) Slog.v( 15069 TAG, "Enqueueing ordered broadcast " + r 15070 + ": prev had " + queue.mOrderedBroadcasts.size()); 15071 if (DEBUG_BROADCAST) { 15072 int seq = r.intent.getIntExtra("seq", -1); 15073 Slog.i(TAG, "Enqueueing broadcast " + r.intent.getAction() + " seq=" + seq); 15074 } 15075 boolean replaced = replacePending && queue.replaceOrderedBroadcastLocked(r); 15076 if (!replaced) { 15077 queue.enqueueOrderedBroadcastLocked(r); 15078 queue.scheduleBroadcastsLocked(); 15079 } 15080 } 15081 15082 return ActivityManager.BROADCAST_SUCCESS; 15083 } 15084 15085 final Intent verifyBroadcastLocked(Intent intent) { 15086 // Refuse possible leaked file descriptors 15087 if (intent != null && intent.hasFileDescriptors() == true) { 15088 throw new IllegalArgumentException("File descriptors passed in Intent"); 15089 } 15090 15091 int flags = intent.getFlags(); 15092 15093 if (!mProcessesReady) { 15094 // if the caller really truly claims to know what they're doing, go 15095 // ahead and allow the broadcast without launching any receivers 15096 if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT) != 0) { 15097 intent = new Intent(intent); 15098 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 15099 } else if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) { 15100 Slog.e(TAG, "Attempt to launch receivers of broadcast intent " + intent 15101 + " before boot completion"); 15102 throw new IllegalStateException("Cannot broadcast before boot completed"); 15103 } 15104 } 15105 15106 if ((flags&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 15107 throw new IllegalArgumentException( 15108 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 15109 } 15110 15111 return intent; 15112 } 15113 15114 public final int broadcastIntent(IApplicationThread caller, 15115 Intent intent, String resolvedType, IIntentReceiver resultTo, 15116 int resultCode, String resultData, Bundle map, 15117 String requiredPermission, int appOp, boolean serialized, boolean sticky, int userId) { 15118 enforceNotIsolatedCaller("broadcastIntent"); 15119 synchronized(this) { 15120 intent = verifyBroadcastLocked(intent); 15121 15122 final ProcessRecord callerApp = getRecordForAppLocked(caller); 15123 final int callingPid = Binder.getCallingPid(); 15124 final int callingUid = Binder.getCallingUid(); 15125 final long origId = Binder.clearCallingIdentity(); 15126 int res = broadcastIntentLocked(callerApp, 15127 callerApp != null ? callerApp.info.packageName : null, 15128 intent, resolvedType, resultTo, 15129 resultCode, resultData, map, requiredPermission, appOp, serialized, sticky, 15130 callingPid, callingUid, userId); 15131 Binder.restoreCallingIdentity(origId); 15132 return res; 15133 } 15134 } 15135 15136 int broadcastIntentInPackage(String packageName, int uid, 15137 Intent intent, String resolvedType, IIntentReceiver resultTo, 15138 int resultCode, String resultData, Bundle map, 15139 String requiredPermission, boolean serialized, boolean sticky, int userId) { 15140 synchronized(this) { 15141 intent = verifyBroadcastLocked(intent); 15142 15143 final long origId = Binder.clearCallingIdentity(); 15144 int res = broadcastIntentLocked(null, packageName, intent, resolvedType, 15145 resultTo, resultCode, resultData, map, requiredPermission, 15146 AppOpsManager.OP_NONE, serialized, sticky, -1, uid, userId); 15147 Binder.restoreCallingIdentity(origId); 15148 return res; 15149 } 15150 } 15151 15152 public final void unbroadcastIntent(IApplicationThread caller, Intent intent, int userId) { 15153 // Refuse possible leaked file descriptors 15154 if (intent != null && intent.hasFileDescriptors() == true) { 15155 throw new IllegalArgumentException("File descriptors passed in Intent"); 15156 } 15157 15158 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 15159 userId, true, ALLOW_NON_FULL, "removeStickyBroadcast", null); 15160 15161 synchronized(this) { 15162 if (checkCallingPermission(android.Manifest.permission.BROADCAST_STICKY) 15163 != PackageManager.PERMISSION_GRANTED) { 15164 String msg = "Permission Denial: unbroadcastIntent() from pid=" 15165 + Binder.getCallingPid() 15166 + ", uid=" + Binder.getCallingUid() 15167 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 15168 Slog.w(TAG, msg); 15169 throw new SecurityException(msg); 15170 } 15171 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 15172 if (stickies != null) { 15173 ArrayList<Intent> list = stickies.get(intent.getAction()); 15174 if (list != null) { 15175 int N = list.size(); 15176 int i; 15177 for (i=0; i<N; i++) { 15178 if (intent.filterEquals(list.get(i))) { 15179 list.remove(i); 15180 break; 15181 } 15182 } 15183 if (list.size() <= 0) { 15184 stickies.remove(intent.getAction()); 15185 } 15186 } 15187 if (stickies.size() <= 0) { 15188 mStickyBroadcasts.remove(userId); 15189 } 15190 } 15191 } 15192 } 15193 15194 private final boolean finishReceiverLocked(IBinder receiver, int resultCode, 15195 String resultData, Bundle resultExtras, boolean resultAbort) { 15196 final BroadcastRecord r = broadcastRecordForReceiverLocked(receiver); 15197 if (r == null) { 15198 Slog.w(TAG, "finishReceiver called but not found on queue"); 15199 return false; 15200 } 15201 15202 return r.queue.finishReceiverLocked(r, resultCode, resultData, resultExtras, resultAbort, false); 15203 } 15204 15205 void backgroundServicesFinishedLocked(int userId) { 15206 for (BroadcastQueue queue : mBroadcastQueues) { 15207 queue.backgroundServicesFinishedLocked(userId); 15208 } 15209 } 15210 15211 public void finishReceiver(IBinder who, int resultCode, String resultData, 15212 Bundle resultExtras, boolean resultAbort) { 15213 if (DEBUG_BROADCAST) Slog.v(TAG, "Finish receiver: " + who); 15214 15215 // Refuse possible leaked file descriptors 15216 if (resultExtras != null && resultExtras.hasFileDescriptors()) { 15217 throw new IllegalArgumentException("File descriptors passed in Bundle"); 15218 } 15219 15220 final long origId = Binder.clearCallingIdentity(); 15221 try { 15222 boolean doNext = false; 15223 BroadcastRecord r; 15224 15225 synchronized(this) { 15226 r = broadcastRecordForReceiverLocked(who); 15227 if (r != null) { 15228 doNext = r.queue.finishReceiverLocked(r, resultCode, 15229 resultData, resultExtras, resultAbort, true); 15230 } 15231 } 15232 15233 if (doNext) { 15234 r.queue.processNextBroadcast(false); 15235 } 15236 trimApplications(); 15237 } finally { 15238 Binder.restoreCallingIdentity(origId); 15239 } 15240 } 15241 15242 // ========================================================= 15243 // INSTRUMENTATION 15244 // ========================================================= 15245 15246 public boolean startInstrumentation(ComponentName className, 15247 String profileFile, int flags, Bundle arguments, 15248 IInstrumentationWatcher watcher, IUiAutomationConnection uiAutomationConnection, 15249 int userId, String abiOverride) { 15250 enforceNotIsolatedCaller("startInstrumentation"); 15251 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 15252 userId, false, ALLOW_FULL_ONLY, "startInstrumentation", null); 15253 // Refuse possible leaked file descriptors 15254 if (arguments != null && arguments.hasFileDescriptors()) { 15255 throw new IllegalArgumentException("File descriptors passed in Bundle"); 15256 } 15257 15258 synchronized(this) { 15259 InstrumentationInfo ii = null; 15260 ApplicationInfo ai = null; 15261 try { 15262 ii = mContext.getPackageManager().getInstrumentationInfo( 15263 className, STOCK_PM_FLAGS); 15264 ai = AppGlobals.getPackageManager().getApplicationInfo( 15265 ii.targetPackage, STOCK_PM_FLAGS, userId); 15266 } catch (PackageManager.NameNotFoundException e) { 15267 } catch (RemoteException e) { 15268 } 15269 if (ii == null) { 15270 reportStartInstrumentationFailure(watcher, className, 15271 "Unable to find instrumentation info for: " + className); 15272 return false; 15273 } 15274 if (ai == null) { 15275 reportStartInstrumentationFailure(watcher, className, 15276 "Unable to find instrumentation target package: " + ii.targetPackage); 15277 return false; 15278 } 15279 15280 int match = mContext.getPackageManager().checkSignatures( 15281 ii.targetPackage, ii.packageName); 15282 if (match < 0 && match != PackageManager.SIGNATURE_FIRST_NOT_SIGNED) { 15283 String msg = "Permission Denial: starting instrumentation " 15284 + className + " from pid=" 15285 + Binder.getCallingPid() 15286 + ", uid=" + Binder.getCallingPid() 15287 + " not allowed because package " + ii.packageName 15288 + " does not have a signature matching the target " 15289 + ii.targetPackage; 15290 reportStartInstrumentationFailure(watcher, className, msg); 15291 throw new SecurityException(msg); 15292 } 15293 15294 final long origId = Binder.clearCallingIdentity(); 15295 // Instrumentation can kill and relaunch even persistent processes 15296 forceStopPackageLocked(ii.targetPackage, -1, true, false, true, true, false, userId, 15297 "start instr"); 15298 ProcessRecord app = addAppLocked(ai, false, abiOverride); 15299 app.instrumentationClass = className; 15300 app.instrumentationInfo = ai; 15301 app.instrumentationProfileFile = profileFile; 15302 app.instrumentationArguments = arguments; 15303 app.instrumentationWatcher = watcher; 15304 app.instrumentationUiAutomationConnection = uiAutomationConnection; 15305 app.instrumentationResultClass = className; 15306 Binder.restoreCallingIdentity(origId); 15307 } 15308 15309 return true; 15310 } 15311 15312 /** 15313 * Report errors that occur while attempting to start Instrumentation. Always writes the 15314 * error to the logs, but if somebody is watching, send the report there too. This enables 15315 * the "am" command to report errors with more information. 15316 * 15317 * @param watcher The IInstrumentationWatcher. Null if there isn't one. 15318 * @param cn The component name of the instrumentation. 15319 * @param report The error report. 15320 */ 15321 private void reportStartInstrumentationFailure(IInstrumentationWatcher watcher, 15322 ComponentName cn, String report) { 15323 Slog.w(TAG, report); 15324 try { 15325 if (watcher != null) { 15326 Bundle results = new Bundle(); 15327 results.putString(Instrumentation.REPORT_KEY_IDENTIFIER, "ActivityManagerService"); 15328 results.putString("Error", report); 15329 watcher.instrumentationStatus(cn, -1, results); 15330 } 15331 } catch (RemoteException e) { 15332 Slog.w(TAG, e); 15333 } 15334 } 15335 15336 void finishInstrumentationLocked(ProcessRecord app, int resultCode, Bundle results) { 15337 if (app.instrumentationWatcher != null) { 15338 try { 15339 // NOTE: IInstrumentationWatcher *must* be oneway here 15340 app.instrumentationWatcher.instrumentationFinished( 15341 app.instrumentationClass, 15342 resultCode, 15343 results); 15344 } catch (RemoteException e) { 15345 } 15346 } 15347 if (app.instrumentationUiAutomationConnection != null) { 15348 try { 15349 app.instrumentationUiAutomationConnection.shutdown(); 15350 } catch (RemoteException re) { 15351 /* ignore */ 15352 } 15353 // Only a UiAutomation can set this flag and now that 15354 // it is finished we make sure it is reset to its default. 15355 mUserIsMonkey = false; 15356 } 15357 app.instrumentationWatcher = null; 15358 app.instrumentationUiAutomationConnection = null; 15359 app.instrumentationClass = null; 15360 app.instrumentationInfo = null; 15361 app.instrumentationProfileFile = null; 15362 app.instrumentationArguments = null; 15363 15364 forceStopPackageLocked(app.info.packageName, -1, false, false, true, true, false, app.userId, 15365 "finished inst"); 15366 } 15367 15368 public void finishInstrumentation(IApplicationThread target, 15369 int resultCode, Bundle results) { 15370 int userId = UserHandle.getCallingUserId(); 15371 // Refuse possible leaked file descriptors 15372 if (results != null && results.hasFileDescriptors()) { 15373 throw new IllegalArgumentException("File descriptors passed in Intent"); 15374 } 15375 15376 synchronized(this) { 15377 ProcessRecord app = getRecordForAppLocked(target); 15378 if (app == null) { 15379 Slog.w(TAG, "finishInstrumentation: no app for " + target); 15380 return; 15381 } 15382 final long origId = Binder.clearCallingIdentity(); 15383 finishInstrumentationLocked(app, resultCode, results); 15384 Binder.restoreCallingIdentity(origId); 15385 } 15386 } 15387 15388 // ========================================================= 15389 // CONFIGURATION 15390 // ========================================================= 15391 15392 public ConfigurationInfo getDeviceConfigurationInfo() { 15393 ConfigurationInfo config = new ConfigurationInfo(); 15394 synchronized (this) { 15395 config.reqTouchScreen = mConfiguration.touchscreen; 15396 config.reqKeyboardType = mConfiguration.keyboard; 15397 config.reqNavigation = mConfiguration.navigation; 15398 if (mConfiguration.navigation == Configuration.NAVIGATION_DPAD 15399 || mConfiguration.navigation == Configuration.NAVIGATION_TRACKBALL) { 15400 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_FIVE_WAY_NAV; 15401 } 15402 if (mConfiguration.keyboard != Configuration.KEYBOARD_UNDEFINED 15403 && mConfiguration.keyboard != Configuration.KEYBOARD_NOKEYS) { 15404 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_HARD_KEYBOARD; 15405 } 15406 config.reqGlEsVersion = GL_ES_VERSION; 15407 } 15408 return config; 15409 } 15410 15411 ActivityStack getFocusedStack() { 15412 return mStackSupervisor.getFocusedStack(); 15413 } 15414 15415 public Configuration getConfiguration() { 15416 Configuration ci; 15417 synchronized(this) { 15418 ci = new Configuration(mConfiguration); 15419 } 15420 return ci; 15421 } 15422 15423 public void updatePersistentConfiguration(Configuration values) { 15424 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 15425 "updateConfiguration()"); 15426 enforceCallingPermission(android.Manifest.permission.WRITE_SETTINGS, 15427 "updateConfiguration()"); 15428 if (values == null) { 15429 throw new NullPointerException("Configuration must not be null"); 15430 } 15431 15432 synchronized(this) { 15433 final long origId = Binder.clearCallingIdentity(); 15434 updateConfigurationLocked(values, null, true, false); 15435 Binder.restoreCallingIdentity(origId); 15436 } 15437 } 15438 15439 public void updateConfiguration(Configuration values) { 15440 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 15441 "updateConfiguration()"); 15442 15443 synchronized(this) { 15444 if (values == null && mWindowManager != null) { 15445 // sentinel: fetch the current configuration from the window manager 15446 values = mWindowManager.computeNewConfiguration(); 15447 } 15448 15449 if (mWindowManager != null) { 15450 mProcessList.applyDisplaySize(mWindowManager); 15451 } 15452 15453 final long origId = Binder.clearCallingIdentity(); 15454 if (values != null) { 15455 Settings.System.clearConfiguration(values); 15456 } 15457 updateConfigurationLocked(values, null, false, false); 15458 Binder.restoreCallingIdentity(origId); 15459 } 15460 } 15461 15462 /** 15463 * Do either or both things: (1) change the current configuration, and (2) 15464 * make sure the given activity is running with the (now) current 15465 * configuration. Returns true if the activity has been left running, or 15466 * false if <var>starting</var> is being destroyed to match the new 15467 * configuration. 15468 * @param persistent TODO 15469 */ 15470 boolean updateConfigurationLocked(Configuration values, 15471 ActivityRecord starting, boolean persistent, boolean initLocale) { 15472 int changes = 0; 15473 15474 if (values != null) { 15475 Configuration newConfig = new Configuration(mConfiguration); 15476 changes = newConfig.updateFrom(values); 15477 if (changes != 0) { 15478 if (DEBUG_SWITCH || DEBUG_CONFIGURATION) { 15479 Slog.i(TAG, "Updating configuration to: " + values); 15480 } 15481 15482 EventLog.writeEvent(EventLogTags.CONFIGURATION_CHANGED, changes); 15483 15484 if (values.locale != null && !initLocale) { 15485 saveLocaleLocked(values.locale, 15486 !values.locale.equals(mConfiguration.locale), 15487 values.userSetLocale); 15488 } 15489 15490 mConfigurationSeq++; 15491 if (mConfigurationSeq <= 0) { 15492 mConfigurationSeq = 1; 15493 } 15494 newConfig.seq = mConfigurationSeq; 15495 mConfiguration = newConfig; 15496 Slog.i(TAG, "Config changes=" + Integer.toHexString(changes) + " " + newConfig); 15497 //mUsageStatsService.noteStartConfig(newConfig); 15498 15499 final Configuration configCopy = new Configuration(mConfiguration); 15500 15501 // TODO: If our config changes, should we auto dismiss any currently 15502 // showing dialogs? 15503 mShowDialogs = shouldShowDialogs(newConfig); 15504 15505 AttributeCache ac = AttributeCache.instance(); 15506 if (ac != null) { 15507 ac.updateConfiguration(configCopy); 15508 } 15509 15510 // Make sure all resources in our process are updated 15511 // right now, so that anyone who is going to retrieve 15512 // resource values after we return will be sure to get 15513 // the new ones. This is especially important during 15514 // boot, where the first config change needs to guarantee 15515 // all resources have that config before following boot 15516 // code is executed. 15517 mSystemThread.applyConfigurationToResources(configCopy); 15518 15519 if (persistent && Settings.System.hasInterestingConfigurationChanges(changes)) { 15520 Message msg = mHandler.obtainMessage(UPDATE_CONFIGURATION_MSG); 15521 msg.obj = new Configuration(configCopy); 15522 mHandler.sendMessage(msg); 15523 } 15524 15525 for (int i=mLruProcesses.size()-1; i>=0; i--) { 15526 ProcessRecord app = mLruProcesses.get(i); 15527 try { 15528 if (app.thread != null) { 15529 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Sending to proc " 15530 + app.processName + " new config " + mConfiguration); 15531 app.thread.scheduleConfigurationChanged(configCopy); 15532 } 15533 } catch (Exception e) { 15534 } 15535 } 15536 Intent intent = new Intent(Intent.ACTION_CONFIGURATION_CHANGED); 15537 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 15538 | Intent.FLAG_RECEIVER_REPLACE_PENDING 15539 | Intent.FLAG_RECEIVER_FOREGROUND); 15540 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, 15541 null, AppOpsManager.OP_NONE, false, false, MY_PID, 15542 Process.SYSTEM_UID, UserHandle.USER_ALL); 15543 if ((changes&ActivityInfo.CONFIG_LOCALE) != 0) { 15544 intent = new Intent(Intent.ACTION_LOCALE_CHANGED); 15545 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 15546 broadcastIntentLocked(null, null, intent, 15547 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 15548 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 15549 } 15550 } 15551 } 15552 15553 boolean kept = true; 15554 final ActivityStack mainStack = mStackSupervisor.getFocusedStack(); 15555 // mainStack is null during startup. 15556 if (mainStack != null) { 15557 if (changes != 0 && starting == null) { 15558 // If the configuration changed, and the caller is not already 15559 // in the process of starting an activity, then find the top 15560 // activity to check if its configuration needs to change. 15561 starting = mainStack.topRunningActivityLocked(null); 15562 } 15563 15564 if (starting != null) { 15565 kept = mainStack.ensureActivityConfigurationLocked(starting, changes); 15566 // And we need to make sure at this point that all other activities 15567 // are made visible with the correct configuration. 15568 mStackSupervisor.ensureActivitiesVisibleLocked(starting, changes); 15569 } 15570 } 15571 15572 if (values != null && mWindowManager != null) { 15573 mWindowManager.setNewConfiguration(mConfiguration); 15574 } 15575 15576 return kept; 15577 } 15578 15579 /** 15580 * Decide based on the configuration whether we should shouw the ANR, 15581 * crash, etc dialogs. The idea is that if there is no affordnace to 15582 * press the on-screen buttons, we shouldn't show the dialog. 15583 * 15584 * A thought: SystemUI might also want to get told about this, the Power 15585 * dialog / global actions also might want different behaviors. 15586 */ 15587 private static final boolean shouldShowDialogs(Configuration config) { 15588 return !(config.keyboard == Configuration.KEYBOARD_NOKEYS 15589 && config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH); 15590 } 15591 15592 /** 15593 * Save the locale. You must be inside a synchronized (this) block. 15594 */ 15595 private void saveLocaleLocked(Locale l, boolean isDiff, boolean isPersist) { 15596 if(isDiff) { 15597 SystemProperties.set("user.language", l.getLanguage()); 15598 SystemProperties.set("user.region", l.getCountry()); 15599 } 15600 15601 if(isPersist) { 15602 SystemProperties.set("persist.sys.language", l.getLanguage()); 15603 SystemProperties.set("persist.sys.country", l.getCountry()); 15604 SystemProperties.set("persist.sys.localevar", l.getVariant()); 15605 } 15606 } 15607 15608 @Override 15609 public boolean shouldUpRecreateTask(IBinder token, String destAffinity) { 15610 synchronized (this) { 15611 ActivityRecord srec = ActivityRecord.forToken(token); 15612 if (srec.task != null && srec.task.stack != null) { 15613 return srec.task.stack.shouldUpRecreateTaskLocked(srec, destAffinity); 15614 } 15615 } 15616 return false; 15617 } 15618 15619 public boolean navigateUpTo(IBinder token, Intent destIntent, int resultCode, 15620 Intent resultData) { 15621 15622 synchronized (this) { 15623 final ActivityStack stack = ActivityRecord.getStackLocked(token); 15624 if (stack != null) { 15625 return stack.navigateUpToLocked(token, destIntent, resultCode, resultData); 15626 } 15627 return false; 15628 } 15629 } 15630 15631 public int getLaunchedFromUid(IBinder activityToken) { 15632 ActivityRecord srec = ActivityRecord.forToken(activityToken); 15633 if (srec == null) { 15634 return -1; 15635 } 15636 return srec.launchedFromUid; 15637 } 15638 15639 public String getLaunchedFromPackage(IBinder activityToken) { 15640 ActivityRecord srec = ActivityRecord.forToken(activityToken); 15641 if (srec == null) { 15642 return null; 15643 } 15644 return srec.launchedFromPackage; 15645 } 15646 15647 // ========================================================= 15648 // LIFETIME MANAGEMENT 15649 // ========================================================= 15650 15651 // Returns which broadcast queue the app is the current [or imminent] receiver 15652 // on, or 'null' if the app is not an active broadcast recipient. 15653 private BroadcastQueue isReceivingBroadcast(ProcessRecord app) { 15654 BroadcastRecord r = app.curReceiver; 15655 if (r != null) { 15656 return r.queue; 15657 } 15658 15659 // It's not the current receiver, but it might be starting up to become one 15660 synchronized (this) { 15661 for (BroadcastQueue queue : mBroadcastQueues) { 15662 r = queue.mPendingBroadcast; 15663 if (r != null && r.curApp == app) { 15664 // found it; report which queue it's in 15665 return queue; 15666 } 15667 } 15668 } 15669 15670 return null; 15671 } 15672 15673 private final int computeOomAdjLocked(ProcessRecord app, int cachedAdj, ProcessRecord TOP_APP, 15674 boolean doingAll, long now) { 15675 if (mAdjSeq == app.adjSeq) { 15676 // This adjustment has already been computed. 15677 return app.curRawAdj; 15678 } 15679 15680 if (app.thread == null) { 15681 app.adjSeq = mAdjSeq; 15682 app.curSchedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15683 app.curProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15684 return (app.curAdj=app.curRawAdj=ProcessList.CACHED_APP_MAX_ADJ); 15685 } 15686 15687 app.adjTypeCode = ActivityManager.RunningAppProcessInfo.REASON_UNKNOWN; 15688 app.adjSource = null; 15689 app.adjTarget = null; 15690 app.empty = false; 15691 app.cached = false; 15692 15693 final int activitiesSize = app.activities.size(); 15694 15695 if (app.maxAdj <= ProcessList.FOREGROUND_APP_ADJ) { 15696 // The max adjustment doesn't allow this app to be anything 15697 // below foreground, so it is not worth doing work for it. 15698 app.adjType = "fixed"; 15699 app.adjSeq = mAdjSeq; 15700 app.curRawAdj = app.maxAdj; 15701 app.foregroundActivities = false; 15702 app.curSchedGroup = Process.THREAD_GROUP_DEFAULT; 15703 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT; 15704 // System processes can do UI, and when they do we want to have 15705 // them trim their memory after the user leaves the UI. To 15706 // facilitate this, here we need to determine whether or not it 15707 // is currently showing UI. 15708 app.systemNoUi = true; 15709 if (app == TOP_APP) { 15710 app.systemNoUi = false; 15711 } else if (activitiesSize > 0) { 15712 for (int j = 0; j < activitiesSize; j++) { 15713 final ActivityRecord r = app.activities.get(j); 15714 if (r.visible) { 15715 app.systemNoUi = false; 15716 } 15717 } 15718 } 15719 if (!app.systemNoUi) { 15720 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT_UI; 15721 } 15722 return (app.curAdj=app.maxAdj); 15723 } 15724 15725 app.systemNoUi = false; 15726 15727 // Determine the importance of the process, starting with most 15728 // important to least, and assign an appropriate OOM adjustment. 15729 int adj; 15730 int schedGroup; 15731 int procState; 15732 boolean foregroundActivities = false; 15733 BroadcastQueue queue; 15734 if (app == TOP_APP) { 15735 // The last app on the list is the foreground app. 15736 adj = ProcessList.FOREGROUND_APP_ADJ; 15737 schedGroup = Process.THREAD_GROUP_DEFAULT; 15738 app.adjType = "top-activity"; 15739 foregroundActivities = true; 15740 procState = ActivityManager.PROCESS_STATE_TOP; 15741 } else if (app.instrumentationClass != null) { 15742 // Don't want to kill running instrumentation. 15743 adj = ProcessList.FOREGROUND_APP_ADJ; 15744 schedGroup = Process.THREAD_GROUP_DEFAULT; 15745 app.adjType = "instrumentation"; 15746 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15747 } else if ((queue = isReceivingBroadcast(app)) != null) { 15748 // An app that is currently receiving a broadcast also 15749 // counts as being in the foreground for OOM killer purposes. 15750 // It's placed in a sched group based on the nature of the 15751 // broadcast as reflected by which queue it's active in. 15752 adj = ProcessList.FOREGROUND_APP_ADJ; 15753 schedGroup = (queue == mFgBroadcastQueue) 15754 ? Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 15755 app.adjType = "broadcast"; 15756 procState = ActivityManager.PROCESS_STATE_RECEIVER; 15757 } else if (app.executingServices.size() > 0) { 15758 // An app that is currently executing a service callback also 15759 // counts as being in the foreground. 15760 adj = ProcessList.FOREGROUND_APP_ADJ; 15761 schedGroup = app.execServicesFg ? 15762 Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 15763 app.adjType = "exec-service"; 15764 procState = ActivityManager.PROCESS_STATE_SERVICE; 15765 //Slog.i(TAG, "EXEC " + (app.execServicesFg ? "FG" : "BG") + ": " + app); 15766 } else { 15767 // As far as we know the process is empty. We may change our mind later. 15768 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15769 // At this point we don't actually know the adjustment. Use the cached adj 15770 // value that the caller wants us to. 15771 adj = cachedAdj; 15772 procState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15773 app.cached = true; 15774 app.empty = true; 15775 app.adjType = "cch-empty"; 15776 } 15777 15778 // Examine all activities if not already foreground. 15779 if (!foregroundActivities && activitiesSize > 0) { 15780 for (int j = 0; j < activitiesSize; j++) { 15781 final ActivityRecord r = app.activities.get(j); 15782 if (r.app != app) { 15783 Slog.w(TAG, "Wtf, activity " + r + " in proc activity list not using proc " 15784 + app + "?!?"); 15785 continue; 15786 } 15787 if (r.visible) { 15788 // App has a visible activity; only upgrade adjustment. 15789 if (adj > ProcessList.VISIBLE_APP_ADJ) { 15790 adj = ProcessList.VISIBLE_APP_ADJ; 15791 app.adjType = "visible"; 15792 } 15793 if (procState > ActivityManager.PROCESS_STATE_TOP) { 15794 procState = ActivityManager.PROCESS_STATE_TOP; 15795 } 15796 schedGroup = Process.THREAD_GROUP_DEFAULT; 15797 app.cached = false; 15798 app.empty = false; 15799 foregroundActivities = true; 15800 break; 15801 } else if (r.state == ActivityState.PAUSING || r.state == ActivityState.PAUSED) { 15802 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15803 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15804 app.adjType = "pausing"; 15805 } 15806 if (procState > ActivityManager.PROCESS_STATE_TOP) { 15807 procState = ActivityManager.PROCESS_STATE_TOP; 15808 } 15809 schedGroup = Process.THREAD_GROUP_DEFAULT; 15810 app.cached = false; 15811 app.empty = false; 15812 foregroundActivities = true; 15813 } else if (r.state == ActivityState.STOPPING) { 15814 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15815 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15816 app.adjType = "stopping"; 15817 } 15818 // For the process state, we will at this point consider the 15819 // process to be cached. It will be cached either as an activity 15820 // or empty depending on whether the activity is finishing. We do 15821 // this so that we can treat the process as cached for purposes of 15822 // memory trimming (determing current memory level, trim command to 15823 // send to process) since there can be an arbitrary number of stopping 15824 // processes and they should soon all go into the cached state. 15825 if (!r.finishing) { 15826 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15827 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 15828 } 15829 } 15830 app.cached = false; 15831 app.empty = false; 15832 foregroundActivities = true; 15833 } else { 15834 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15835 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 15836 app.adjType = "cch-act"; 15837 } 15838 } 15839 } 15840 } 15841 15842 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15843 if (app.foregroundServices) { 15844 // The user is aware of this app, so make it visible. 15845 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15846 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15847 app.cached = false; 15848 app.adjType = "fg-service"; 15849 schedGroup = Process.THREAD_GROUP_DEFAULT; 15850 } else if (app.forcingToForeground != null) { 15851 // The user is aware of this app, so make it visible. 15852 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15853 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15854 app.cached = false; 15855 app.adjType = "force-fg"; 15856 app.adjSource = app.forcingToForeground; 15857 schedGroup = Process.THREAD_GROUP_DEFAULT; 15858 } 15859 } 15860 15861 if (app == mHeavyWeightProcess) { 15862 if (adj > ProcessList.HEAVY_WEIGHT_APP_ADJ) { 15863 // We don't want to kill the current heavy-weight process. 15864 adj = ProcessList.HEAVY_WEIGHT_APP_ADJ; 15865 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15866 app.cached = false; 15867 app.adjType = "heavy"; 15868 } 15869 if (procState > ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 15870 procState = ActivityManager.PROCESS_STATE_HEAVY_WEIGHT; 15871 } 15872 } 15873 15874 if (app == mHomeProcess) { 15875 if (adj > ProcessList.HOME_APP_ADJ) { 15876 // This process is hosting what we currently consider to be the 15877 // home app, so we don't want to let it go into the background. 15878 adj = ProcessList.HOME_APP_ADJ; 15879 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15880 app.cached = false; 15881 app.adjType = "home"; 15882 } 15883 if (procState > ActivityManager.PROCESS_STATE_HOME) { 15884 procState = ActivityManager.PROCESS_STATE_HOME; 15885 } 15886 } 15887 15888 if (app == mPreviousProcess && app.activities.size() > 0) { 15889 if (adj > ProcessList.PREVIOUS_APP_ADJ) { 15890 // This was the previous process that showed UI to the user. 15891 // We want to try to keep it around more aggressively, to give 15892 // a good experience around switching between two apps. 15893 adj = ProcessList.PREVIOUS_APP_ADJ; 15894 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15895 app.cached = false; 15896 app.adjType = "previous"; 15897 } 15898 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 15899 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 15900 } 15901 } 15902 15903 if (false) Slog.i(TAG, "OOM " + app + ": initial adj=" + adj 15904 + " reason=" + app.adjType); 15905 15906 // By default, we use the computed adjustment. It may be changed if 15907 // there are applications dependent on our services or providers, but 15908 // this gives us a baseline and makes sure we don't get into an 15909 // infinite recursion. 15910 app.adjSeq = mAdjSeq; 15911 app.curRawAdj = adj; 15912 app.hasStartedServices = false; 15913 15914 if (mBackupTarget != null && app == mBackupTarget.app) { 15915 // If possible we want to avoid killing apps while they're being backed up 15916 if (adj > ProcessList.BACKUP_APP_ADJ) { 15917 if (DEBUG_BACKUP) Slog.v(TAG, "oom BACKUP_APP_ADJ for " + app); 15918 adj = ProcessList.BACKUP_APP_ADJ; 15919 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 15920 procState = ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 15921 } 15922 app.adjType = "backup"; 15923 app.cached = false; 15924 } 15925 if (procState > ActivityManager.PROCESS_STATE_BACKUP) { 15926 procState = ActivityManager.PROCESS_STATE_BACKUP; 15927 } 15928 } 15929 15930 boolean mayBeTop = false; 15931 15932 for (int is = app.services.size()-1; 15933 is >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15934 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15935 || procState > ActivityManager.PROCESS_STATE_TOP); 15936 is--) { 15937 ServiceRecord s = app.services.valueAt(is); 15938 if (s.startRequested) { 15939 app.hasStartedServices = true; 15940 if (procState > ActivityManager.PROCESS_STATE_SERVICE) { 15941 procState = ActivityManager.PROCESS_STATE_SERVICE; 15942 } 15943 if (app.hasShownUi && app != mHomeProcess) { 15944 // If this process has shown some UI, let it immediately 15945 // go to the LRU list because it may be pretty heavy with 15946 // UI stuff. We'll tag it with a label just to help 15947 // debug and understand what is going on. 15948 if (adj > ProcessList.SERVICE_ADJ) { 15949 app.adjType = "cch-started-ui-services"; 15950 } 15951 } else { 15952 if (now < (s.lastActivity + ActiveServices.MAX_SERVICE_INACTIVITY)) { 15953 // This service has seen some activity within 15954 // recent memory, so we will keep its process ahead 15955 // of the background processes. 15956 if (adj > ProcessList.SERVICE_ADJ) { 15957 adj = ProcessList.SERVICE_ADJ; 15958 app.adjType = "started-services"; 15959 app.cached = false; 15960 } 15961 } 15962 // If we have let the service slide into the background 15963 // state, still have some text describing what it is doing 15964 // even though the service no longer has an impact. 15965 if (adj > ProcessList.SERVICE_ADJ) { 15966 app.adjType = "cch-started-services"; 15967 } 15968 } 15969 } 15970 for (int conni = s.connections.size()-1; 15971 conni >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15972 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15973 || procState > ActivityManager.PROCESS_STATE_TOP); 15974 conni--) { 15975 ArrayList<ConnectionRecord> clist = s.connections.valueAt(conni); 15976 for (int i = 0; 15977 i < clist.size() && (adj > ProcessList.FOREGROUND_APP_ADJ 15978 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15979 || procState > ActivityManager.PROCESS_STATE_TOP); 15980 i++) { 15981 // XXX should compute this based on the max of 15982 // all connected clients. 15983 ConnectionRecord cr = clist.get(i); 15984 if (cr.binding.client == app) { 15985 // Binding to ourself is not interesting. 15986 continue; 15987 } 15988 if ((cr.flags&Context.BIND_WAIVE_PRIORITY) == 0) { 15989 ProcessRecord client = cr.binding.client; 15990 int clientAdj = computeOomAdjLocked(client, cachedAdj, 15991 TOP_APP, doingAll, now); 15992 int clientProcState = client.curProcState; 15993 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15994 // If the other app is cached for any reason, for purposes here 15995 // we are going to consider it empty. The specific cached state 15996 // doesn't propagate except under certain conditions. 15997 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15998 } 15999 String adjType = null; 16000 if ((cr.flags&Context.BIND_ALLOW_OOM_MANAGEMENT) != 0) { 16001 // Not doing bind OOM management, so treat 16002 // this guy more like a started service. 16003 if (app.hasShownUi && app != mHomeProcess) { 16004 // If this process has shown some UI, let it immediately 16005 // go to the LRU list because it may be pretty heavy with 16006 // UI stuff. We'll tag it with a label just to help 16007 // debug and understand what is going on. 16008 if (adj > clientAdj) { 16009 adjType = "cch-bound-ui-services"; 16010 } 16011 app.cached = false; 16012 clientAdj = adj; 16013 clientProcState = procState; 16014 } else { 16015 if (now >= (s.lastActivity 16016 + ActiveServices.MAX_SERVICE_INACTIVITY)) { 16017 // This service has not seen activity within 16018 // recent memory, so allow it to drop to the 16019 // LRU list if there is no other reason to keep 16020 // it around. We'll also tag it with a label just 16021 // to help debug and undertand what is going on. 16022 if (adj > clientAdj) { 16023 adjType = "cch-bound-services"; 16024 } 16025 clientAdj = adj; 16026 } 16027 } 16028 } 16029 if (adj > clientAdj) { 16030 // If this process has recently shown UI, and 16031 // the process that is binding to it is less 16032 // important than being visible, then we don't 16033 // care about the binding as much as we care 16034 // about letting this process get into the LRU 16035 // list to be killed and restarted if needed for 16036 // memory. 16037 if (app.hasShownUi && app != mHomeProcess 16038 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16039 adjType = "cch-bound-ui-services"; 16040 } else { 16041 if ((cr.flags&(Context.BIND_ABOVE_CLIENT 16042 |Context.BIND_IMPORTANT)) != 0) { 16043 adj = clientAdj; 16044 } else if ((cr.flags&Context.BIND_NOT_VISIBLE) != 0 16045 && clientAdj < ProcessList.PERCEPTIBLE_APP_ADJ 16046 && adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16047 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16048 } else if (clientAdj > ProcessList.VISIBLE_APP_ADJ) { 16049 adj = clientAdj; 16050 } else { 16051 if (adj > ProcessList.VISIBLE_APP_ADJ) { 16052 adj = ProcessList.VISIBLE_APP_ADJ; 16053 } 16054 } 16055 if (!client.cached) { 16056 app.cached = false; 16057 } 16058 adjType = "service"; 16059 } 16060 } 16061 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 16062 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 16063 schedGroup = Process.THREAD_GROUP_DEFAULT; 16064 } 16065 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 16066 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 16067 // Special handling of clients who are in the top state. 16068 // We *may* want to consider this process to be in the 16069 // top state as well, but only if there is not another 16070 // reason for it to be running. Being on the top is a 16071 // special state, meaning you are specifically running 16072 // for the current top app. If the process is already 16073 // running in the background for some other reason, it 16074 // is more important to continue considering it to be 16075 // in the background state. 16076 mayBeTop = true; 16077 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16078 } else { 16079 // Special handling for above-top states (persistent 16080 // processes). These should not bring the current process 16081 // into the top state, since they are not on top. Instead 16082 // give them the best state after that. 16083 clientProcState = 16084 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16085 } 16086 } 16087 } else { 16088 if (clientProcState < 16089 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 16090 clientProcState = 16091 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 16092 } 16093 } 16094 if (procState > clientProcState) { 16095 procState = clientProcState; 16096 } 16097 if (procState < ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 16098 && (cr.flags&Context.BIND_SHOWING_UI) != 0) { 16099 app.pendingUiClean = true; 16100 } 16101 if (adjType != null) { 16102 app.adjType = adjType; 16103 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 16104 .REASON_SERVICE_IN_USE; 16105 app.adjSource = cr.binding.client; 16106 app.adjSourceProcState = clientProcState; 16107 app.adjTarget = s.name; 16108 } 16109 } 16110 if ((cr.flags&Context.BIND_TREAT_LIKE_ACTIVITY) != 0) { 16111 app.treatLikeActivity = true; 16112 } 16113 final ActivityRecord a = cr.activity; 16114 if ((cr.flags&Context.BIND_ADJUST_WITH_ACTIVITY) != 0) { 16115 if (a != null && adj > ProcessList.FOREGROUND_APP_ADJ && 16116 (a.visible || a.state == ActivityState.RESUMED 16117 || a.state == ActivityState.PAUSING)) { 16118 adj = ProcessList.FOREGROUND_APP_ADJ; 16119 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 16120 schedGroup = Process.THREAD_GROUP_DEFAULT; 16121 } 16122 app.cached = false; 16123 app.adjType = "service"; 16124 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 16125 .REASON_SERVICE_IN_USE; 16126 app.adjSource = a; 16127 app.adjSourceProcState = procState; 16128 app.adjTarget = s.name; 16129 } 16130 } 16131 } 16132 } 16133 } 16134 16135 for (int provi = app.pubProviders.size()-1; 16136 provi >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 16137 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16138 || procState > ActivityManager.PROCESS_STATE_TOP); 16139 provi--) { 16140 ContentProviderRecord cpr = app.pubProviders.valueAt(provi); 16141 for (int i = cpr.connections.size()-1; 16142 i >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 16143 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16144 || procState > ActivityManager.PROCESS_STATE_TOP); 16145 i--) { 16146 ContentProviderConnection conn = cpr.connections.get(i); 16147 ProcessRecord client = conn.client; 16148 if (client == app) { 16149 // Being our own client is not interesting. 16150 continue; 16151 } 16152 int clientAdj = computeOomAdjLocked(client, cachedAdj, TOP_APP, doingAll, now); 16153 int clientProcState = client.curProcState; 16154 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 16155 // If the other app is cached for any reason, for purposes here 16156 // we are going to consider it empty. 16157 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16158 } 16159 if (adj > clientAdj) { 16160 if (app.hasShownUi && app != mHomeProcess 16161 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16162 app.adjType = "cch-ui-provider"; 16163 } else { 16164 adj = clientAdj > ProcessList.FOREGROUND_APP_ADJ 16165 ? clientAdj : ProcessList.FOREGROUND_APP_ADJ; 16166 app.adjType = "provider"; 16167 } 16168 app.cached &= client.cached; 16169 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 16170 .REASON_PROVIDER_IN_USE; 16171 app.adjSource = client; 16172 app.adjSourceProcState = clientProcState; 16173 app.adjTarget = cpr.name; 16174 } 16175 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 16176 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 16177 // Special handling of clients who are in the top state. 16178 // We *may* want to consider this process to be in the 16179 // top state as well, but only if there is not another 16180 // reason for it to be running. Being on the top is a 16181 // special state, meaning you are specifically running 16182 // for the current top app. If the process is already 16183 // running in the background for some other reason, it 16184 // is more important to continue considering it to be 16185 // in the background state. 16186 mayBeTop = true; 16187 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16188 } else { 16189 // Special handling for above-top states (persistent 16190 // processes). These should not bring the current process 16191 // into the top state, since they are not on top. Instead 16192 // give them the best state after that. 16193 clientProcState = 16194 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16195 } 16196 } 16197 if (procState > clientProcState) { 16198 procState = clientProcState; 16199 } 16200 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 16201 schedGroup = Process.THREAD_GROUP_DEFAULT; 16202 } 16203 } 16204 // If the provider has external (non-framework) process 16205 // dependencies, ensure that its adjustment is at least 16206 // FOREGROUND_APP_ADJ. 16207 if (cpr.hasExternalProcessHandles()) { 16208 if (adj > ProcessList.FOREGROUND_APP_ADJ) { 16209 adj = ProcessList.FOREGROUND_APP_ADJ; 16210 schedGroup = Process.THREAD_GROUP_DEFAULT; 16211 app.cached = false; 16212 app.adjType = "provider"; 16213 app.adjTarget = cpr.name; 16214 } 16215 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) { 16216 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16217 } 16218 } 16219 } 16220 16221 if (mayBeTop && procState > ActivityManager.PROCESS_STATE_TOP) { 16222 // A client of one of our services or providers is in the top state. We 16223 // *may* want to be in the top state, but not if we are already running in 16224 // the background for some other reason. For the decision here, we are going 16225 // to pick out a few specific states that we want to remain in when a client 16226 // is top (states that tend to be longer-term) and otherwise allow it to go 16227 // to the top state. 16228 switch (procState) { 16229 case ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND: 16230 case ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND: 16231 case ActivityManager.PROCESS_STATE_SERVICE: 16232 // These all are longer-term states, so pull them up to the top 16233 // of the background states, but not all the way to the top state. 16234 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16235 break; 16236 default: 16237 // Otherwise, top is a better choice, so take it. 16238 procState = ActivityManager.PROCESS_STATE_TOP; 16239 break; 16240 } 16241 } 16242 16243 if (procState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 16244 if (app.hasClientActivities) { 16245 // This is a cached process, but with client activities. Mark it so. 16246 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT; 16247 app.adjType = "cch-client-act"; 16248 } else if (app.treatLikeActivity) { 16249 // This is a cached process, but somebody wants us to treat it like it has 16250 // an activity, okay! 16251 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 16252 app.adjType = "cch-as-act"; 16253 } 16254 } 16255 16256 if (adj == ProcessList.SERVICE_ADJ) { 16257 if (doingAll) { 16258 app.serviceb = mNewNumAServiceProcs > (mNumServiceProcs/3); 16259 mNewNumServiceProcs++; 16260 //Slog.i(TAG, "ADJ " + app + " serviceb=" + app.serviceb); 16261 if (!app.serviceb) { 16262 // This service isn't far enough down on the LRU list to 16263 // normally be a B service, but if we are low on RAM and it 16264 // is large we want to force it down since we would prefer to 16265 // keep launcher over it. 16266 if (mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 16267 && app.lastPss >= mProcessList.getCachedRestoreThresholdKb()) { 16268 app.serviceHighRam = true; 16269 app.serviceb = true; 16270 //Slog.i(TAG, "ADJ " + app + " high ram!"); 16271 } else { 16272 mNewNumAServiceProcs++; 16273 //Slog.i(TAG, "ADJ " + app + " not high ram!"); 16274 } 16275 } else { 16276 app.serviceHighRam = false; 16277 } 16278 } 16279 if (app.serviceb) { 16280 adj = ProcessList.SERVICE_B_ADJ; 16281 } 16282 } 16283 16284 app.curRawAdj = adj; 16285 16286 //Slog.i(TAG, "OOM ADJ " + app + ": pid=" + app.pid + 16287 // " adj=" + adj + " curAdj=" + app.curAdj + " maxAdj=" + app.maxAdj); 16288 if (adj > app.maxAdj) { 16289 adj = app.maxAdj; 16290 if (app.maxAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 16291 schedGroup = Process.THREAD_GROUP_DEFAULT; 16292 } 16293 } 16294 16295 // Do final modification to adj. Everything we do between here and applying 16296 // the final setAdj must be done in this function, because we will also use 16297 // it when computing the final cached adj later. Note that we don't need to 16298 // worry about this for max adj above, since max adj will always be used to 16299 // keep it out of the cached vaues. 16300 app.curAdj = app.modifyRawOomAdj(adj); 16301 app.curSchedGroup = schedGroup; 16302 app.curProcState = procState; 16303 app.foregroundActivities = foregroundActivities; 16304 16305 return app.curRawAdj; 16306 } 16307 16308 /** 16309 * Schedule PSS collection of a process. 16310 */ 16311 void requestPssLocked(ProcessRecord proc, int procState) { 16312 if (mPendingPssProcesses.contains(proc)) { 16313 return; 16314 } 16315 if (mPendingPssProcesses.size() == 0) { 16316 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 16317 } 16318 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of: " + proc); 16319 proc.pssProcState = procState; 16320 mPendingPssProcesses.add(proc); 16321 } 16322 16323 /** 16324 * Schedule PSS collection of all processes. 16325 */ 16326 void requestPssAllProcsLocked(long now, boolean always, boolean memLowered) { 16327 if (!always) { 16328 if (now < (mLastFullPssTime + 16329 (memLowered ? FULL_PSS_LOWERED_INTERVAL : FULL_PSS_MIN_INTERVAL))) { 16330 return; 16331 } 16332 } 16333 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of all procs! memLowered=" + memLowered); 16334 mLastFullPssTime = now; 16335 mFullPssPending = true; 16336 mPendingPssProcesses.ensureCapacity(mLruProcesses.size()); 16337 mPendingPssProcesses.clear(); 16338 for (int i=mLruProcesses.size()-1; i>=0; i--) { 16339 ProcessRecord app = mLruProcesses.get(i); 16340 if (memLowered || now > (app.lastStateTime+ProcessList.PSS_ALL_INTERVAL)) { 16341 app.pssProcState = app.setProcState; 16342 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 16343 isSleeping(), now); 16344 mPendingPssProcesses.add(app); 16345 } 16346 } 16347 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 16348 } 16349 16350 /** 16351 * Ask a given process to GC right now. 16352 */ 16353 final void performAppGcLocked(ProcessRecord app) { 16354 try { 16355 app.lastRequestedGc = SystemClock.uptimeMillis(); 16356 if (app.thread != null) { 16357 if (app.reportLowMemory) { 16358 app.reportLowMemory = false; 16359 app.thread.scheduleLowMemory(); 16360 } else { 16361 app.thread.processInBackground(); 16362 } 16363 } 16364 } catch (Exception e) { 16365 // whatever. 16366 } 16367 } 16368 16369 /** 16370 * Returns true if things are idle enough to perform GCs. 16371 */ 16372 private final boolean canGcNowLocked() { 16373 boolean processingBroadcasts = false; 16374 for (BroadcastQueue q : mBroadcastQueues) { 16375 if (q.mParallelBroadcasts.size() != 0 || q.mOrderedBroadcasts.size() != 0) { 16376 processingBroadcasts = true; 16377 } 16378 } 16379 return !processingBroadcasts 16380 && (isSleeping() || mStackSupervisor.allResumedActivitiesIdle()); 16381 } 16382 16383 /** 16384 * Perform GCs on all processes that are waiting for it, but only 16385 * if things are idle. 16386 */ 16387 final void performAppGcsLocked() { 16388 final int N = mProcessesToGc.size(); 16389 if (N <= 0) { 16390 return; 16391 } 16392 if (canGcNowLocked()) { 16393 while (mProcessesToGc.size() > 0) { 16394 ProcessRecord proc = mProcessesToGc.remove(0); 16395 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ || proc.reportLowMemory) { 16396 if ((proc.lastRequestedGc+GC_MIN_INTERVAL) 16397 <= SystemClock.uptimeMillis()) { 16398 // To avoid spamming the system, we will GC processes one 16399 // at a time, waiting a few seconds between each. 16400 performAppGcLocked(proc); 16401 scheduleAppGcsLocked(); 16402 return; 16403 } else { 16404 // It hasn't been long enough since we last GCed this 16405 // process... put it in the list to wait for its time. 16406 addProcessToGcListLocked(proc); 16407 break; 16408 } 16409 } 16410 } 16411 16412 scheduleAppGcsLocked(); 16413 } 16414 } 16415 16416 /** 16417 * If all looks good, perform GCs on all processes waiting for them. 16418 */ 16419 final void performAppGcsIfAppropriateLocked() { 16420 if (canGcNowLocked()) { 16421 performAppGcsLocked(); 16422 return; 16423 } 16424 // Still not idle, wait some more. 16425 scheduleAppGcsLocked(); 16426 } 16427 16428 /** 16429 * Schedule the execution of all pending app GCs. 16430 */ 16431 final void scheduleAppGcsLocked() { 16432 mHandler.removeMessages(GC_BACKGROUND_PROCESSES_MSG); 16433 16434 if (mProcessesToGc.size() > 0) { 16435 // Schedule a GC for the time to the next process. 16436 ProcessRecord proc = mProcessesToGc.get(0); 16437 Message msg = mHandler.obtainMessage(GC_BACKGROUND_PROCESSES_MSG); 16438 16439 long when = proc.lastRequestedGc + GC_MIN_INTERVAL; 16440 long now = SystemClock.uptimeMillis(); 16441 if (when < (now+GC_TIMEOUT)) { 16442 when = now + GC_TIMEOUT; 16443 } 16444 mHandler.sendMessageAtTime(msg, when); 16445 } 16446 } 16447 16448 /** 16449 * Add a process to the array of processes waiting to be GCed. Keeps the 16450 * list in sorted order by the last GC time. The process can't already be 16451 * on the list. 16452 */ 16453 final void addProcessToGcListLocked(ProcessRecord proc) { 16454 boolean added = false; 16455 for (int i=mProcessesToGc.size()-1; i>=0; i--) { 16456 if (mProcessesToGc.get(i).lastRequestedGc < 16457 proc.lastRequestedGc) { 16458 added = true; 16459 mProcessesToGc.add(i+1, proc); 16460 break; 16461 } 16462 } 16463 if (!added) { 16464 mProcessesToGc.add(0, proc); 16465 } 16466 } 16467 16468 /** 16469 * Set up to ask a process to GC itself. This will either do it 16470 * immediately, or put it on the list of processes to gc the next 16471 * time things are idle. 16472 */ 16473 final void scheduleAppGcLocked(ProcessRecord app) { 16474 long now = SystemClock.uptimeMillis(); 16475 if ((app.lastRequestedGc+GC_MIN_INTERVAL) > now) { 16476 return; 16477 } 16478 if (!mProcessesToGc.contains(app)) { 16479 addProcessToGcListLocked(app); 16480 scheduleAppGcsLocked(); 16481 } 16482 } 16483 16484 final void checkExcessivePowerUsageLocked(boolean doKills) { 16485 updateCpuStatsNow(); 16486 16487 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 16488 boolean doWakeKills = doKills; 16489 boolean doCpuKills = doKills; 16490 if (mLastPowerCheckRealtime == 0) { 16491 doWakeKills = false; 16492 } 16493 if (mLastPowerCheckUptime == 0) { 16494 doCpuKills = false; 16495 } 16496 if (stats.isScreenOn()) { 16497 doWakeKills = false; 16498 } 16499 final long curRealtime = SystemClock.elapsedRealtime(); 16500 final long realtimeSince = curRealtime - mLastPowerCheckRealtime; 16501 final long curUptime = SystemClock.uptimeMillis(); 16502 final long uptimeSince = curUptime - mLastPowerCheckUptime; 16503 mLastPowerCheckRealtime = curRealtime; 16504 mLastPowerCheckUptime = curUptime; 16505 if (realtimeSince < WAKE_LOCK_MIN_CHECK_DURATION) { 16506 doWakeKills = false; 16507 } 16508 if (uptimeSince < CPU_MIN_CHECK_DURATION) { 16509 doCpuKills = false; 16510 } 16511 int i = mLruProcesses.size(); 16512 while (i > 0) { 16513 i--; 16514 ProcessRecord app = mLruProcesses.get(i); 16515 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 16516 long wtime; 16517 synchronized (stats) { 16518 wtime = stats.getProcessWakeTime(app.info.uid, 16519 app.pid, curRealtime); 16520 } 16521 long wtimeUsed = wtime - app.lastWakeTime; 16522 long cputimeUsed = app.curCpuTime - app.lastCpuTime; 16523 if (DEBUG_POWER) { 16524 StringBuilder sb = new StringBuilder(128); 16525 sb.append("Wake for "); 16526 app.toShortString(sb); 16527 sb.append(": over "); 16528 TimeUtils.formatDuration(realtimeSince, sb); 16529 sb.append(" used "); 16530 TimeUtils.formatDuration(wtimeUsed, sb); 16531 sb.append(" ("); 16532 sb.append((wtimeUsed*100)/realtimeSince); 16533 sb.append("%)"); 16534 Slog.i(TAG, sb.toString()); 16535 sb.setLength(0); 16536 sb.append("CPU for "); 16537 app.toShortString(sb); 16538 sb.append(": over "); 16539 TimeUtils.formatDuration(uptimeSince, sb); 16540 sb.append(" used "); 16541 TimeUtils.formatDuration(cputimeUsed, sb); 16542 sb.append(" ("); 16543 sb.append((cputimeUsed*100)/uptimeSince); 16544 sb.append("%)"); 16545 Slog.i(TAG, sb.toString()); 16546 } 16547 // If a process has held a wake lock for more 16548 // than 50% of the time during this period, 16549 // that sounds bad. Kill! 16550 if (doWakeKills && realtimeSince > 0 16551 && ((wtimeUsed*100)/realtimeSince) >= 50) { 16552 synchronized (stats) { 16553 stats.reportExcessiveWakeLocked(app.info.uid, app.processName, 16554 realtimeSince, wtimeUsed); 16555 } 16556 killUnneededProcessLocked(app, "excessive wake held " + wtimeUsed 16557 + " during " + realtimeSince); 16558 app.baseProcessTracker.reportExcessiveWake(app.pkgList); 16559 } else if (doCpuKills && uptimeSince > 0 16560 && ((cputimeUsed*100)/uptimeSince) >= 25) { 16561 synchronized (stats) { 16562 stats.reportExcessiveCpuLocked(app.info.uid, app.processName, 16563 uptimeSince, cputimeUsed); 16564 } 16565 killUnneededProcessLocked(app, "excessive cpu " + cputimeUsed 16566 + " during " + uptimeSince); 16567 app.baseProcessTracker.reportExcessiveCpu(app.pkgList); 16568 } else { 16569 app.lastWakeTime = wtime; 16570 app.lastCpuTime = app.curCpuTime; 16571 } 16572 } 16573 } 16574 } 16575 16576 private final boolean applyOomAdjLocked(ProcessRecord app, 16577 ProcessRecord TOP_APP, boolean doingAll, long now) { 16578 boolean success = true; 16579 16580 if (app.curRawAdj != app.setRawAdj) { 16581 app.setRawAdj = app.curRawAdj; 16582 } 16583 16584 int changes = 0; 16585 16586 if (app.curAdj != app.setAdj) { 16587 ProcessList.setOomAdj(app.pid, app.info.uid, app.curAdj); 16588 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v( 16589 TAG, "Set " + app.pid + " " + app.processName + 16590 " adj " + app.curAdj + ": " + app.adjType); 16591 app.setAdj = app.curAdj; 16592 } 16593 16594 if (app.setSchedGroup != app.curSchedGroup) { 16595 app.setSchedGroup = app.curSchedGroup; 16596 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16597 "Setting process group of " + app.processName 16598 + " to " + app.curSchedGroup); 16599 if (app.waitingToKill != null && 16600 app.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 16601 killUnneededProcessLocked(app, app.waitingToKill); 16602 success = false; 16603 } else { 16604 if (true) { 16605 long oldId = Binder.clearCallingIdentity(); 16606 try { 16607 Process.setProcessGroup(app.pid, app.curSchedGroup); 16608 } catch (Exception e) { 16609 Slog.w(TAG, "Failed setting process group of " + app.pid 16610 + " to " + app.curSchedGroup); 16611 e.printStackTrace(); 16612 } finally { 16613 Binder.restoreCallingIdentity(oldId); 16614 } 16615 } else { 16616 if (app.thread != null) { 16617 try { 16618 app.thread.setSchedulingGroup(app.curSchedGroup); 16619 } catch (RemoteException e) { 16620 } 16621 } 16622 } 16623 Process.setSwappiness(app.pid, 16624 app.curSchedGroup <= Process.THREAD_GROUP_BG_NONINTERACTIVE); 16625 } 16626 } 16627 if (app.repForegroundActivities != app.foregroundActivities) { 16628 app.repForegroundActivities = app.foregroundActivities; 16629 changes |= ProcessChangeItem.CHANGE_ACTIVITIES; 16630 } 16631 if (app.repProcState != app.curProcState) { 16632 app.repProcState = app.curProcState; 16633 changes |= ProcessChangeItem.CHANGE_PROCESS_STATE; 16634 if (app.thread != null) { 16635 try { 16636 if (false) { 16637 //RuntimeException h = new RuntimeException("here"); 16638 Slog.i(TAG, "Sending new process state " + app.repProcState 16639 + " to " + app /*, h*/); 16640 } 16641 app.thread.setProcessState(app.repProcState); 16642 } catch (RemoteException e) { 16643 } 16644 } 16645 } 16646 if (app.setProcState < 0 || ProcessList.procStatesDifferForMem(app.curProcState, 16647 app.setProcState)) { 16648 app.lastStateTime = now; 16649 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 16650 isSleeping(), now); 16651 if (DEBUG_PSS) Slog.d(TAG, "Process state change from " 16652 + ProcessList.makeProcStateString(app.setProcState) + " to " 16653 + ProcessList.makeProcStateString(app.curProcState) + " next pss in " 16654 + (app.nextPssTime-now) + ": " + app); 16655 } else { 16656 if (now > app.nextPssTime || (now > (app.lastPssTime+ProcessList.PSS_MAX_INTERVAL) 16657 && now > (app.lastStateTime+ProcessList.PSS_MIN_TIME_FROM_STATE_CHANGE))) { 16658 requestPssLocked(app, app.setProcState); 16659 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, false, 16660 isSleeping(), now); 16661 } else if (false && DEBUG_PSS) { 16662 Slog.d(TAG, "Not requesting PSS of " + app + ": next=" + (app.nextPssTime-now)); 16663 } 16664 } 16665 if (app.setProcState != app.curProcState) { 16666 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16667 "Proc state change of " + app.processName 16668 + " to " + app.curProcState); 16669 boolean setImportant = app.setProcState < ActivityManager.PROCESS_STATE_SERVICE; 16670 boolean curImportant = app.curProcState < ActivityManager.PROCESS_STATE_SERVICE; 16671 if (setImportant && !curImportant) { 16672 // This app is no longer something we consider important enough to allow to 16673 // use arbitrary amounts of battery power. Note 16674 // its current wake lock time to later know to kill it if 16675 // it is not behaving well. 16676 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 16677 synchronized (stats) { 16678 app.lastWakeTime = stats.getProcessWakeTime(app.info.uid, 16679 app.pid, SystemClock.elapsedRealtime()); 16680 } 16681 app.lastCpuTime = app.curCpuTime; 16682 16683 } 16684 app.setProcState = app.curProcState; 16685 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 16686 app.notCachedSinceIdle = false; 16687 } 16688 if (!doingAll) { 16689 setProcessTrackerStateLocked(app, mProcessStats.getMemFactorLocked(), now); 16690 } else { 16691 app.procStateChanged = true; 16692 } 16693 } 16694 16695 if (changes != 0) { 16696 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Changes in " + app + ": " + changes); 16697 int i = mPendingProcessChanges.size()-1; 16698 ProcessChangeItem item = null; 16699 while (i >= 0) { 16700 item = mPendingProcessChanges.get(i); 16701 if (item.pid == app.pid) { 16702 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Re-using existing item: " + item); 16703 break; 16704 } 16705 i--; 16706 } 16707 if (i < 0) { 16708 // No existing item in pending changes; need a new one. 16709 final int NA = mAvailProcessChanges.size(); 16710 if (NA > 0) { 16711 item = mAvailProcessChanges.remove(NA-1); 16712 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Retreiving available item: " + item); 16713 } else { 16714 item = new ProcessChangeItem(); 16715 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Allocating new item: " + item); 16716 } 16717 item.changes = 0; 16718 item.pid = app.pid; 16719 item.uid = app.info.uid; 16720 if (mPendingProcessChanges.size() == 0) { 16721 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, 16722 "*** Enqueueing dispatch processes changed!"); 16723 mHandler.obtainMessage(DISPATCH_PROCESSES_CHANGED).sendToTarget(); 16724 } 16725 mPendingProcessChanges.add(item); 16726 } 16727 item.changes |= changes; 16728 item.processState = app.repProcState; 16729 item.foregroundActivities = app.repForegroundActivities; 16730 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Item " 16731 + Integer.toHexString(System.identityHashCode(item)) 16732 + " " + app.toShortString() + ": changes=" + item.changes 16733 + " procState=" + item.processState 16734 + " foreground=" + item.foregroundActivities 16735 + " type=" + app.adjType + " source=" + app.adjSource 16736 + " target=" + app.adjTarget); 16737 } 16738 16739 return success; 16740 } 16741 16742 private final void setProcessTrackerStateLocked(ProcessRecord proc, int memFactor, long now) { 16743 if (proc.thread != null) { 16744 if (proc.baseProcessTracker != null) { 16745 proc.baseProcessTracker.setState(proc.repProcState, memFactor, now, proc.pkgList); 16746 } 16747 if (proc.repProcState >= 0) { 16748 mBatteryStatsService.noteProcessState(proc.processName, proc.info.uid, 16749 proc.repProcState); 16750 } 16751 } 16752 } 16753 16754 private final boolean updateOomAdjLocked(ProcessRecord app, int cachedAdj, 16755 ProcessRecord TOP_APP, boolean doingAll, long now) { 16756 if (app.thread == null) { 16757 return false; 16758 } 16759 16760 computeOomAdjLocked(app, cachedAdj, TOP_APP, doingAll, now); 16761 16762 return applyOomAdjLocked(app, TOP_APP, doingAll, now); 16763 } 16764 16765 final void updateProcessForegroundLocked(ProcessRecord proc, boolean isForeground, 16766 boolean oomAdj) { 16767 if (isForeground != proc.foregroundServices) { 16768 proc.foregroundServices = isForeground; 16769 ArrayList<ProcessRecord> curProcs = mForegroundPackages.get(proc.info.packageName, 16770 proc.info.uid); 16771 if (isForeground) { 16772 if (curProcs == null) { 16773 curProcs = new ArrayList<ProcessRecord>(); 16774 mForegroundPackages.put(proc.info.packageName, proc.info.uid, curProcs); 16775 } 16776 if (!curProcs.contains(proc)) { 16777 curProcs.add(proc); 16778 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_FOREGROUND_START, 16779 proc.info.packageName, proc.info.uid); 16780 } 16781 } else { 16782 if (curProcs != null) { 16783 if (curProcs.remove(proc)) { 16784 mBatteryStatsService.noteEvent( 16785 BatteryStats.HistoryItem.EVENT_FOREGROUND_FINISH, 16786 proc.info.packageName, proc.info.uid); 16787 if (curProcs.size() <= 0) { 16788 mForegroundPackages.remove(proc.info.packageName, proc.info.uid); 16789 } 16790 } 16791 } 16792 } 16793 if (oomAdj) { 16794 updateOomAdjLocked(); 16795 } 16796 } 16797 } 16798 16799 private final ActivityRecord resumedAppLocked() { 16800 ActivityRecord act = mStackSupervisor.resumedAppLocked(); 16801 String pkg; 16802 int uid; 16803 if (act != null) { 16804 pkg = act.packageName; 16805 uid = act.info.applicationInfo.uid; 16806 } else { 16807 pkg = null; 16808 uid = -1; 16809 } 16810 // Has the UID or resumed package name changed? 16811 if (uid != mCurResumedUid || (pkg != mCurResumedPackage 16812 && (pkg == null || !pkg.equals(mCurResumedPackage)))) { 16813 if (mCurResumedPackage != null) { 16814 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_FINISH, 16815 mCurResumedPackage, mCurResumedUid); 16816 } 16817 mCurResumedPackage = pkg; 16818 mCurResumedUid = uid; 16819 if (mCurResumedPackage != null) { 16820 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_START, 16821 mCurResumedPackage, mCurResumedUid); 16822 } 16823 } 16824 return act; 16825 } 16826 16827 final boolean updateOomAdjLocked(ProcessRecord app) { 16828 final ActivityRecord TOP_ACT = resumedAppLocked(); 16829 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 16830 final boolean wasCached = app.cached; 16831 16832 mAdjSeq++; 16833 16834 // This is the desired cached adjusment we want to tell it to use. 16835 // If our app is currently cached, we know it, and that is it. Otherwise, 16836 // we don't know it yet, and it needs to now be cached we will then 16837 // need to do a complete oom adj. 16838 final int cachedAdj = app.curRawAdj >= ProcessList.CACHED_APP_MIN_ADJ 16839 ? app.curRawAdj : ProcessList.UNKNOWN_ADJ; 16840 boolean success = updateOomAdjLocked(app, cachedAdj, TOP_APP, false, 16841 SystemClock.uptimeMillis()); 16842 if (wasCached != app.cached || app.curRawAdj == ProcessList.UNKNOWN_ADJ) { 16843 // Changed to/from cached state, so apps after it in the LRU 16844 // list may also be changed. 16845 updateOomAdjLocked(); 16846 } 16847 return success; 16848 } 16849 16850 final void updateOomAdjLocked() { 16851 final ActivityRecord TOP_ACT = resumedAppLocked(); 16852 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 16853 final long now = SystemClock.uptimeMillis(); 16854 final long oldTime = now - ProcessList.MAX_EMPTY_TIME; 16855 final int N = mLruProcesses.size(); 16856 16857 if (false) { 16858 RuntimeException e = new RuntimeException(); 16859 e.fillInStackTrace(); 16860 Slog.i(TAG, "updateOomAdj: top=" + TOP_ACT, e); 16861 } 16862 16863 mAdjSeq++; 16864 mNewNumServiceProcs = 0; 16865 mNewNumAServiceProcs = 0; 16866 16867 final int emptyProcessLimit; 16868 final int cachedProcessLimit; 16869 if (mProcessLimit <= 0) { 16870 emptyProcessLimit = cachedProcessLimit = 0; 16871 } else if (mProcessLimit == 1) { 16872 emptyProcessLimit = 1; 16873 cachedProcessLimit = 0; 16874 } else { 16875 emptyProcessLimit = ProcessList.computeEmptyProcessLimit(mProcessLimit); 16876 cachedProcessLimit = mProcessLimit - emptyProcessLimit; 16877 } 16878 16879 // Let's determine how many processes we have running vs. 16880 // how many slots we have for background processes; we may want 16881 // to put multiple processes in a slot of there are enough of 16882 // them. 16883 int numSlots = (ProcessList.CACHED_APP_MAX_ADJ 16884 - ProcessList.CACHED_APP_MIN_ADJ + 1) / 2; 16885 int numEmptyProcs = N - mNumNonCachedProcs - mNumCachedHiddenProcs; 16886 if (numEmptyProcs > cachedProcessLimit) { 16887 // If there are more empty processes than our limit on cached 16888 // processes, then use the cached process limit for the factor. 16889 // This ensures that the really old empty processes get pushed 16890 // down to the bottom, so if we are running low on memory we will 16891 // have a better chance at keeping around more cached processes 16892 // instead of a gazillion empty processes. 16893 numEmptyProcs = cachedProcessLimit; 16894 } 16895 int emptyFactor = numEmptyProcs/numSlots; 16896 if (emptyFactor < 1) emptyFactor = 1; 16897 int cachedFactor = (mNumCachedHiddenProcs > 0 ? mNumCachedHiddenProcs : 1)/numSlots; 16898 if (cachedFactor < 1) cachedFactor = 1; 16899 int stepCached = 0; 16900 int stepEmpty = 0; 16901 int numCached = 0; 16902 int numEmpty = 0; 16903 int numTrimming = 0; 16904 16905 mNumNonCachedProcs = 0; 16906 mNumCachedHiddenProcs = 0; 16907 16908 // First update the OOM adjustment for each of the 16909 // application processes based on their current state. 16910 int curCachedAdj = ProcessList.CACHED_APP_MIN_ADJ; 16911 int nextCachedAdj = curCachedAdj+1; 16912 int curEmptyAdj = ProcessList.CACHED_APP_MIN_ADJ; 16913 int nextEmptyAdj = curEmptyAdj+2; 16914 for (int i=N-1; i>=0; i--) { 16915 ProcessRecord app = mLruProcesses.get(i); 16916 if (!app.killedByAm && app.thread != null) { 16917 app.procStateChanged = false; 16918 computeOomAdjLocked(app, ProcessList.UNKNOWN_ADJ, TOP_APP, true, now); 16919 16920 // If we haven't yet assigned the final cached adj 16921 // to the process, do that now. 16922 if (app.curAdj >= ProcessList.UNKNOWN_ADJ) { 16923 switch (app.curProcState) { 16924 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 16925 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 16926 // This process is a cached process holding activities... 16927 // assign it the next cached value for that type, and then 16928 // step that cached level. 16929 app.curRawAdj = curCachedAdj; 16930 app.curAdj = app.modifyRawOomAdj(curCachedAdj); 16931 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning activity LRU #" + i 16932 + " adj: " + app.curAdj + " (curCachedAdj=" + curCachedAdj 16933 + ")"); 16934 if (curCachedAdj != nextCachedAdj) { 16935 stepCached++; 16936 if (stepCached >= cachedFactor) { 16937 stepCached = 0; 16938 curCachedAdj = nextCachedAdj; 16939 nextCachedAdj += 2; 16940 if (nextCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) { 16941 nextCachedAdj = ProcessList.CACHED_APP_MAX_ADJ; 16942 } 16943 } 16944 } 16945 break; 16946 default: 16947 // For everything else, assign next empty cached process 16948 // level and bump that up. Note that this means that 16949 // long-running services that have dropped down to the 16950 // cached level will be treated as empty (since their process 16951 // state is still as a service), which is what we want. 16952 app.curRawAdj = curEmptyAdj; 16953 app.curAdj = app.modifyRawOomAdj(curEmptyAdj); 16954 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning empty LRU #" + i 16955 + " adj: " + app.curAdj + " (curEmptyAdj=" + curEmptyAdj 16956 + ")"); 16957 if (curEmptyAdj != nextEmptyAdj) { 16958 stepEmpty++; 16959 if (stepEmpty >= emptyFactor) { 16960 stepEmpty = 0; 16961 curEmptyAdj = nextEmptyAdj; 16962 nextEmptyAdj += 2; 16963 if (nextEmptyAdj > ProcessList.CACHED_APP_MAX_ADJ) { 16964 nextEmptyAdj = ProcessList.CACHED_APP_MAX_ADJ; 16965 } 16966 } 16967 } 16968 break; 16969 } 16970 } 16971 16972 applyOomAdjLocked(app, TOP_APP, true, now); 16973 16974 // Count the number of process types. 16975 switch (app.curProcState) { 16976 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 16977 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 16978 mNumCachedHiddenProcs++; 16979 numCached++; 16980 if (numCached > cachedProcessLimit) { 16981 killUnneededProcessLocked(app, "cached #" + numCached); 16982 } 16983 break; 16984 case ActivityManager.PROCESS_STATE_CACHED_EMPTY: 16985 if (numEmpty > ProcessList.TRIM_EMPTY_APPS 16986 && app.lastActivityTime < oldTime) { 16987 killUnneededProcessLocked(app, "empty for " 16988 + ((oldTime + ProcessList.MAX_EMPTY_TIME - app.lastActivityTime) 16989 / 1000) + "s"); 16990 } else { 16991 numEmpty++; 16992 if (numEmpty > emptyProcessLimit) { 16993 killUnneededProcessLocked(app, "empty #" + numEmpty); 16994 } 16995 } 16996 break; 16997 default: 16998 mNumNonCachedProcs++; 16999 break; 17000 } 17001 17002 if (app.isolated && app.services.size() <= 0) { 17003 // If this is an isolated process, and there are no 17004 // services running in it, then the process is no longer 17005 // needed. We agressively kill these because we can by 17006 // definition not re-use the same process again, and it is 17007 // good to avoid having whatever code was running in them 17008 // left sitting around after no longer needed. 17009 killUnneededProcessLocked(app, "isolated not needed"); 17010 } 17011 17012 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 17013 && !app.killedByAm) { 17014 numTrimming++; 17015 } 17016 } 17017 } 17018 17019 mNumServiceProcs = mNewNumServiceProcs; 17020 17021 // Now determine the memory trimming level of background processes. 17022 // Unfortunately we need to start at the back of the list to do this 17023 // properly. We only do this if the number of background apps we 17024 // are managing to keep around is less than half the maximum we desire; 17025 // if we are keeping a good number around, we'll let them use whatever 17026 // memory they want. 17027 final int numCachedAndEmpty = numCached + numEmpty; 17028 int memFactor; 17029 if (numCached <= ProcessList.TRIM_CACHED_APPS 17030 && numEmpty <= ProcessList.TRIM_EMPTY_APPS) { 17031 if (numCachedAndEmpty <= ProcessList.TRIM_CRITICAL_THRESHOLD) { 17032 memFactor = ProcessStats.ADJ_MEM_FACTOR_CRITICAL; 17033 } else if (numCachedAndEmpty <= ProcessList.TRIM_LOW_THRESHOLD) { 17034 memFactor = ProcessStats.ADJ_MEM_FACTOR_LOW; 17035 } else { 17036 memFactor = ProcessStats.ADJ_MEM_FACTOR_MODERATE; 17037 } 17038 } else { 17039 memFactor = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 17040 } 17041 // We always allow the memory level to go up (better). We only allow it to go 17042 // down if we are in a state where that is allowed, *and* the total number of processes 17043 // has gone down since last time. 17044 if (DEBUG_OOM_ADJ) Slog.d(TAG, "oom: memFactor=" + memFactor + " last=" + mLastMemoryLevel 17045 + " allowLow=" + mAllowLowerMemLevel + " numProcs=" + mLruProcesses.size() 17046 + " last=" + mLastNumProcesses); 17047 if (memFactor > mLastMemoryLevel) { 17048 if (!mAllowLowerMemLevel || mLruProcesses.size() >= mLastNumProcesses) { 17049 memFactor = mLastMemoryLevel; 17050 if (DEBUG_OOM_ADJ) Slog.d(TAG, "Keeping last mem factor!"); 17051 } 17052 } 17053 mLastMemoryLevel = memFactor; 17054 mLastNumProcesses = mLruProcesses.size(); 17055 boolean allChanged = mProcessStats.setMemFactorLocked(memFactor, !isSleeping(), now); 17056 final int trackerMemFactor = mProcessStats.getMemFactorLocked(); 17057 if (memFactor != ProcessStats.ADJ_MEM_FACTOR_NORMAL) { 17058 if (mLowRamStartTime == 0) { 17059 mLowRamStartTime = now; 17060 } 17061 int step = 0; 17062 int fgTrimLevel; 17063 switch (memFactor) { 17064 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 17065 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_CRITICAL; 17066 break; 17067 case ProcessStats.ADJ_MEM_FACTOR_LOW: 17068 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_LOW; 17069 break; 17070 default: 17071 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_MODERATE; 17072 break; 17073 } 17074 int factor = numTrimming/3; 17075 int minFactor = 2; 17076 if (mHomeProcess != null) minFactor++; 17077 if (mPreviousProcess != null) minFactor++; 17078 if (factor < minFactor) factor = minFactor; 17079 int curLevel = ComponentCallbacks2.TRIM_MEMORY_COMPLETE; 17080 for (int i=N-1; i>=0; i--) { 17081 ProcessRecord app = mLruProcesses.get(i); 17082 if (allChanged || app.procStateChanged) { 17083 setProcessTrackerStateLocked(app, trackerMemFactor, now); 17084 app.procStateChanged = false; 17085 } 17086 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 17087 && !app.killedByAm) { 17088 if (app.trimMemoryLevel < curLevel && app.thread != null) { 17089 try { 17090 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17091 "Trimming memory of " + app.processName 17092 + " to " + curLevel); 17093 app.thread.scheduleTrimMemory(curLevel); 17094 } catch (RemoteException e) { 17095 } 17096 if (false) { 17097 // For now we won't do this; our memory trimming seems 17098 // to be good enough at this point that destroying 17099 // activities causes more harm than good. 17100 if (curLevel >= ComponentCallbacks2.TRIM_MEMORY_COMPLETE 17101 && app != mHomeProcess && app != mPreviousProcess) { 17102 // Need to do this on its own message because the stack may not 17103 // be in a consistent state at this point. 17104 // For these apps we will also finish their activities 17105 // to help them free memory. 17106 mStackSupervisor.scheduleDestroyAllActivities(app, "trim"); 17107 } 17108 } 17109 } 17110 app.trimMemoryLevel = curLevel; 17111 step++; 17112 if (step >= factor) { 17113 step = 0; 17114 switch (curLevel) { 17115 case ComponentCallbacks2.TRIM_MEMORY_COMPLETE: 17116 curLevel = ComponentCallbacks2.TRIM_MEMORY_MODERATE; 17117 break; 17118 case ComponentCallbacks2.TRIM_MEMORY_MODERATE: 17119 curLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 17120 break; 17121 } 17122 } 17123 } else if (app.curProcState == ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 17124 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_BACKGROUND 17125 && app.thread != null) { 17126 try { 17127 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17128 "Trimming memory of heavy-weight " + app.processName 17129 + " to " + ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 17130 app.thread.scheduleTrimMemory( 17131 ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 17132 } catch (RemoteException e) { 17133 } 17134 } 17135 app.trimMemoryLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 17136 } else { 17137 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 17138 || app.systemNoUi) && app.pendingUiClean) { 17139 // If this application is now in the background and it 17140 // had done UI, then give it the special trim level to 17141 // have it free UI resources. 17142 final int level = ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN; 17143 if (app.trimMemoryLevel < level && app.thread != null) { 17144 try { 17145 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17146 "Trimming memory of bg-ui " + app.processName 17147 + " to " + level); 17148 app.thread.scheduleTrimMemory(level); 17149 } catch (RemoteException e) { 17150 } 17151 } 17152 app.pendingUiClean = false; 17153 } 17154 if (app.trimMemoryLevel < fgTrimLevel && app.thread != null) { 17155 try { 17156 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17157 "Trimming memory of fg " + app.processName 17158 + " to " + fgTrimLevel); 17159 app.thread.scheduleTrimMemory(fgTrimLevel); 17160 } catch (RemoteException e) { 17161 } 17162 } 17163 app.trimMemoryLevel = fgTrimLevel; 17164 } 17165 } 17166 } else { 17167 if (mLowRamStartTime != 0) { 17168 mLowRamTimeSinceLastIdle += now - mLowRamStartTime; 17169 mLowRamStartTime = 0; 17170 } 17171 for (int i=N-1; i>=0; i--) { 17172 ProcessRecord app = mLruProcesses.get(i); 17173 if (allChanged || app.procStateChanged) { 17174 setProcessTrackerStateLocked(app, trackerMemFactor, now); 17175 app.procStateChanged = false; 17176 } 17177 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 17178 || app.systemNoUi) && app.pendingUiClean) { 17179 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN 17180 && app.thread != null) { 17181 try { 17182 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17183 "Trimming memory of ui hidden " + app.processName 17184 + " to " + ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 17185 app.thread.scheduleTrimMemory( 17186 ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 17187 } catch (RemoteException e) { 17188 } 17189 } 17190 app.pendingUiClean = false; 17191 } 17192 app.trimMemoryLevel = 0; 17193 } 17194 } 17195 17196 if (mAlwaysFinishActivities) { 17197 // Need to do this on its own message because the stack may not 17198 // be in a consistent state at this point. 17199 mStackSupervisor.scheduleDestroyAllActivities(null, "always-finish"); 17200 } 17201 17202 if (allChanged) { 17203 requestPssAllProcsLocked(now, false, mProcessStats.isMemFactorLowered()); 17204 } 17205 17206 if (mProcessStats.shouldWriteNowLocked(now)) { 17207 mHandler.post(new Runnable() { 17208 @Override public void run() { 17209 synchronized (ActivityManagerService.this) { 17210 mProcessStats.writeStateAsyncLocked(); 17211 } 17212 } 17213 }); 17214 } 17215 17216 if (DEBUG_OOM_ADJ) { 17217 Slog.d(TAG, "Did OOM ADJ in " + (SystemClock.uptimeMillis()-now) + "ms"); 17218 } 17219 } 17220 17221 final void trimApplications() { 17222 synchronized (this) { 17223 int i; 17224 17225 // First remove any unused application processes whose package 17226 // has been removed. 17227 for (i=mRemovedProcesses.size()-1; i>=0; i--) { 17228 final ProcessRecord app = mRemovedProcesses.get(i); 17229 if (app.activities.size() == 0 17230 && app.curReceiver == null && app.services.size() == 0) { 17231 Slog.i( 17232 TAG, "Exiting empty application process " 17233 + app.processName + " (" 17234 + (app.thread != null ? app.thread.asBinder() : null) 17235 + ")\n"); 17236 if (app.pid > 0 && app.pid != MY_PID) { 17237 EventLog.writeEvent(EventLogTags.AM_KILL, app.userId, app.pid, 17238 app.processName, app.setAdj, "empty"); 17239 app.killedByAm = true; 17240 Process.killProcessQuiet(app.pid); 17241 Process.killProcessGroup(app.info.uid, app.pid); 17242 } else { 17243 try { 17244 app.thread.scheduleExit(); 17245 } catch (Exception e) { 17246 // Ignore exceptions. 17247 } 17248 } 17249 cleanUpApplicationRecordLocked(app, false, true, -1); 17250 mRemovedProcesses.remove(i); 17251 17252 if (app.persistent) { 17253 addAppLocked(app.info, false, null /* ABI override */); 17254 } 17255 } 17256 } 17257 17258 // Now update the oom adj for all processes. 17259 updateOomAdjLocked(); 17260 } 17261 } 17262 17263 /** This method sends the specified signal to each of the persistent apps */ 17264 public void signalPersistentProcesses(int sig) throws RemoteException { 17265 if (sig != Process.SIGNAL_USR1) { 17266 throw new SecurityException("Only SIGNAL_USR1 is allowed"); 17267 } 17268 17269 synchronized (this) { 17270 if (checkCallingPermission(android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES) 17271 != PackageManager.PERMISSION_GRANTED) { 17272 throw new SecurityException("Requires permission " 17273 + android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES); 17274 } 17275 17276 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 17277 ProcessRecord r = mLruProcesses.get(i); 17278 if (r.thread != null && r.persistent) { 17279 Process.sendSignal(r.pid, sig); 17280 } 17281 } 17282 } 17283 } 17284 17285 private void stopProfilerLocked(ProcessRecord proc, String path, int profileType) { 17286 if (proc == null || proc == mProfileProc) { 17287 proc = mProfileProc; 17288 path = mProfileFile; 17289 profileType = mProfileType; 17290 clearProfilerLocked(); 17291 } 17292 if (proc == null) { 17293 return; 17294 } 17295 try { 17296 proc.thread.profilerControl(false, path, null, profileType); 17297 } catch (RemoteException e) { 17298 throw new IllegalStateException("Process disappeared"); 17299 } 17300 } 17301 17302 private void clearProfilerLocked() { 17303 if (mProfileFd != null) { 17304 try { 17305 mProfileFd.close(); 17306 } catch (IOException e) { 17307 } 17308 } 17309 mProfileApp = null; 17310 mProfileProc = null; 17311 mProfileFile = null; 17312 mProfileType = 0; 17313 mAutoStopProfiler = false; 17314 } 17315 17316 public boolean profileControl(String process, int userId, boolean start, 17317 String path, ParcelFileDescriptor fd, int profileType) throws RemoteException { 17318 17319 try { 17320 synchronized (this) { 17321 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 17322 // its own permission. 17323 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 17324 != PackageManager.PERMISSION_GRANTED) { 17325 throw new SecurityException("Requires permission " 17326 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 17327 } 17328 17329 if (start && fd == null) { 17330 throw new IllegalArgumentException("null fd"); 17331 } 17332 17333 ProcessRecord proc = null; 17334 if (process != null) { 17335 proc = findProcessLocked(process, userId, "profileControl"); 17336 } 17337 17338 if (start && (proc == null || proc.thread == null)) { 17339 throw new IllegalArgumentException("Unknown process: " + process); 17340 } 17341 17342 if (start) { 17343 stopProfilerLocked(null, null, 0); 17344 setProfileApp(proc.info, proc.processName, path, fd, false); 17345 mProfileProc = proc; 17346 mProfileType = profileType; 17347 try { 17348 fd = fd.dup(); 17349 } catch (IOException e) { 17350 fd = null; 17351 } 17352 proc.thread.profilerControl(start, path, fd, profileType); 17353 fd = null; 17354 mProfileFd = null; 17355 } else { 17356 stopProfilerLocked(proc, path, profileType); 17357 if (fd != null) { 17358 try { 17359 fd.close(); 17360 } catch (IOException e) { 17361 } 17362 } 17363 } 17364 17365 return true; 17366 } 17367 } catch (RemoteException e) { 17368 throw new IllegalStateException("Process disappeared"); 17369 } finally { 17370 if (fd != null) { 17371 try { 17372 fd.close(); 17373 } catch (IOException e) { 17374 } 17375 } 17376 } 17377 } 17378 17379 private ProcessRecord findProcessLocked(String process, int userId, String callName) { 17380 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 17381 userId, true, ALLOW_FULL_ONLY, callName, null); 17382 ProcessRecord proc = null; 17383 try { 17384 int pid = Integer.parseInt(process); 17385 synchronized (mPidsSelfLocked) { 17386 proc = mPidsSelfLocked.get(pid); 17387 } 17388 } catch (NumberFormatException e) { 17389 } 17390 17391 if (proc == null) { 17392 ArrayMap<String, SparseArray<ProcessRecord>> all 17393 = mProcessNames.getMap(); 17394 SparseArray<ProcessRecord> procs = all.get(process); 17395 if (procs != null && procs.size() > 0) { 17396 proc = procs.valueAt(0); 17397 if (userId != UserHandle.USER_ALL && proc.userId != userId) { 17398 for (int i=1; i<procs.size(); i++) { 17399 ProcessRecord thisProc = procs.valueAt(i); 17400 if (thisProc.userId == userId) { 17401 proc = thisProc; 17402 break; 17403 } 17404 } 17405 } 17406 } 17407 } 17408 17409 return proc; 17410 } 17411 17412 public boolean dumpHeap(String process, int userId, boolean managed, 17413 String path, ParcelFileDescriptor fd) throws RemoteException { 17414 17415 try { 17416 synchronized (this) { 17417 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 17418 // its own permission (same as profileControl). 17419 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 17420 != PackageManager.PERMISSION_GRANTED) { 17421 throw new SecurityException("Requires permission " 17422 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 17423 } 17424 17425 if (fd == null) { 17426 throw new IllegalArgumentException("null fd"); 17427 } 17428 17429 ProcessRecord proc = findProcessLocked(process, userId, "dumpHeap"); 17430 if (proc == null || proc.thread == null) { 17431 throw new IllegalArgumentException("Unknown process: " + process); 17432 } 17433 17434 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 17435 if (!isDebuggable) { 17436 if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 17437 throw new SecurityException("Process not debuggable: " + proc); 17438 } 17439 } 17440 17441 proc.thread.dumpHeap(managed, path, fd); 17442 fd = null; 17443 return true; 17444 } 17445 } catch (RemoteException e) { 17446 throw new IllegalStateException("Process disappeared"); 17447 } finally { 17448 if (fd != null) { 17449 try { 17450 fd.close(); 17451 } catch (IOException e) { 17452 } 17453 } 17454 } 17455 } 17456 17457 /** In this method we try to acquire our lock to make sure that we have not deadlocked */ 17458 public void monitor() { 17459 synchronized (this) { } 17460 } 17461 17462 void onCoreSettingsChange(Bundle settings) { 17463 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 17464 ProcessRecord processRecord = mLruProcesses.get(i); 17465 try { 17466 if (processRecord.thread != null) { 17467 processRecord.thread.setCoreSettings(settings); 17468 } 17469 } catch (RemoteException re) { 17470 /* ignore */ 17471 } 17472 } 17473 } 17474 17475 // Multi-user methods 17476 17477 /** 17478 * Start user, if its not already running, but don't bring it to foreground. 17479 */ 17480 @Override 17481 public boolean startUserInBackground(final int userId) { 17482 return startUser(userId, /* foreground */ false); 17483 } 17484 17485 /** 17486 * Start user, if its not already running, and bring it to foreground. 17487 */ 17488 boolean startUserInForeground(final int userId, Dialog dlg) { 17489 boolean result = startUser(userId, /* foreground */ true); 17490 dlg.dismiss(); 17491 return result; 17492 } 17493 17494 /** 17495 * Refreshes the list of users related to the current user when either a 17496 * user switch happens or when a new related user is started in the 17497 * background. 17498 */ 17499 private void updateCurrentProfileIdsLocked() { 17500 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17501 mCurrentUserId, false /* enabledOnly */); 17502 int[] currentProfileIds = new int[profiles.size()]; // profiles will not be null 17503 for (int i = 0; i < currentProfileIds.length; i++) { 17504 currentProfileIds[i] = profiles.get(i).id; 17505 } 17506 mCurrentProfileIds = currentProfileIds; 17507 17508 synchronized (mUserProfileGroupIdsSelfLocked) { 17509 mUserProfileGroupIdsSelfLocked.clear(); 17510 final List<UserInfo> users = getUserManagerLocked().getUsers(false); 17511 for (int i = 0; i < users.size(); i++) { 17512 UserInfo user = users.get(i); 17513 if (user.profileGroupId != UserInfo.NO_PROFILE_GROUP_ID) { 17514 mUserProfileGroupIdsSelfLocked.put(user.id, user.profileGroupId); 17515 } 17516 } 17517 } 17518 } 17519 17520 private Set getProfileIdsLocked(int userId) { 17521 Set userIds = new HashSet<Integer>(); 17522 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17523 userId, false /* enabledOnly */); 17524 for (UserInfo user : profiles) { 17525 userIds.add(Integer.valueOf(user.id)); 17526 } 17527 return userIds; 17528 } 17529 17530 @Override 17531 public boolean switchUser(final int userId) { 17532 String userName; 17533 synchronized (this) { 17534 UserInfo userInfo = getUserManagerLocked().getUserInfo(userId); 17535 if (userInfo == null) { 17536 Slog.w(TAG, "No user info for user #" + userId); 17537 return false; 17538 } 17539 if (userInfo.isManagedProfile()) { 17540 Slog.w(TAG, "Cannot switch to User #" + userId + ": not a full user"); 17541 return false; 17542 } 17543 userName = userInfo.name; 17544 } 17545 mHandler.removeMessages(START_USER_SWITCH_MSG); 17546 mHandler.sendMessage(mHandler.obtainMessage(START_USER_SWITCH_MSG, userId, 0, userName)); 17547 return true; 17548 } 17549 17550 private void showUserSwitchDialog(int userId, String userName) { 17551 // The dialog will show and then initiate the user switch by calling startUserInForeground 17552 Dialog d = new UserSwitchingDialog(this, mContext, userId, userName, 17553 true /* above system */); 17554 d.show(); 17555 } 17556 17557 private boolean startUser(final int userId, boolean foreground) { 17558 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17559 != PackageManager.PERMISSION_GRANTED) { 17560 String msg = "Permission Denial: switchUser() from pid=" 17561 + Binder.getCallingPid() 17562 + ", uid=" + Binder.getCallingUid() 17563 + " requires " + INTERACT_ACROSS_USERS_FULL; 17564 Slog.w(TAG, msg); 17565 throw new SecurityException(msg); 17566 } 17567 17568 if (DEBUG_MU) Slog.i(TAG_MU, "starting userid:" + userId + " fore:" + foreground); 17569 17570 final long ident = Binder.clearCallingIdentity(); 17571 try { 17572 synchronized (this) { 17573 final int oldUserId = mCurrentUserId; 17574 if (oldUserId == userId) { 17575 return true; 17576 } 17577 17578 mStackSupervisor.setLockTaskModeLocked(null, false); 17579 17580 final UserInfo userInfo = getUserManagerLocked().getUserInfo(userId); 17581 if (userInfo == null) { 17582 Slog.w(TAG, "No user info for user #" + userId); 17583 return false; 17584 } 17585 if (foreground && userInfo.isManagedProfile()) { 17586 Slog.w(TAG, "Cannot switch to User #" + userId + ": not a full user"); 17587 return false; 17588 } 17589 17590 if (foreground) { 17591 mWindowManager.startFreezingScreen(R.anim.screen_user_exit, 17592 R.anim.screen_user_enter); 17593 } 17594 17595 boolean needStart = false; 17596 17597 // If the user we are switching to is not currently started, then 17598 // we need to start it now. 17599 if (mStartedUsers.get(userId) == null) { 17600 mStartedUsers.put(userId, new UserStartedState(new UserHandle(userId), false)); 17601 updateStartedUserArrayLocked(); 17602 needStart = true; 17603 } 17604 17605 final Integer userIdInt = Integer.valueOf(userId); 17606 mUserLru.remove(userIdInt); 17607 mUserLru.add(userIdInt); 17608 17609 if (foreground) { 17610 mCurrentUserId = userId; 17611 updateCurrentProfileIdsLocked(); 17612 mWindowManager.setCurrentUser(userId, mCurrentProfileIds); 17613 // Once the internal notion of the active user has switched, we lock the device 17614 // with the option to show the user switcher on the keyguard. 17615 mWindowManager.lockNow(null); 17616 } else { 17617 final Integer currentUserIdInt = Integer.valueOf(mCurrentUserId); 17618 updateCurrentProfileIdsLocked(); 17619 mWindowManager.setCurrentProfileIds(mCurrentProfileIds); 17620 mUserLru.remove(currentUserIdInt); 17621 mUserLru.add(currentUserIdInt); 17622 } 17623 17624 final UserStartedState uss = mStartedUsers.get(userId); 17625 17626 // Make sure user is in the started state. If it is currently 17627 // stopping, we need to knock that off. 17628 if (uss.mState == UserStartedState.STATE_STOPPING) { 17629 // If we are stopping, we haven't sent ACTION_SHUTDOWN, 17630 // so we can just fairly silently bring the user back from 17631 // the almost-dead. 17632 uss.mState = UserStartedState.STATE_RUNNING; 17633 updateStartedUserArrayLocked(); 17634 needStart = true; 17635 } else if (uss.mState == UserStartedState.STATE_SHUTDOWN) { 17636 // This means ACTION_SHUTDOWN has been sent, so we will 17637 // need to treat this as a new boot of the user. 17638 uss.mState = UserStartedState.STATE_BOOTING; 17639 updateStartedUserArrayLocked(); 17640 needStart = true; 17641 } 17642 17643 if (uss.mState == UserStartedState.STATE_BOOTING) { 17644 // Booting up a new user, need to tell system services about it. 17645 // Note that this is on the same handler as scheduling of broadcasts, 17646 // which is important because it needs to go first. 17647 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_START_MSG, userId, 0)); 17648 } 17649 17650 if (foreground) { 17651 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_CURRENT_MSG, userId, 17652 oldUserId)); 17653 mHandler.removeMessages(REPORT_USER_SWITCH_MSG); 17654 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 17655 mHandler.sendMessage(mHandler.obtainMessage(REPORT_USER_SWITCH_MSG, 17656 oldUserId, userId, uss)); 17657 mHandler.sendMessageDelayed(mHandler.obtainMessage(USER_SWITCH_TIMEOUT_MSG, 17658 oldUserId, userId, uss), USER_SWITCH_TIMEOUT); 17659 } 17660 17661 if (needStart) { 17662 // Send USER_STARTED broadcast 17663 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 17664 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 17665 | Intent.FLAG_RECEIVER_FOREGROUND); 17666 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17667 broadcastIntentLocked(null, null, intent, 17668 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 17669 false, false, MY_PID, Process.SYSTEM_UID, userId); 17670 } 17671 17672 if ((userInfo.flags&UserInfo.FLAG_INITIALIZED) == 0) { 17673 if (userId != UserHandle.USER_OWNER) { 17674 Intent intent = new Intent(Intent.ACTION_USER_INITIALIZE); 17675 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 17676 broadcastIntentLocked(null, null, intent, null, 17677 new IIntentReceiver.Stub() { 17678 public void performReceive(Intent intent, int resultCode, 17679 String data, Bundle extras, boolean ordered, 17680 boolean sticky, int sendingUser) { 17681 userInitialized(uss, userId); 17682 } 17683 }, 0, null, null, null, AppOpsManager.OP_NONE, 17684 true, false, MY_PID, Process.SYSTEM_UID, 17685 userId); 17686 uss.initializing = true; 17687 } else { 17688 getUserManagerLocked().makeInitialized(userInfo.id); 17689 } 17690 } 17691 17692 if (foreground) { 17693 boolean homeInFront = mStackSupervisor.switchUserLocked(userId, uss); 17694 if (homeInFront) { 17695 startHomeActivityLocked(userId); 17696 } else { 17697 mStackSupervisor.resumeTopActivitiesLocked(); 17698 } 17699 EventLogTags.writeAmSwitchUser(userId); 17700 getUserManagerLocked().userForeground(userId); 17701 sendUserSwitchBroadcastsLocked(oldUserId, userId); 17702 } else { 17703 mStackSupervisor.startBackgroundUserLocked(userId, uss); 17704 } 17705 17706 if (needStart) { 17707 Intent intent = new Intent(Intent.ACTION_USER_STARTING); 17708 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 17709 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17710 broadcastIntentLocked(null, null, intent, 17711 null, new IIntentReceiver.Stub() { 17712 @Override 17713 public void performReceive(Intent intent, int resultCode, String data, 17714 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 17715 throws RemoteException { 17716 } 17717 }, 0, null, null, 17718 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 17719 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 17720 } 17721 } 17722 } finally { 17723 Binder.restoreCallingIdentity(ident); 17724 } 17725 17726 return true; 17727 } 17728 17729 void sendUserSwitchBroadcastsLocked(int oldUserId, int newUserId) { 17730 long ident = Binder.clearCallingIdentity(); 17731 try { 17732 Intent intent; 17733 if (oldUserId >= 0) { 17734 // Send USER_BACKGROUND broadcast to all profiles of the outgoing user 17735 List<UserInfo> profiles = mUserManager.getProfiles(oldUserId, false); 17736 int count = profiles.size(); 17737 for (int i = 0; i < count; i++) { 17738 int profileUserId = profiles.get(i).id; 17739 intent = new Intent(Intent.ACTION_USER_BACKGROUND); 17740 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 17741 | Intent.FLAG_RECEIVER_FOREGROUND); 17742 intent.putExtra(Intent.EXTRA_USER_HANDLE, profileUserId); 17743 broadcastIntentLocked(null, null, intent, 17744 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 17745 false, false, MY_PID, Process.SYSTEM_UID, profileUserId); 17746 } 17747 } 17748 if (newUserId >= 0) { 17749 // Send USER_FOREGROUND broadcast to all profiles of the incoming user 17750 List<UserInfo> profiles = mUserManager.getProfiles(newUserId, false); 17751 int count = profiles.size(); 17752 for (int i = 0; i < count; i++) { 17753 int profileUserId = profiles.get(i).id; 17754 intent = new Intent(Intent.ACTION_USER_FOREGROUND); 17755 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 17756 | Intent.FLAG_RECEIVER_FOREGROUND); 17757 intent.putExtra(Intent.EXTRA_USER_HANDLE, profileUserId); 17758 broadcastIntentLocked(null, null, intent, 17759 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 17760 false, false, MY_PID, Process.SYSTEM_UID, profileUserId); 17761 } 17762 intent = new Intent(Intent.ACTION_USER_SWITCHED); 17763 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 17764 | Intent.FLAG_RECEIVER_FOREGROUND); 17765 intent.putExtra(Intent.EXTRA_USER_HANDLE, newUserId); 17766 broadcastIntentLocked(null, null, intent, 17767 null, null, 0, null, null, 17768 android.Manifest.permission.MANAGE_USERS, AppOpsManager.OP_NONE, 17769 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 17770 } 17771 } finally { 17772 Binder.restoreCallingIdentity(ident); 17773 } 17774 } 17775 17776 void dispatchUserSwitch(final UserStartedState uss, final int oldUserId, 17777 final int newUserId) { 17778 final int N = mUserSwitchObservers.beginBroadcast(); 17779 if (N > 0) { 17780 final IRemoteCallback callback = new IRemoteCallback.Stub() { 17781 int mCount = 0; 17782 @Override 17783 public void sendResult(Bundle data) throws RemoteException { 17784 synchronized (ActivityManagerService.this) { 17785 if (mCurUserSwitchCallback == this) { 17786 mCount++; 17787 if (mCount == N) { 17788 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 17789 } 17790 } 17791 } 17792 } 17793 }; 17794 synchronized (this) { 17795 uss.switching = true; 17796 mCurUserSwitchCallback = callback; 17797 } 17798 for (int i=0; i<N; i++) { 17799 try { 17800 mUserSwitchObservers.getBroadcastItem(i).onUserSwitching( 17801 newUserId, callback); 17802 } catch (RemoteException e) { 17803 } 17804 } 17805 } else { 17806 synchronized (this) { 17807 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 17808 } 17809 } 17810 mUserSwitchObservers.finishBroadcast(); 17811 } 17812 17813 void timeoutUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 17814 synchronized (this) { 17815 Slog.w(TAG, "User switch timeout: from " + oldUserId + " to " + newUserId); 17816 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 17817 } 17818 } 17819 17820 void sendContinueUserSwitchLocked(UserStartedState uss, int oldUserId, int newUserId) { 17821 mCurUserSwitchCallback = null; 17822 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 17823 mHandler.sendMessage(mHandler.obtainMessage(CONTINUE_USER_SWITCH_MSG, 17824 oldUserId, newUserId, uss)); 17825 } 17826 17827 void userInitialized(UserStartedState uss, int newUserId) { 17828 completeSwitchAndInitalize(uss, newUserId, true, false); 17829 } 17830 17831 void continueUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 17832 completeSwitchAndInitalize(uss, newUserId, false, true); 17833 } 17834 17835 void completeSwitchAndInitalize(UserStartedState uss, int newUserId, 17836 boolean clearInitializing, boolean clearSwitching) { 17837 boolean unfrozen = false; 17838 synchronized (this) { 17839 if (clearInitializing) { 17840 uss.initializing = false; 17841 getUserManagerLocked().makeInitialized(uss.mHandle.getIdentifier()); 17842 } 17843 if (clearSwitching) { 17844 uss.switching = false; 17845 } 17846 if (!uss.switching && !uss.initializing) { 17847 mWindowManager.stopFreezingScreen(); 17848 unfrozen = true; 17849 } 17850 } 17851 if (unfrozen) { 17852 final int N = mUserSwitchObservers.beginBroadcast(); 17853 for (int i=0; i<N; i++) { 17854 try { 17855 mUserSwitchObservers.getBroadcastItem(i).onUserSwitchComplete(newUserId); 17856 } catch (RemoteException e) { 17857 } 17858 } 17859 mUserSwitchObservers.finishBroadcast(); 17860 } 17861 } 17862 17863 void scheduleStartProfilesLocked() { 17864 if (!mHandler.hasMessages(START_PROFILES_MSG)) { 17865 mHandler.sendMessageDelayed(mHandler.obtainMessage(START_PROFILES_MSG), 17866 DateUtils.SECOND_IN_MILLIS); 17867 } 17868 } 17869 17870 void startProfilesLocked() { 17871 if (DEBUG_MU) Slog.i(TAG_MU, "startProfilesLocked"); 17872 List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17873 mCurrentUserId, false /* enabledOnly */); 17874 List<UserInfo> toStart = new ArrayList<UserInfo>(profiles.size()); 17875 for (UserInfo user : profiles) { 17876 if ((user.flags & UserInfo.FLAG_INITIALIZED) == UserInfo.FLAG_INITIALIZED 17877 && user.id != mCurrentUserId) { 17878 toStart.add(user); 17879 } 17880 } 17881 final int n = toStart.size(); 17882 int i = 0; 17883 for (; i < n && i < (MAX_RUNNING_USERS - 1); ++i) { 17884 startUserInBackground(toStart.get(i).id); 17885 } 17886 if (i < n) { 17887 Slog.w(TAG_MU, "More profiles than MAX_RUNNING_USERS"); 17888 } 17889 } 17890 17891 void finishUserBoot(UserStartedState uss) { 17892 synchronized (this) { 17893 if (uss.mState == UserStartedState.STATE_BOOTING 17894 && mStartedUsers.get(uss.mHandle.getIdentifier()) == uss) { 17895 uss.mState = UserStartedState.STATE_RUNNING; 17896 final int userId = uss.mHandle.getIdentifier(); 17897 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 17898 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17899 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 17900 broadcastIntentLocked(null, null, intent, 17901 null, null, 0, null, null, 17902 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, AppOpsManager.OP_NONE, 17903 true, false, MY_PID, Process.SYSTEM_UID, userId); 17904 } 17905 } 17906 } 17907 17908 void finishUserSwitch(UserStartedState uss) { 17909 synchronized (this) { 17910 finishUserBoot(uss); 17911 17912 startProfilesLocked(); 17913 17914 int num = mUserLru.size(); 17915 int i = 0; 17916 while (num > MAX_RUNNING_USERS && i < mUserLru.size()) { 17917 Integer oldUserId = mUserLru.get(i); 17918 UserStartedState oldUss = mStartedUsers.get(oldUserId); 17919 if (oldUss == null) { 17920 // Shouldn't happen, but be sane if it does. 17921 mUserLru.remove(i); 17922 num--; 17923 continue; 17924 } 17925 if (oldUss.mState == UserStartedState.STATE_STOPPING 17926 || oldUss.mState == UserStartedState.STATE_SHUTDOWN) { 17927 // This user is already stopping, doesn't count. 17928 num--; 17929 i++; 17930 continue; 17931 } 17932 if (oldUserId == UserHandle.USER_OWNER || oldUserId == mCurrentUserId) { 17933 // Owner and current can't be stopped, but count as running. 17934 i++; 17935 continue; 17936 } 17937 // This is a user to be stopped. 17938 stopUserLocked(oldUserId, null); 17939 num--; 17940 i++; 17941 } 17942 } 17943 } 17944 17945 @Override 17946 public int stopUser(final int userId, final IStopUserCallback callback) { 17947 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17948 != PackageManager.PERMISSION_GRANTED) { 17949 String msg = "Permission Denial: switchUser() from pid=" 17950 + Binder.getCallingPid() 17951 + ", uid=" + Binder.getCallingUid() 17952 + " requires " + INTERACT_ACROSS_USERS_FULL; 17953 Slog.w(TAG, msg); 17954 throw new SecurityException(msg); 17955 } 17956 if (userId <= 0) { 17957 throw new IllegalArgumentException("Can't stop primary user " + userId); 17958 } 17959 synchronized (this) { 17960 return stopUserLocked(userId, callback); 17961 } 17962 } 17963 17964 private int stopUserLocked(final int userId, final IStopUserCallback callback) { 17965 if (DEBUG_MU) Slog.i(TAG_MU, "stopUserLocked userId=" + userId); 17966 if (mCurrentUserId == userId) { 17967 return ActivityManager.USER_OP_IS_CURRENT; 17968 } 17969 17970 final UserStartedState uss = mStartedUsers.get(userId); 17971 if (uss == null) { 17972 // User is not started, nothing to do... but we do need to 17973 // callback if requested. 17974 if (callback != null) { 17975 mHandler.post(new Runnable() { 17976 @Override 17977 public void run() { 17978 try { 17979 callback.userStopped(userId); 17980 } catch (RemoteException e) { 17981 } 17982 } 17983 }); 17984 } 17985 return ActivityManager.USER_OP_SUCCESS; 17986 } 17987 17988 if (callback != null) { 17989 uss.mStopCallbacks.add(callback); 17990 } 17991 17992 if (uss.mState != UserStartedState.STATE_STOPPING 17993 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17994 uss.mState = UserStartedState.STATE_STOPPING; 17995 updateStartedUserArrayLocked(); 17996 17997 long ident = Binder.clearCallingIdentity(); 17998 try { 17999 // We are going to broadcast ACTION_USER_STOPPING and then 18000 // once that is done send a final ACTION_SHUTDOWN and then 18001 // stop the user. 18002 final Intent stoppingIntent = new Intent(Intent.ACTION_USER_STOPPING); 18003 stoppingIntent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 18004 stoppingIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 18005 stoppingIntent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 18006 final Intent shutdownIntent = new Intent(Intent.ACTION_SHUTDOWN); 18007 // This is the result receiver for the final shutdown broadcast. 18008 final IIntentReceiver shutdownReceiver = new IIntentReceiver.Stub() { 18009 @Override 18010 public void performReceive(Intent intent, int resultCode, String data, 18011 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 18012 finishUserStop(uss); 18013 } 18014 }; 18015 // This is the result receiver for the initial stopping broadcast. 18016 final IIntentReceiver stoppingReceiver = new IIntentReceiver.Stub() { 18017 @Override 18018 public void performReceive(Intent intent, int resultCode, String data, 18019 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 18020 // On to the next. 18021 synchronized (ActivityManagerService.this) { 18022 if (uss.mState != UserStartedState.STATE_STOPPING) { 18023 // Whoops, we are being started back up. Abort, abort! 18024 return; 18025 } 18026 uss.mState = UserStartedState.STATE_SHUTDOWN; 18027 } 18028 mBatteryStatsService.noteEvent( 18029 BatteryStats.HistoryItem.EVENT_USER_RUNNING_FINISH, 18030 Integer.toString(userId), userId); 18031 mSystemServiceManager.stopUser(userId); 18032 broadcastIntentLocked(null, null, shutdownIntent, 18033 null, shutdownReceiver, 0, null, null, null, AppOpsManager.OP_NONE, 18034 true, false, MY_PID, Process.SYSTEM_UID, userId); 18035 } 18036 }; 18037 // Kick things off. 18038 broadcastIntentLocked(null, null, stoppingIntent, 18039 null, stoppingReceiver, 0, null, null, 18040 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 18041 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 18042 } finally { 18043 Binder.restoreCallingIdentity(ident); 18044 } 18045 } 18046 18047 return ActivityManager.USER_OP_SUCCESS; 18048 } 18049 18050 void finishUserStop(UserStartedState uss) { 18051 final int userId = uss.mHandle.getIdentifier(); 18052 boolean stopped; 18053 ArrayList<IStopUserCallback> callbacks; 18054 synchronized (this) { 18055 callbacks = new ArrayList<IStopUserCallback>(uss.mStopCallbacks); 18056 if (mStartedUsers.get(userId) != uss) { 18057 stopped = false; 18058 } else if (uss.mState != UserStartedState.STATE_SHUTDOWN) { 18059 stopped = false; 18060 } else { 18061 stopped = true; 18062 // User can no longer run. 18063 mStartedUsers.remove(userId); 18064 mUserLru.remove(Integer.valueOf(userId)); 18065 updateStartedUserArrayLocked(); 18066 18067 // Clean up all state and processes associated with the user. 18068 // Kill all the processes for the user. 18069 forceStopUserLocked(userId, "finish user"); 18070 } 18071 18072 // Explicitly remove the old information in mRecentTasks. 18073 removeRecentTasksForUserLocked(userId); 18074 } 18075 18076 for (int i=0; i<callbacks.size(); i++) { 18077 try { 18078 if (stopped) callbacks.get(i).userStopped(userId); 18079 else callbacks.get(i).userStopAborted(userId); 18080 } catch (RemoteException e) { 18081 } 18082 } 18083 18084 if (stopped) { 18085 mSystemServiceManager.cleanupUser(userId); 18086 synchronized (this) { 18087 mStackSupervisor.removeUserLocked(userId); 18088 } 18089 } 18090 } 18091 18092 @Override 18093 public UserInfo getCurrentUser() { 18094 if ((checkCallingPermission(INTERACT_ACROSS_USERS) 18095 != PackageManager.PERMISSION_GRANTED) && ( 18096 checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 18097 != PackageManager.PERMISSION_GRANTED)) { 18098 String msg = "Permission Denial: getCurrentUser() from pid=" 18099 + Binder.getCallingPid() 18100 + ", uid=" + Binder.getCallingUid() 18101 + " requires " + INTERACT_ACROSS_USERS; 18102 Slog.w(TAG, msg); 18103 throw new SecurityException(msg); 18104 } 18105 synchronized (this) { 18106 return getUserManagerLocked().getUserInfo(mCurrentUserId); 18107 } 18108 } 18109 18110 int getCurrentUserIdLocked() { 18111 return mCurrentUserId; 18112 } 18113 18114 @Override 18115 public boolean isUserRunning(int userId, boolean orStopped) { 18116 if (checkCallingPermission(INTERACT_ACROSS_USERS) 18117 != PackageManager.PERMISSION_GRANTED) { 18118 String msg = "Permission Denial: isUserRunning() from pid=" 18119 + Binder.getCallingPid() 18120 + ", uid=" + Binder.getCallingUid() 18121 + " requires " + INTERACT_ACROSS_USERS; 18122 Slog.w(TAG, msg); 18123 throw new SecurityException(msg); 18124 } 18125 synchronized (this) { 18126 return isUserRunningLocked(userId, orStopped); 18127 } 18128 } 18129 18130 boolean isUserRunningLocked(int userId, boolean orStopped) { 18131 UserStartedState state = mStartedUsers.get(userId); 18132 if (state == null) { 18133 return false; 18134 } 18135 if (orStopped) { 18136 return true; 18137 } 18138 return state.mState != UserStartedState.STATE_STOPPING 18139 && state.mState != UserStartedState.STATE_SHUTDOWN; 18140 } 18141 18142 @Override 18143 public int[] getRunningUserIds() { 18144 if (checkCallingPermission(INTERACT_ACROSS_USERS) 18145 != PackageManager.PERMISSION_GRANTED) { 18146 String msg = "Permission Denial: isUserRunning() from pid=" 18147 + Binder.getCallingPid() 18148 + ", uid=" + Binder.getCallingUid() 18149 + " requires " + INTERACT_ACROSS_USERS; 18150 Slog.w(TAG, msg); 18151 throw new SecurityException(msg); 18152 } 18153 synchronized (this) { 18154 return mStartedUserArray; 18155 } 18156 } 18157 18158 private void updateStartedUserArrayLocked() { 18159 int num = 0; 18160 for (int i=0; i<mStartedUsers.size(); i++) { 18161 UserStartedState uss = mStartedUsers.valueAt(i); 18162 // This list does not include stopping users. 18163 if (uss.mState != UserStartedState.STATE_STOPPING 18164 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 18165 num++; 18166 } 18167 } 18168 mStartedUserArray = new int[num]; 18169 num = 0; 18170 for (int i=0; i<mStartedUsers.size(); i++) { 18171 UserStartedState uss = mStartedUsers.valueAt(i); 18172 if (uss.mState != UserStartedState.STATE_STOPPING 18173 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 18174 mStartedUserArray[num] = mStartedUsers.keyAt(i); 18175 num++; 18176 } 18177 } 18178 } 18179 18180 @Override 18181 public void registerUserSwitchObserver(IUserSwitchObserver observer) { 18182 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 18183 != PackageManager.PERMISSION_GRANTED) { 18184 String msg = "Permission Denial: registerUserSwitchObserver() from pid=" 18185 + Binder.getCallingPid() 18186 + ", uid=" + Binder.getCallingUid() 18187 + " requires " + INTERACT_ACROSS_USERS_FULL; 18188 Slog.w(TAG, msg); 18189 throw new SecurityException(msg); 18190 } 18191 18192 mUserSwitchObservers.register(observer); 18193 } 18194 18195 @Override 18196 public void unregisterUserSwitchObserver(IUserSwitchObserver observer) { 18197 mUserSwitchObservers.unregister(observer); 18198 } 18199 18200 private boolean userExists(int userId) { 18201 if (userId == 0) { 18202 return true; 18203 } 18204 UserManagerService ums = getUserManagerLocked(); 18205 return ums != null ? (ums.getUserInfo(userId) != null) : false; 18206 } 18207 18208 int[] getUsersLocked() { 18209 UserManagerService ums = getUserManagerLocked(); 18210 return ums != null ? ums.getUserIds() : new int[] { 0 }; 18211 } 18212 18213 UserManagerService getUserManagerLocked() { 18214 if (mUserManager == null) { 18215 IBinder b = ServiceManager.getService(Context.USER_SERVICE); 18216 mUserManager = (UserManagerService)IUserManager.Stub.asInterface(b); 18217 } 18218 return mUserManager; 18219 } 18220 18221 private int applyUserId(int uid, int userId) { 18222 return UserHandle.getUid(userId, uid); 18223 } 18224 18225 ApplicationInfo getAppInfoForUser(ApplicationInfo info, int userId) { 18226 if (info == null) return null; 18227 ApplicationInfo newInfo = new ApplicationInfo(info); 18228 newInfo.uid = applyUserId(info.uid, userId); 18229 newInfo.dataDir = USER_DATA_DIR + userId + "/" 18230 + info.packageName; 18231 return newInfo; 18232 } 18233 18234 ActivityInfo getActivityInfoForUser(ActivityInfo aInfo, int userId) { 18235 if (aInfo == null 18236 || (userId < 1 && aInfo.applicationInfo.uid < UserHandle.PER_USER_RANGE)) { 18237 return aInfo; 18238 } 18239 18240 ActivityInfo info = new ActivityInfo(aInfo); 18241 info.applicationInfo = getAppInfoForUser(info.applicationInfo, userId); 18242 return info; 18243 } 18244 18245 private final class LocalService extends ActivityManagerInternal { 18246 @Override 18247 public void goingToSleep() { 18248 ActivityManagerService.this.goingToSleep(); 18249 } 18250 18251 @Override 18252 public void wakingUp() { 18253 ActivityManagerService.this.wakingUp(); 18254 } 18255 18256 @Override 18257 public int startIsolatedProcess(String entryPoint, String[] entryPointArgs, 18258 String processName, String abiOverride, int uid, Runnable crashHandler) { 18259 return ActivityManagerService.this.startIsolatedProcess(entryPoint, entryPointArgs, 18260 processName, abiOverride, uid, crashHandler); 18261 } 18262 } 18263 18264 /** 18265 * An implementation of IAppTask, that allows an app to manage its own tasks via 18266 * {@link android.app.ActivityManager.AppTask}. We keep track of the callingUid to ensure that 18267 * only the process that calls getAppTasks() can call the AppTask methods. 18268 */ 18269 class AppTaskImpl extends IAppTask.Stub { 18270 private int mTaskId; 18271 private int mCallingUid; 18272 18273 public AppTaskImpl(int taskId, int callingUid) { 18274 mTaskId = taskId; 18275 mCallingUid = callingUid; 18276 } 18277 18278 private void checkCaller() { 18279 if (mCallingUid != Binder.getCallingUid()) { 18280 throw new SecurityException("Caller " + mCallingUid 18281 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 18282 } 18283 } 18284 18285 @Override 18286 public void finishAndRemoveTask() { 18287 checkCaller(); 18288 18289 synchronized (ActivityManagerService.this) { 18290 long origId = Binder.clearCallingIdentity(); 18291 try { 18292 TaskRecord tr = recentTaskForIdLocked(mTaskId); 18293 if (tr != null) { 18294 // Only kill the process if we are not a new document 18295 int flags = tr.getBaseIntent().getFlags(); 18296 boolean isDocument = (flags & Intent.FLAG_ACTIVITY_NEW_DOCUMENT) == 18297 Intent.FLAG_ACTIVITY_NEW_DOCUMENT; 18298 removeTaskByIdLocked(mTaskId, 18299 !isDocument ? ActivityManager.REMOVE_TASK_KILL_PROCESS : 0); 18300 } 18301 } finally { 18302 Binder.restoreCallingIdentity(origId); 18303 } 18304 } 18305 } 18306 18307 @Override 18308 public ActivityManager.RecentTaskInfo getTaskInfo() { 18309 checkCaller(); 18310 18311 synchronized (ActivityManagerService.this) { 18312 long origId = Binder.clearCallingIdentity(); 18313 try { 18314 TaskRecord tr = recentTaskForIdLocked(mTaskId); 18315 if (tr != null) { 18316 return createRecentTaskInfoFromTaskRecord(tr); 18317 } 18318 } finally { 18319 Binder.restoreCallingIdentity(origId); 18320 } 18321 return null; 18322 } 18323 } 18324 18325 @Override 18326 public void setExcludeFromRecents(boolean exclude) { 18327 checkCaller(); 18328 18329 synchronized (ActivityManagerService.this) { 18330 long origId = Binder.clearCallingIdentity(); 18331 try { 18332 TaskRecord tr = recentTaskForIdLocked(mTaskId); 18333 if (tr != null) { 18334 Intent intent = tr.getBaseIntent(); 18335 if (exclude) { 18336 intent.addFlags(Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 18337 } else { 18338 intent.setFlags(intent.getFlags() 18339 & ~Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 18340 } 18341 } 18342 } finally { 18343 Binder.restoreCallingIdentity(origId); 18344 } 18345 } 18346 } 18347 } 18348} 18349