ActivityManagerService.java revision a4e102ee580282dc7abeb22f4a025813e53b9431
1/* 2 * Copyright (C) 2006-2008 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17package com.android.server.am; 18 19import static android.Manifest.permission.INTERACT_ACROSS_USERS; 20import static android.Manifest.permission.INTERACT_ACROSS_USERS_FULL; 21import static android.Manifest.permission.START_TASKS_FROM_RECENTS; 22import static android.content.pm.PackageManager.PERMISSION_GRANTED; 23import static com.android.internal.util.XmlUtils.readBooleanAttribute; 24import static com.android.internal.util.XmlUtils.readIntAttribute; 25import static com.android.internal.util.XmlUtils.readLongAttribute; 26import static com.android.internal.util.XmlUtils.writeBooleanAttribute; 27import static com.android.internal.util.XmlUtils.writeIntAttribute; 28import static com.android.internal.util.XmlUtils.writeLongAttribute; 29import static com.android.server.Watchdog.NATIVE_STACKS_OF_INTEREST; 30import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT; 31import static org.xmlpull.v1.XmlPullParser.START_TAG; 32import static com.android.server.am.ActivityStackSupervisor.HOME_STACK_ID; 33 34import android.Manifest; 35import android.app.AppOpsManager; 36import android.app.ApplicationThreadNative; 37import android.app.IActivityContainer; 38import android.app.IActivityContainerCallback; 39import android.app.IAppTask; 40import android.app.ProfilerInfo; 41import android.app.admin.DevicePolicyManager; 42import android.app.usage.UsageEvents; 43import android.app.usage.UsageStatsManagerInternal; 44import android.appwidget.AppWidgetManager; 45import android.content.res.Resources; 46import android.graphics.Bitmap; 47import android.graphics.Point; 48import android.graphics.Rect; 49import android.os.BatteryStats; 50import android.os.PersistableBundle; 51import android.service.voice.IVoiceInteractionSession; 52import android.util.ArrayMap; 53import android.util.ArraySet; 54import android.util.SparseIntArray; 55 56import com.android.internal.R; 57import com.android.internal.annotations.GuardedBy; 58import com.android.internal.app.IAppOpsService; 59import com.android.internal.app.IVoiceInteractor; 60import com.android.internal.app.ProcessMap; 61import com.android.internal.app.ProcessStats; 62import com.android.internal.content.PackageMonitor; 63import com.android.internal.os.BackgroundThread; 64import com.android.internal.os.BatteryStatsImpl; 65import com.android.internal.os.ProcessCpuTracker; 66import com.android.internal.os.TransferPipe; 67import com.android.internal.os.Zygote; 68import com.android.internal.util.FastPrintWriter; 69import com.android.internal.util.FastXmlSerializer; 70import com.android.internal.util.MemInfoReader; 71import com.android.internal.util.Preconditions; 72import com.android.server.AppOpsService; 73import com.android.server.AttributeCache; 74import com.android.server.IntentResolver; 75import com.android.server.LocalServices; 76import com.android.server.ServiceThread; 77import com.android.server.SystemService; 78import com.android.server.SystemServiceManager; 79import com.android.server.Watchdog; 80import com.android.server.am.ActivityStack.ActivityState; 81import com.android.server.firewall.IntentFirewall; 82import com.android.server.pm.UserManagerService; 83import com.android.server.wm.AppTransition; 84import com.android.server.wm.WindowManagerService; 85import com.google.android.collect.Lists; 86import com.google.android.collect.Maps; 87 88import libcore.io.IoUtils; 89 90import org.xmlpull.v1.XmlPullParser; 91import org.xmlpull.v1.XmlPullParserException; 92import org.xmlpull.v1.XmlSerializer; 93 94import android.app.Activity; 95import android.app.ActivityManager; 96import android.app.ActivityManager.RunningTaskInfo; 97import android.app.ActivityManager.StackInfo; 98import android.app.ActivityManagerInternal; 99import android.app.ActivityManagerNative; 100import android.app.ActivityOptions; 101import android.app.ActivityThread; 102import android.app.AlertDialog; 103import android.app.AppGlobals; 104import android.app.ApplicationErrorReport; 105import android.app.Dialog; 106import android.app.IActivityController; 107import android.app.IApplicationThread; 108import android.app.IInstrumentationWatcher; 109import android.app.INotificationManager; 110import android.app.IProcessObserver; 111import android.app.IServiceConnection; 112import android.app.IStopUserCallback; 113import android.app.IUiAutomationConnection; 114import android.app.IUserSwitchObserver; 115import android.app.Instrumentation; 116import android.app.Notification; 117import android.app.NotificationManager; 118import android.app.PendingIntent; 119import android.app.backup.IBackupManager; 120import android.content.ActivityNotFoundException; 121import android.content.BroadcastReceiver; 122import android.content.ClipData; 123import android.content.ComponentCallbacks2; 124import android.content.ComponentName; 125import android.content.ContentProvider; 126import android.content.ContentResolver; 127import android.content.Context; 128import android.content.DialogInterface; 129import android.content.IContentProvider; 130import android.content.IIntentReceiver; 131import android.content.IIntentSender; 132import android.content.Intent; 133import android.content.IntentFilter; 134import android.content.IntentSender; 135import android.content.pm.ActivityInfo; 136import android.content.pm.ApplicationInfo; 137import android.content.pm.ConfigurationInfo; 138import android.content.pm.IPackageDataObserver; 139import android.content.pm.IPackageManager; 140import android.content.pm.InstrumentationInfo; 141import android.content.pm.PackageInfo; 142import android.content.pm.PackageManager; 143import android.content.pm.ParceledListSlice; 144import android.content.pm.UserInfo; 145import android.content.pm.PackageManager.NameNotFoundException; 146import android.content.pm.PathPermission; 147import android.content.pm.ProviderInfo; 148import android.content.pm.ResolveInfo; 149import android.content.pm.ServiceInfo; 150import android.content.res.CompatibilityInfo; 151import android.content.res.Configuration; 152import android.net.Proxy; 153import android.net.ProxyInfo; 154import android.net.Uri; 155import android.os.Binder; 156import android.os.Build; 157import android.os.Bundle; 158import android.os.Debug; 159import android.os.DropBoxManager; 160import android.os.Environment; 161import android.os.FactoryTest; 162import android.os.FileObserver; 163import android.os.FileUtils; 164import android.os.Handler; 165import android.os.IBinder; 166import android.os.IPermissionController; 167import android.os.IRemoteCallback; 168import android.os.IUserManager; 169import android.os.Looper; 170import android.os.Message; 171import android.os.Parcel; 172import android.os.ParcelFileDescriptor; 173import android.os.Process; 174import android.os.RemoteCallbackList; 175import android.os.RemoteException; 176import android.os.SELinux; 177import android.os.ServiceManager; 178import android.os.StrictMode; 179import android.os.SystemClock; 180import android.os.SystemProperties; 181import android.os.UpdateLock; 182import android.os.UserHandle; 183import android.provider.Settings; 184import android.text.format.DateUtils; 185import android.text.format.Time; 186import android.util.AtomicFile; 187import android.util.EventLog; 188import android.util.Log; 189import android.util.Pair; 190import android.util.PrintWriterPrinter; 191import android.util.Slog; 192import android.util.SparseArray; 193import android.util.TimeUtils; 194import android.util.Xml; 195import android.view.Gravity; 196import android.view.LayoutInflater; 197import android.view.View; 198import android.view.WindowManager; 199 200import java.io.BufferedInputStream; 201import java.io.BufferedOutputStream; 202import java.io.DataInputStream; 203import java.io.DataOutputStream; 204import java.io.File; 205import java.io.FileDescriptor; 206import java.io.FileInputStream; 207import java.io.FileNotFoundException; 208import java.io.FileOutputStream; 209import java.io.IOException; 210import java.io.InputStreamReader; 211import java.io.PrintWriter; 212import java.io.StringWriter; 213import java.lang.ref.WeakReference; 214import java.util.ArrayList; 215import java.util.Arrays; 216import java.util.Collections; 217import java.util.Comparator; 218import java.util.HashMap; 219import java.util.HashSet; 220import java.util.Iterator; 221import java.util.List; 222import java.util.Locale; 223import java.util.Map; 224import java.util.Set; 225import java.util.concurrent.atomic.AtomicBoolean; 226import java.util.concurrent.atomic.AtomicLong; 227 228public final class ActivityManagerService extends ActivityManagerNative 229 implements Watchdog.Monitor, BatteryStatsImpl.BatteryCallback { 230 231 private static final String USER_DATA_DIR = "/data/user/"; 232 // File that stores last updated system version and called preboot receivers 233 static final String CALLED_PRE_BOOTS_FILENAME = "called_pre_boots.dat"; 234 235 static final String TAG = "ActivityManager"; 236 static final String TAG_MU = "ActivityManagerServiceMU"; 237 static final boolean DEBUG = false; 238 static final boolean localLOGV = DEBUG; 239 static final boolean DEBUG_BACKUP = localLOGV || false; 240 static final boolean DEBUG_BROADCAST = localLOGV || false; 241 static final boolean DEBUG_BROADCAST_LIGHT = DEBUG_BROADCAST || false; 242 static final boolean DEBUG_BACKGROUND_BROADCAST = DEBUG_BROADCAST || false; 243 static final boolean DEBUG_CLEANUP = localLOGV || false; 244 static final boolean DEBUG_CONFIGURATION = localLOGV || false; 245 static final boolean DEBUG_FOCUS = false; 246 static final boolean DEBUG_IMMERSIVE = localLOGV || false; 247 static final boolean DEBUG_MU = localLOGV || false; 248 static final boolean DEBUG_OOM_ADJ = localLOGV || false; 249 static final boolean DEBUG_LRU = localLOGV || false; 250 static final boolean DEBUG_PAUSE = localLOGV || false; 251 static final boolean DEBUG_POWER = localLOGV || false; 252 static final boolean DEBUG_POWER_QUICK = DEBUG_POWER || false; 253 static final boolean DEBUG_PROCESS_OBSERVERS = localLOGV || false; 254 static final boolean DEBUG_PROCESSES = localLOGV || false; 255 static final boolean DEBUG_PROVIDER = localLOGV || false; 256 static final boolean DEBUG_RESULTS = localLOGV || false; 257 static final boolean DEBUG_SERVICE = localLOGV || false; 258 static final boolean DEBUG_SERVICE_EXECUTING = localLOGV || false; 259 static final boolean DEBUG_STACK = localLOGV || false; 260 static final boolean DEBUG_SWITCH = localLOGV || false; 261 static final boolean DEBUG_TASKS = localLOGV || false; 262 static final boolean DEBUG_THUMBNAILS = localLOGV || false; 263 static final boolean DEBUG_TRANSITION = localLOGV || false; 264 static final boolean DEBUG_URI_PERMISSION = localLOGV || false; 265 static final boolean DEBUG_USER_LEAVING = localLOGV || false; 266 static final boolean DEBUG_VISBILITY = localLOGV || false; 267 static final boolean DEBUG_PSS = localLOGV || false; 268 static final boolean DEBUG_LOCKSCREEN = localLOGV || false; 269 static final boolean DEBUG_RECENTS = localLOGV || false; 270 static final boolean VALIDATE_TOKENS = false; 271 static final boolean SHOW_ACTIVITY_START_TIME = true; 272 273 // Control over CPU and battery monitoring. 274 static final long BATTERY_STATS_TIME = 30*60*1000; // write battery stats every 30 minutes. 275 static final boolean MONITOR_CPU_USAGE = true; 276 static final long MONITOR_CPU_MIN_TIME = 5*1000; // don't sample cpu less than every 5 seconds. 277 static final long MONITOR_CPU_MAX_TIME = 0x0fffffff; // wait possibly forever for next cpu sample. 278 static final boolean MONITOR_THREAD_CPU_USAGE = false; 279 280 // The flags that are set for all calls we make to the package manager. 281 static final int STOCK_PM_FLAGS = PackageManager.GET_SHARED_LIBRARY_FILES; 282 283 private static final String SYSTEM_DEBUGGABLE = "ro.debuggable"; 284 285 static final boolean IS_USER_BUILD = "user".equals(Build.TYPE); 286 287 // Maximum number recent bitmaps to keep in memory. 288 static final int MAX_RECENT_BITMAPS = 5; 289 290 // Amount of time after a call to stopAppSwitches() during which we will 291 // prevent further untrusted switches from happening. 292 static final long APP_SWITCH_DELAY_TIME = 5*1000; 293 294 // How long we wait for a launched process to attach to the activity manager 295 // before we decide it's never going to come up for real. 296 static final int PROC_START_TIMEOUT = 10*1000; 297 298 // How long we wait for a launched process to attach to the activity manager 299 // before we decide it's never going to come up for real, when the process was 300 // started with a wrapper for instrumentation (such as Valgrind) because it 301 // could take much longer than usual. 302 static final int PROC_START_TIMEOUT_WITH_WRAPPER = 1200*1000; 303 304 // How long to wait after going idle before forcing apps to GC. 305 static final int GC_TIMEOUT = 5*1000; 306 307 // The minimum amount of time between successive GC requests for a process. 308 static final int GC_MIN_INTERVAL = 60*1000; 309 310 // The minimum amount of time between successive PSS requests for a process. 311 static final int FULL_PSS_MIN_INTERVAL = 10*60*1000; 312 313 // The minimum amount of time between successive PSS requests for a process 314 // when the request is due to the memory state being lowered. 315 static final int FULL_PSS_LOWERED_INTERVAL = 2*60*1000; 316 317 // The rate at which we check for apps using excessive power -- 15 mins. 318 static final int POWER_CHECK_DELAY = (DEBUG_POWER_QUICK ? 2 : 15) * 60*1000; 319 320 // The minimum sample duration we will allow before deciding we have 321 // enough data on wake locks to start killing things. 322 static final int WAKE_LOCK_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 323 324 // The minimum sample duration we will allow before deciding we have 325 // enough data on CPU usage to start killing things. 326 static final int CPU_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 327 328 // How long we allow a receiver to run before giving up on it. 329 static final int BROADCAST_FG_TIMEOUT = 10*1000; 330 static final int BROADCAST_BG_TIMEOUT = 60*1000; 331 332 // How long we wait until we timeout on key dispatching. 333 static final int KEY_DISPATCHING_TIMEOUT = 5*1000; 334 335 // How long we wait until we timeout on key dispatching during instrumentation. 336 static final int INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT = 60*1000; 337 338 // Amount of time we wait for observers to handle a user switch before 339 // giving up on them and unfreezing the screen. 340 static final int USER_SWITCH_TIMEOUT = 2*1000; 341 342 // Maximum number of users we allow to be running at a time. 343 static final int MAX_RUNNING_USERS = 3; 344 345 // How long to wait in getAssistContextExtras for the activity and foreground services 346 // to respond with the result. 347 static final int PENDING_ASSIST_EXTRAS_TIMEOUT = 500; 348 349 // Maximum number of persisted Uri grants a package is allowed 350 static final int MAX_PERSISTED_URI_GRANTS = 128; 351 352 static final int MY_PID = Process.myPid(); 353 354 static final String[] EMPTY_STRING_ARRAY = new String[0]; 355 356 // How many bytes to write into the dropbox log before truncating 357 static final int DROPBOX_MAX_SIZE = 256 * 1024; 358 359 // Access modes for handleIncomingUser. 360 static final int ALLOW_NON_FULL = 0; 361 static final int ALLOW_NON_FULL_IN_PROFILE = 1; 362 static final int ALLOW_FULL_ONLY = 2; 363 364 static final int LAST_PREBOOT_DELIVERED_FILE_VERSION = 10000; 365 366 /** All system services */ 367 SystemServiceManager mSystemServiceManager; 368 369 /** Run all ActivityStacks through this */ 370 ActivityStackSupervisor mStackSupervisor; 371 372 public IntentFirewall mIntentFirewall; 373 374 // Whether we should show our dialogs (ANR, crash, etc) or just perform their 375 // default actuion automatically. Important for devices without direct input 376 // devices. 377 private boolean mShowDialogs = true; 378 379 BroadcastQueue mFgBroadcastQueue; 380 BroadcastQueue mBgBroadcastQueue; 381 // Convenient for easy iteration over the queues. Foreground is first 382 // so that dispatch of foreground broadcasts gets precedence. 383 final BroadcastQueue[] mBroadcastQueues = new BroadcastQueue[2]; 384 385 BroadcastQueue broadcastQueueForIntent(Intent intent) { 386 final boolean isFg = (intent.getFlags() & Intent.FLAG_RECEIVER_FOREGROUND) != 0; 387 if (DEBUG_BACKGROUND_BROADCAST) { 388 Slog.i(TAG, "Broadcast intent " + intent + " on " 389 + (isFg ? "foreground" : "background") 390 + " queue"); 391 } 392 return (isFg) ? mFgBroadcastQueue : mBgBroadcastQueue; 393 } 394 395 BroadcastRecord broadcastRecordForReceiverLocked(IBinder receiver) { 396 for (BroadcastQueue queue : mBroadcastQueues) { 397 BroadcastRecord r = queue.getMatchingOrderedReceiver(receiver); 398 if (r != null) { 399 return r; 400 } 401 } 402 return null; 403 } 404 405 /** 406 * Activity we have told the window manager to have key focus. 407 */ 408 ActivityRecord mFocusedActivity = null; 409 410 /** 411 * List of intents that were used to start the most recent tasks. 412 */ 413 ArrayList<TaskRecord> mRecentTasks; 414 ArraySet<TaskRecord> mTmpRecents = new ArraySet<TaskRecord>(); 415 416 /** 417 * For addAppTask: cached of the last activity component that was added. 418 */ 419 ComponentName mLastAddedTaskComponent; 420 421 /** 422 * For addAppTask: cached of the last activity uid that was added. 423 */ 424 int mLastAddedTaskUid; 425 426 /** 427 * For addAppTask: cached of the last ActivityInfo that was added. 428 */ 429 ActivityInfo mLastAddedTaskActivity; 430 431 public class PendingAssistExtras extends Binder implements Runnable { 432 public final ActivityRecord activity; 433 public boolean haveResult = false; 434 public Bundle result = null; 435 public PendingAssistExtras(ActivityRecord _activity) { 436 activity = _activity; 437 } 438 @Override 439 public void run() { 440 Slog.w(TAG, "getAssistContextExtras failed: timeout retrieving from " + activity); 441 synchronized (this) { 442 haveResult = true; 443 notifyAll(); 444 } 445 } 446 } 447 448 final ArrayList<PendingAssistExtras> mPendingAssistExtras 449 = new ArrayList<PendingAssistExtras>(); 450 451 /** 452 * Process management. 453 */ 454 final ProcessList mProcessList = new ProcessList(); 455 456 /** 457 * All of the applications we currently have running organized by name. 458 * The keys are strings of the application package name (as 459 * returned by the package manager), and the keys are ApplicationRecord 460 * objects. 461 */ 462 final ProcessMap<ProcessRecord> mProcessNames = new ProcessMap<ProcessRecord>(); 463 464 /** 465 * Tracking long-term execution of processes to look for abuse and other 466 * bad app behavior. 467 */ 468 final ProcessStatsService mProcessStats; 469 470 /** 471 * The currently running isolated processes. 472 */ 473 final SparseArray<ProcessRecord> mIsolatedProcesses = new SparseArray<ProcessRecord>(); 474 475 /** 476 * Counter for assigning isolated process uids, to avoid frequently reusing the 477 * same ones. 478 */ 479 int mNextIsolatedProcessUid = 0; 480 481 /** 482 * The currently running heavy-weight process, if any. 483 */ 484 ProcessRecord mHeavyWeightProcess = null; 485 486 /** 487 * The last time that various processes have crashed. 488 */ 489 final ProcessMap<Long> mProcessCrashTimes = new ProcessMap<Long>(); 490 491 /** 492 * Information about a process that is currently marked as bad. 493 */ 494 static final class BadProcessInfo { 495 BadProcessInfo(long time, String shortMsg, String longMsg, String stack) { 496 this.time = time; 497 this.shortMsg = shortMsg; 498 this.longMsg = longMsg; 499 this.stack = stack; 500 } 501 502 final long time; 503 final String shortMsg; 504 final String longMsg; 505 final String stack; 506 } 507 508 /** 509 * Set of applications that we consider to be bad, and will reject 510 * incoming broadcasts from (which the user has no control over). 511 * Processes are added to this set when they have crashed twice within 512 * a minimum amount of time; they are removed from it when they are 513 * later restarted (hopefully due to some user action). The value is the 514 * time it was added to the list. 515 */ 516 final ProcessMap<BadProcessInfo> mBadProcesses = new ProcessMap<BadProcessInfo>(); 517 518 /** 519 * All of the processes we currently have running organized by pid. 520 * The keys are the pid running the application. 521 * 522 * <p>NOTE: This object is protected by its own lock, NOT the global 523 * activity manager lock! 524 */ 525 final SparseArray<ProcessRecord> mPidsSelfLocked = new SparseArray<ProcessRecord>(); 526 527 /** 528 * All of the processes that have been forced to be foreground. The key 529 * is the pid of the caller who requested it (we hold a death 530 * link on it). 531 */ 532 abstract class ForegroundToken implements IBinder.DeathRecipient { 533 int pid; 534 IBinder token; 535 } 536 final SparseArray<ForegroundToken> mForegroundProcesses = new SparseArray<ForegroundToken>(); 537 538 /** 539 * List of records for processes that someone had tried to start before the 540 * system was ready. We don't start them at that point, but ensure they 541 * are started by the time booting is complete. 542 */ 543 final ArrayList<ProcessRecord> mProcessesOnHold = new ArrayList<ProcessRecord>(); 544 545 /** 546 * List of persistent applications that are in the process 547 * of being started. 548 */ 549 final ArrayList<ProcessRecord> mPersistentStartingProcesses = new ArrayList<ProcessRecord>(); 550 551 /** 552 * Processes that are being forcibly torn down. 553 */ 554 final ArrayList<ProcessRecord> mRemovedProcesses = new ArrayList<ProcessRecord>(); 555 556 /** 557 * List of running applications, sorted by recent usage. 558 * The first entry in the list is the least recently used. 559 */ 560 final ArrayList<ProcessRecord> mLruProcesses = new ArrayList<ProcessRecord>(); 561 562 /** 563 * Where in mLruProcesses that the processes hosting activities start. 564 */ 565 int mLruProcessActivityStart = 0; 566 567 /** 568 * Where in mLruProcesses that the processes hosting services start. 569 * This is after (lower index) than mLruProcessesActivityStart. 570 */ 571 int mLruProcessServiceStart = 0; 572 573 /** 574 * List of processes that should gc as soon as things are idle. 575 */ 576 final ArrayList<ProcessRecord> mProcessesToGc = new ArrayList<ProcessRecord>(); 577 578 /** 579 * Processes we want to collect PSS data from. 580 */ 581 final ArrayList<ProcessRecord> mPendingPssProcesses = new ArrayList<ProcessRecord>(); 582 583 /** 584 * Last time we requested PSS data of all processes. 585 */ 586 long mLastFullPssTime = SystemClock.uptimeMillis(); 587 588 /** 589 * If set, the next time we collect PSS data we should do a full collection 590 * with data from native processes and the kernel. 591 */ 592 boolean mFullPssPending = false; 593 594 /** 595 * This is the process holding what we currently consider to be 596 * the "home" activity. 597 */ 598 ProcessRecord mHomeProcess; 599 600 /** 601 * This is the process holding the activity the user last visited that 602 * is in a different process from the one they are currently in. 603 */ 604 ProcessRecord mPreviousProcess; 605 606 /** 607 * The time at which the previous process was last visible. 608 */ 609 long mPreviousProcessVisibleTime; 610 611 /** 612 * Which uses have been started, so are allowed to run code. 613 */ 614 final SparseArray<UserStartedState> mStartedUsers = new SparseArray<UserStartedState>(); 615 616 /** 617 * LRU list of history of current users. Most recently current is at the end. 618 */ 619 final ArrayList<Integer> mUserLru = new ArrayList<Integer>(); 620 621 /** 622 * Constant array of the users that are currently started. 623 */ 624 int[] mStartedUserArray = new int[] { 0 }; 625 626 /** 627 * Registered observers of the user switching mechanics. 628 */ 629 final RemoteCallbackList<IUserSwitchObserver> mUserSwitchObservers 630 = new RemoteCallbackList<IUserSwitchObserver>(); 631 632 /** 633 * Currently active user switch. 634 */ 635 Object mCurUserSwitchCallback; 636 637 /** 638 * Packages that the user has asked to have run in screen size 639 * compatibility mode instead of filling the screen. 640 */ 641 final CompatModePackages mCompatModePackages; 642 643 /** 644 * Set of IntentSenderRecord objects that are currently active. 645 */ 646 final HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>> mIntentSenderRecords 647 = new HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>>(); 648 649 /** 650 * Fingerprints (hashCode()) of stack traces that we've 651 * already logged DropBox entries for. Guarded by itself. If 652 * something (rogue user app) forces this over 653 * MAX_DUP_SUPPRESSED_STACKS entries, the contents are cleared. 654 */ 655 private final HashSet<Integer> mAlreadyLoggedViolatedStacks = new HashSet<Integer>(); 656 private static final int MAX_DUP_SUPPRESSED_STACKS = 5000; 657 658 /** 659 * Strict Mode background batched logging state. 660 * 661 * The string buffer is guarded by itself, and its lock is also 662 * used to determine if another batched write is already 663 * in-flight. 664 */ 665 private final StringBuilder mStrictModeBuffer = new StringBuilder(); 666 667 /** 668 * Keeps track of all IIntentReceivers that have been registered for 669 * broadcasts. Hash keys are the receiver IBinder, hash value is 670 * a ReceiverList. 671 */ 672 final HashMap<IBinder, ReceiverList> mRegisteredReceivers = 673 new HashMap<IBinder, ReceiverList>(); 674 675 /** 676 * Resolver for broadcast intents to registered receivers. 677 * Holds BroadcastFilter (subclass of IntentFilter). 678 */ 679 final IntentResolver<BroadcastFilter, BroadcastFilter> mReceiverResolver 680 = new IntentResolver<BroadcastFilter, BroadcastFilter>() { 681 @Override 682 protected boolean allowFilterResult( 683 BroadcastFilter filter, List<BroadcastFilter> dest) { 684 IBinder target = filter.receiverList.receiver.asBinder(); 685 for (int i=dest.size()-1; i>=0; i--) { 686 if (dest.get(i).receiverList.receiver.asBinder() == target) { 687 return false; 688 } 689 } 690 return true; 691 } 692 693 @Override 694 protected BroadcastFilter newResult(BroadcastFilter filter, int match, int userId) { 695 if (userId == UserHandle.USER_ALL || filter.owningUserId == UserHandle.USER_ALL 696 || userId == filter.owningUserId) { 697 return super.newResult(filter, match, userId); 698 } 699 return null; 700 } 701 702 @Override 703 protected BroadcastFilter[] newArray(int size) { 704 return new BroadcastFilter[size]; 705 } 706 707 @Override 708 protected boolean isPackageForFilter(String packageName, BroadcastFilter filter) { 709 return packageName.equals(filter.packageName); 710 } 711 }; 712 713 /** 714 * State of all active sticky broadcasts per user. Keys are the action of the 715 * sticky Intent, values are an ArrayList of all broadcasted intents with 716 * that action (which should usually be one). The SparseArray is keyed 717 * by the user ID the sticky is for, and can include UserHandle.USER_ALL 718 * for stickies that are sent to all users. 719 */ 720 final SparseArray<ArrayMap<String, ArrayList<Intent>>> mStickyBroadcasts = 721 new SparseArray<ArrayMap<String, ArrayList<Intent>>>(); 722 723 final ActiveServices mServices; 724 725 /** 726 * Backup/restore process management 727 */ 728 String mBackupAppName = null; 729 BackupRecord mBackupTarget = null; 730 731 final ProviderMap mProviderMap; 732 733 /** 734 * List of content providers who have clients waiting for them. The 735 * application is currently being launched and the provider will be 736 * removed from this list once it is published. 737 */ 738 final ArrayList<ContentProviderRecord> mLaunchingProviders 739 = new ArrayList<ContentProviderRecord>(); 740 741 /** 742 * File storing persisted {@link #mGrantedUriPermissions}. 743 */ 744 private final AtomicFile mGrantFile; 745 746 /** XML constants used in {@link #mGrantFile} */ 747 private static final String TAG_URI_GRANTS = "uri-grants"; 748 private static final String TAG_URI_GRANT = "uri-grant"; 749 private static final String ATTR_USER_HANDLE = "userHandle"; 750 private static final String ATTR_SOURCE_USER_ID = "sourceUserId"; 751 private static final String ATTR_TARGET_USER_ID = "targetUserId"; 752 private static final String ATTR_SOURCE_PKG = "sourcePkg"; 753 private static final String ATTR_TARGET_PKG = "targetPkg"; 754 private static final String ATTR_URI = "uri"; 755 private static final String ATTR_MODE_FLAGS = "modeFlags"; 756 private static final String ATTR_CREATED_TIME = "createdTime"; 757 private static final String ATTR_PREFIX = "prefix"; 758 759 /** 760 * Global set of specific {@link Uri} permissions that have been granted. 761 * This optimized lookup structure maps from {@link UriPermission#targetUid} 762 * to {@link UriPermission#uri} to {@link UriPermission}. 763 */ 764 @GuardedBy("this") 765 private final SparseArray<ArrayMap<GrantUri, UriPermission>> 766 mGrantedUriPermissions = new SparseArray<ArrayMap<GrantUri, UriPermission>>(); 767 768 public static class GrantUri { 769 public final int sourceUserId; 770 public final Uri uri; 771 public boolean prefix; 772 773 public GrantUri(int sourceUserId, Uri uri, boolean prefix) { 774 this.sourceUserId = sourceUserId; 775 this.uri = uri; 776 this.prefix = prefix; 777 } 778 779 @Override 780 public int hashCode() { 781 return toString().hashCode(); 782 } 783 784 @Override 785 public boolean equals(Object o) { 786 if (o instanceof GrantUri) { 787 GrantUri other = (GrantUri) o; 788 return uri.equals(other.uri) && (sourceUserId == other.sourceUserId) 789 && prefix == other.prefix; 790 } 791 return false; 792 } 793 794 @Override 795 public String toString() { 796 String result = Integer.toString(sourceUserId) + " @ " + uri.toString(); 797 if (prefix) result += " [prefix]"; 798 return result; 799 } 800 801 public String toSafeString() { 802 String result = Integer.toString(sourceUserId) + " @ " + uri.toSafeString(); 803 if (prefix) result += " [prefix]"; 804 return result; 805 } 806 807 public static GrantUri resolve(int defaultSourceUserHandle, Uri uri) { 808 return new GrantUri(ContentProvider.getUserIdFromUri(uri, defaultSourceUserHandle), 809 ContentProvider.getUriWithoutUserId(uri), false); 810 } 811 } 812 813 CoreSettingsObserver mCoreSettingsObserver; 814 815 /** 816 * Thread-local storage used to carry caller permissions over through 817 * indirect content-provider access. 818 */ 819 private class Identity { 820 public int pid; 821 public int uid; 822 823 Identity(int _pid, int _uid) { 824 pid = _pid; 825 uid = _uid; 826 } 827 } 828 829 private static final ThreadLocal<Identity> sCallerIdentity = new ThreadLocal<Identity>(); 830 831 /** 832 * All information we have collected about the runtime performance of 833 * any user id that can impact battery performance. 834 */ 835 final BatteryStatsService mBatteryStatsService; 836 837 /** 838 * Information about component usage 839 */ 840 UsageStatsManagerInternal mUsageStatsService; 841 842 /** 843 * Information about and control over application operations 844 */ 845 final AppOpsService mAppOpsService; 846 847 /** 848 * Save recent tasks information across reboots. 849 */ 850 final TaskPersister mTaskPersister; 851 852 /** 853 * Current configuration information. HistoryRecord objects are given 854 * a reference to this object to indicate which configuration they are 855 * currently running in, so this object must be kept immutable. 856 */ 857 Configuration mConfiguration = new Configuration(); 858 859 /** 860 * Current sequencing integer of the configuration, for skipping old 861 * configurations. 862 */ 863 int mConfigurationSeq = 0; 864 865 /** 866 * Hardware-reported OpenGLES version. 867 */ 868 final int GL_ES_VERSION; 869 870 /** 871 * List of initialization arguments to pass to all processes when binding applications to them. 872 * For example, references to the commonly used services. 873 */ 874 HashMap<String, IBinder> mAppBindArgs; 875 876 /** 877 * Temporary to avoid allocations. Protected by main lock. 878 */ 879 final StringBuilder mStringBuilder = new StringBuilder(256); 880 881 /** 882 * Used to control how we initialize the service. 883 */ 884 ComponentName mTopComponent; 885 String mTopAction = Intent.ACTION_MAIN; 886 String mTopData; 887 boolean mProcessesReady = false; 888 boolean mSystemReady = false; 889 boolean mBooting = false; 890 boolean mWaitingUpdate = false; 891 boolean mDidUpdate = false; 892 boolean mOnBattery = false; 893 boolean mLaunchWarningShown = false; 894 895 Context mContext; 896 897 int mFactoryTest; 898 899 boolean mCheckedForSetup; 900 901 /** 902 * The time at which we will allow normal application switches again, 903 * after a call to {@link #stopAppSwitches()}. 904 */ 905 long mAppSwitchesAllowedTime; 906 907 /** 908 * This is set to true after the first switch after mAppSwitchesAllowedTime 909 * is set; any switches after that will clear the time. 910 */ 911 boolean mDidAppSwitch; 912 913 /** 914 * Last time (in realtime) at which we checked for power usage. 915 */ 916 long mLastPowerCheckRealtime; 917 918 /** 919 * Last time (in uptime) at which we checked for power usage. 920 */ 921 long mLastPowerCheckUptime; 922 923 /** 924 * Set while we are wanting to sleep, to prevent any 925 * activities from being started/resumed. 926 */ 927 private boolean mSleeping = false; 928 929 /** 930 * Set while we are running a voice interaction. This overrides 931 * sleeping while it is active. 932 */ 933 private boolean mRunningVoice = false; 934 935 /** 936 * State of external calls telling us if the device is asleep. 937 */ 938 private boolean mWentToSleep = false; 939 940 /** 941 * State of external call telling us if the lock screen is shown. 942 */ 943 private boolean mLockScreenShown = false; 944 945 /** 946 * Set if we are shutting down the system, similar to sleeping. 947 */ 948 boolean mShuttingDown = false; 949 950 /** 951 * Current sequence id for oom_adj computation traversal. 952 */ 953 int mAdjSeq = 0; 954 955 /** 956 * Current sequence id for process LRU updating. 957 */ 958 int mLruSeq = 0; 959 960 /** 961 * Keep track of the non-cached/empty process we last found, to help 962 * determine how to distribute cached/empty processes next time. 963 */ 964 int mNumNonCachedProcs = 0; 965 966 /** 967 * Keep track of the number of cached hidden procs, to balance oom adj 968 * distribution between those and empty procs. 969 */ 970 int mNumCachedHiddenProcs = 0; 971 972 /** 973 * Keep track of the number of service processes we last found, to 974 * determine on the next iteration which should be B services. 975 */ 976 int mNumServiceProcs = 0; 977 int mNewNumAServiceProcs = 0; 978 int mNewNumServiceProcs = 0; 979 980 /** 981 * Allow the current computed overall memory level of the system to go down? 982 * This is set to false when we are killing processes for reasons other than 983 * memory management, so that the now smaller process list will not be taken as 984 * an indication that memory is tighter. 985 */ 986 boolean mAllowLowerMemLevel = false; 987 988 /** 989 * The last computed memory level, for holding when we are in a state that 990 * processes are going away for other reasons. 991 */ 992 int mLastMemoryLevel = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 993 994 /** 995 * The last total number of process we have, to determine if changes actually look 996 * like a shrinking number of process due to lower RAM. 997 */ 998 int mLastNumProcesses; 999 1000 /** 1001 * The uptime of the last time we performed idle maintenance. 1002 */ 1003 long mLastIdleTime = SystemClock.uptimeMillis(); 1004 1005 /** 1006 * Total time spent with RAM that has been added in the past since the last idle time. 1007 */ 1008 long mLowRamTimeSinceLastIdle = 0; 1009 1010 /** 1011 * If RAM is currently low, when that horrible situation started. 1012 */ 1013 long mLowRamStartTime = 0; 1014 1015 /** 1016 * For reporting to battery stats the current top application. 1017 */ 1018 private String mCurResumedPackage = null; 1019 private int mCurResumedUid = -1; 1020 1021 /** 1022 * For reporting to battery stats the apps currently running foreground 1023 * service. The ProcessMap is package/uid tuples; each of these contain 1024 * an array of the currently foreground processes. 1025 */ 1026 final ProcessMap<ArrayList<ProcessRecord>> mForegroundPackages 1027 = new ProcessMap<ArrayList<ProcessRecord>>(); 1028 1029 /** 1030 * This is set if we had to do a delayed dexopt of an app before launching 1031 * it, to increase the ANR timeouts in that case. 1032 */ 1033 boolean mDidDexOpt; 1034 1035 /** 1036 * Set if the systemServer made a call to enterSafeMode. 1037 */ 1038 boolean mSafeMode; 1039 1040 String mDebugApp = null; 1041 boolean mWaitForDebugger = false; 1042 boolean mDebugTransient = false; 1043 String mOrigDebugApp = null; 1044 boolean mOrigWaitForDebugger = false; 1045 boolean mAlwaysFinishActivities = false; 1046 IActivityController mController = null; 1047 String mProfileApp = null; 1048 ProcessRecord mProfileProc = null; 1049 String mProfileFile; 1050 ParcelFileDescriptor mProfileFd; 1051 int mSamplingInterval = 0; 1052 boolean mAutoStopProfiler = false; 1053 int mProfileType = 0; 1054 String mOpenGlTraceApp = null; 1055 1056 static class ProcessChangeItem { 1057 static final int CHANGE_ACTIVITIES = 1<<0; 1058 static final int CHANGE_PROCESS_STATE = 1<<1; 1059 int changes; 1060 int uid; 1061 int pid; 1062 int processState; 1063 boolean foregroundActivities; 1064 } 1065 1066 final RemoteCallbackList<IProcessObserver> mProcessObservers 1067 = new RemoteCallbackList<IProcessObserver>(); 1068 ProcessChangeItem[] mActiveProcessChanges = new ProcessChangeItem[5]; 1069 1070 final ArrayList<ProcessChangeItem> mPendingProcessChanges 1071 = new ArrayList<ProcessChangeItem>(); 1072 final ArrayList<ProcessChangeItem> mAvailProcessChanges 1073 = new ArrayList<ProcessChangeItem>(); 1074 1075 /** 1076 * Runtime CPU use collection thread. This object's lock is used to 1077 * protect all related state. 1078 */ 1079 final Thread mProcessCpuThread; 1080 1081 /** 1082 * Used to collect process stats when showing not responding dialog. 1083 * Protected by mProcessCpuThread. 1084 */ 1085 final ProcessCpuTracker mProcessCpuTracker = new ProcessCpuTracker( 1086 MONITOR_THREAD_CPU_USAGE); 1087 final AtomicLong mLastCpuTime = new AtomicLong(0); 1088 final AtomicBoolean mProcessCpuMutexFree = new AtomicBoolean(true); 1089 1090 long mLastWriteTime = 0; 1091 1092 /** 1093 * Used to retain an update lock when the foreground activity is in 1094 * immersive mode. 1095 */ 1096 final UpdateLock mUpdateLock = new UpdateLock("immersive"); 1097 1098 /** 1099 * Set to true after the system has finished booting. 1100 */ 1101 boolean mBooted = false; 1102 1103 int mProcessLimit = ProcessList.MAX_CACHED_APPS; 1104 int mProcessLimitOverride = -1; 1105 1106 WindowManagerService mWindowManager; 1107 1108 final ActivityThread mSystemThread; 1109 1110 // Holds the current foreground user's id 1111 int mCurrentUserId = 0; 1112 // Holds the target user's id during a user switch 1113 int mTargetUserId = UserHandle.USER_NULL; 1114 // If there are multiple profiles for the current user, their ids are here 1115 // Currently only the primary user can have managed profiles 1116 int[] mCurrentProfileIds = new int[] {UserHandle.USER_OWNER}; // Accessed by ActivityStack 1117 1118 /** 1119 * Mapping from each known user ID to the profile group ID it is associated with. 1120 */ 1121 SparseIntArray mUserProfileGroupIdsSelfLocked = new SparseIntArray(); 1122 1123 private UserManagerService mUserManager; 1124 1125 private final class AppDeathRecipient implements IBinder.DeathRecipient { 1126 final ProcessRecord mApp; 1127 final int mPid; 1128 final IApplicationThread mAppThread; 1129 1130 AppDeathRecipient(ProcessRecord app, int pid, 1131 IApplicationThread thread) { 1132 if (localLOGV) Slog.v( 1133 TAG, "New death recipient " + this 1134 + " for thread " + thread.asBinder()); 1135 mApp = app; 1136 mPid = pid; 1137 mAppThread = thread; 1138 } 1139 1140 @Override 1141 public void binderDied() { 1142 if (localLOGV) Slog.v( 1143 TAG, "Death received in " + this 1144 + " for thread " + mAppThread.asBinder()); 1145 synchronized(ActivityManagerService.this) { 1146 appDiedLocked(mApp, mPid, mAppThread); 1147 } 1148 } 1149 } 1150 1151 static final int SHOW_ERROR_MSG = 1; 1152 static final int SHOW_NOT_RESPONDING_MSG = 2; 1153 static final int SHOW_FACTORY_ERROR_MSG = 3; 1154 static final int UPDATE_CONFIGURATION_MSG = 4; 1155 static final int GC_BACKGROUND_PROCESSES_MSG = 5; 1156 static final int WAIT_FOR_DEBUGGER_MSG = 6; 1157 static final int SERVICE_TIMEOUT_MSG = 12; 1158 static final int UPDATE_TIME_ZONE = 13; 1159 static final int SHOW_UID_ERROR_MSG = 14; 1160 static final int IM_FEELING_LUCKY_MSG = 15; 1161 static final int PROC_START_TIMEOUT_MSG = 20; 1162 static final int DO_PENDING_ACTIVITY_LAUNCHES_MSG = 21; 1163 static final int KILL_APPLICATION_MSG = 22; 1164 static final int FINALIZE_PENDING_INTENT_MSG = 23; 1165 static final int POST_HEAVY_NOTIFICATION_MSG = 24; 1166 static final int CANCEL_HEAVY_NOTIFICATION_MSG = 25; 1167 static final int SHOW_STRICT_MODE_VIOLATION_MSG = 26; 1168 static final int CHECK_EXCESSIVE_WAKE_LOCKS_MSG = 27; 1169 static final int CLEAR_DNS_CACHE_MSG = 28; 1170 static final int UPDATE_HTTP_PROXY_MSG = 29; 1171 static final int SHOW_COMPAT_MODE_DIALOG_MSG = 30; 1172 static final int DISPATCH_PROCESSES_CHANGED = 31; 1173 static final int DISPATCH_PROCESS_DIED = 32; 1174 static final int REPORT_MEM_USAGE_MSG = 33; 1175 static final int REPORT_USER_SWITCH_MSG = 34; 1176 static final int CONTINUE_USER_SWITCH_MSG = 35; 1177 static final int USER_SWITCH_TIMEOUT_MSG = 36; 1178 static final int IMMERSIVE_MODE_LOCK_MSG = 37; 1179 static final int PERSIST_URI_GRANTS_MSG = 38; 1180 static final int REQUEST_ALL_PSS_MSG = 39; 1181 static final int START_PROFILES_MSG = 40; 1182 static final int UPDATE_TIME = 41; 1183 static final int SYSTEM_USER_START_MSG = 42; 1184 static final int SYSTEM_USER_CURRENT_MSG = 43; 1185 static final int ENTER_ANIMATION_COMPLETE_MSG = 44; 1186 static final int ENABLE_SCREEN_AFTER_BOOT_MSG = 45; 1187 static final int START_USER_SWITCH_MSG = 46; 1188 1189 static final int FIRST_ACTIVITY_STACK_MSG = 100; 1190 static final int FIRST_BROADCAST_QUEUE_MSG = 200; 1191 static final int FIRST_COMPAT_MODE_MSG = 300; 1192 static final int FIRST_SUPERVISOR_STACK_MSG = 100; 1193 1194 AlertDialog mUidAlert; 1195 CompatModeDialog mCompatModeDialog; 1196 long mLastMemUsageReportTime = 0; 1197 1198 private LockToAppRequestDialog mLockToAppRequest; 1199 1200 /** 1201 * Flag whether the current user is a "monkey", i.e. whether 1202 * the UI is driven by a UI automation tool. 1203 */ 1204 private boolean mUserIsMonkey; 1205 1206 /** Flag whether the device has a Recents UI */ 1207 boolean mHasRecents; 1208 1209 /** The dimensions of the thumbnails in the Recents UI. */ 1210 int mThumbnailWidth; 1211 int mThumbnailHeight; 1212 1213 final ServiceThread mHandlerThread; 1214 final MainHandler mHandler; 1215 1216 final class MainHandler extends Handler { 1217 public MainHandler(Looper looper) { 1218 super(looper, null, true); 1219 } 1220 1221 @Override 1222 public void handleMessage(Message msg) { 1223 switch (msg.what) { 1224 case SHOW_ERROR_MSG: { 1225 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1226 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 1227 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 1228 synchronized (ActivityManagerService.this) { 1229 ProcessRecord proc = (ProcessRecord)data.get("app"); 1230 AppErrorResult res = (AppErrorResult) data.get("result"); 1231 if (proc != null && proc.crashDialog != null) { 1232 Slog.e(TAG, "App already has crash dialog: " + proc); 1233 if (res != null) { 1234 res.set(0); 1235 } 1236 return; 1237 } 1238 boolean isBackground = (UserHandle.getAppId(proc.uid) 1239 >= Process.FIRST_APPLICATION_UID 1240 && proc.pid != MY_PID); 1241 for (int userId : mCurrentProfileIds) { 1242 isBackground &= (proc.userId != userId); 1243 } 1244 if (isBackground && !showBackground) { 1245 Slog.w(TAG, "Skipping crash dialog of " + proc + ": background"); 1246 if (res != null) { 1247 res.set(0); 1248 } 1249 return; 1250 } 1251 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1252 Dialog d = new AppErrorDialog(mContext, 1253 ActivityManagerService.this, res, proc); 1254 d.show(); 1255 proc.crashDialog = d; 1256 } else { 1257 // The device is asleep, so just pretend that the user 1258 // saw a crash dialog and hit "force quit". 1259 if (res != null) { 1260 res.set(0); 1261 } 1262 } 1263 } 1264 1265 ensureBootCompleted(); 1266 } break; 1267 case SHOW_NOT_RESPONDING_MSG: { 1268 synchronized (ActivityManagerService.this) { 1269 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1270 ProcessRecord proc = (ProcessRecord)data.get("app"); 1271 if (proc != null && proc.anrDialog != null) { 1272 Slog.e(TAG, "App already has anr dialog: " + proc); 1273 return; 1274 } 1275 1276 Intent intent = new Intent("android.intent.action.ANR"); 1277 if (!mProcessesReady) { 1278 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 1279 | Intent.FLAG_RECEIVER_FOREGROUND); 1280 } 1281 broadcastIntentLocked(null, null, intent, 1282 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 1283 false, false, MY_PID, Process.SYSTEM_UID, 0 /* TODO: Verify */); 1284 1285 if (mShowDialogs) { 1286 Dialog d = new AppNotRespondingDialog(ActivityManagerService.this, 1287 mContext, proc, (ActivityRecord)data.get("activity"), 1288 msg.arg1 != 0); 1289 d.show(); 1290 proc.anrDialog = d; 1291 } else { 1292 // Just kill the app if there is no dialog to be shown. 1293 killAppAtUsersRequest(proc, null); 1294 } 1295 } 1296 1297 ensureBootCompleted(); 1298 } break; 1299 case SHOW_STRICT_MODE_VIOLATION_MSG: { 1300 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1301 synchronized (ActivityManagerService.this) { 1302 ProcessRecord proc = (ProcessRecord) data.get("app"); 1303 if (proc == null) { 1304 Slog.e(TAG, "App not found when showing strict mode dialog."); 1305 break; 1306 } 1307 if (proc.crashDialog != null) { 1308 Slog.e(TAG, "App already has strict mode dialog: " + proc); 1309 return; 1310 } 1311 AppErrorResult res = (AppErrorResult) data.get("result"); 1312 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1313 Dialog d = new StrictModeViolationDialog(mContext, 1314 ActivityManagerService.this, res, proc); 1315 d.show(); 1316 proc.crashDialog = d; 1317 } else { 1318 // The device is asleep, so just pretend that the user 1319 // saw a crash dialog and hit "force quit". 1320 res.set(0); 1321 } 1322 } 1323 ensureBootCompleted(); 1324 } break; 1325 case SHOW_FACTORY_ERROR_MSG: { 1326 Dialog d = new FactoryErrorDialog( 1327 mContext, msg.getData().getCharSequence("msg")); 1328 d.show(); 1329 ensureBootCompleted(); 1330 } break; 1331 case UPDATE_CONFIGURATION_MSG: { 1332 final ContentResolver resolver = mContext.getContentResolver(); 1333 Settings.System.putConfiguration(resolver, (Configuration)msg.obj); 1334 } break; 1335 case GC_BACKGROUND_PROCESSES_MSG: { 1336 synchronized (ActivityManagerService.this) { 1337 performAppGcsIfAppropriateLocked(); 1338 } 1339 } break; 1340 case WAIT_FOR_DEBUGGER_MSG: { 1341 synchronized (ActivityManagerService.this) { 1342 ProcessRecord app = (ProcessRecord)msg.obj; 1343 if (msg.arg1 != 0) { 1344 if (!app.waitedForDebugger) { 1345 Dialog d = new AppWaitingForDebuggerDialog( 1346 ActivityManagerService.this, 1347 mContext, app); 1348 app.waitDialog = d; 1349 app.waitedForDebugger = true; 1350 d.show(); 1351 } 1352 } else { 1353 if (app.waitDialog != null) { 1354 app.waitDialog.dismiss(); 1355 app.waitDialog = null; 1356 } 1357 } 1358 } 1359 } break; 1360 case SERVICE_TIMEOUT_MSG: { 1361 if (mDidDexOpt) { 1362 mDidDexOpt = false; 1363 Message nmsg = mHandler.obtainMessage(SERVICE_TIMEOUT_MSG); 1364 nmsg.obj = msg.obj; 1365 mHandler.sendMessageDelayed(nmsg, ActiveServices.SERVICE_TIMEOUT); 1366 return; 1367 } 1368 mServices.serviceTimeout((ProcessRecord)msg.obj); 1369 } break; 1370 case UPDATE_TIME_ZONE: { 1371 synchronized (ActivityManagerService.this) { 1372 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1373 ProcessRecord r = mLruProcesses.get(i); 1374 if (r.thread != null) { 1375 try { 1376 r.thread.updateTimeZone(); 1377 } catch (RemoteException ex) { 1378 Slog.w(TAG, "Failed to update time zone for: " + r.info.processName); 1379 } 1380 } 1381 } 1382 } 1383 } break; 1384 case CLEAR_DNS_CACHE_MSG: { 1385 synchronized (ActivityManagerService.this) { 1386 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1387 ProcessRecord r = mLruProcesses.get(i); 1388 if (r.thread != null) { 1389 try { 1390 r.thread.clearDnsCache(); 1391 } catch (RemoteException ex) { 1392 Slog.w(TAG, "Failed to clear dns cache for: " + r.info.processName); 1393 } 1394 } 1395 } 1396 } 1397 } break; 1398 case UPDATE_HTTP_PROXY_MSG: { 1399 ProxyInfo proxy = (ProxyInfo)msg.obj; 1400 String host = ""; 1401 String port = ""; 1402 String exclList = ""; 1403 Uri pacFileUrl = Uri.EMPTY; 1404 if (proxy != null) { 1405 host = proxy.getHost(); 1406 port = Integer.toString(proxy.getPort()); 1407 exclList = proxy.getExclusionListAsString(); 1408 pacFileUrl = proxy.getPacFileUrl(); 1409 } 1410 synchronized (ActivityManagerService.this) { 1411 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1412 ProcessRecord r = mLruProcesses.get(i); 1413 if (r.thread != null) { 1414 try { 1415 r.thread.setHttpProxy(host, port, exclList, pacFileUrl); 1416 } catch (RemoteException ex) { 1417 Slog.w(TAG, "Failed to update http proxy for: " + 1418 r.info.processName); 1419 } 1420 } 1421 } 1422 } 1423 } break; 1424 case SHOW_UID_ERROR_MSG: { 1425 String title = "System UIDs Inconsistent"; 1426 String text = "UIDs on the system are inconsistent, you need to wipe your" 1427 + " data partition or your device will be unstable."; 1428 Log.e(TAG, title + ": " + text); 1429 if (mShowDialogs) { 1430 // XXX This is a temporary dialog, no need to localize. 1431 AlertDialog d = new BaseErrorDialog(mContext); 1432 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 1433 d.setCancelable(false); 1434 d.setTitle(title); 1435 d.setMessage(text); 1436 d.setButton(DialogInterface.BUTTON_POSITIVE, "I'm Feeling Lucky", 1437 mHandler.obtainMessage(IM_FEELING_LUCKY_MSG)); 1438 mUidAlert = d; 1439 d.show(); 1440 } 1441 } break; 1442 case IM_FEELING_LUCKY_MSG: { 1443 if (mUidAlert != null) { 1444 mUidAlert.dismiss(); 1445 mUidAlert = null; 1446 } 1447 } break; 1448 case PROC_START_TIMEOUT_MSG: { 1449 if (mDidDexOpt) { 1450 mDidDexOpt = false; 1451 Message nmsg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 1452 nmsg.obj = msg.obj; 1453 mHandler.sendMessageDelayed(nmsg, PROC_START_TIMEOUT); 1454 return; 1455 } 1456 ProcessRecord app = (ProcessRecord)msg.obj; 1457 synchronized (ActivityManagerService.this) { 1458 processStartTimedOutLocked(app); 1459 } 1460 } break; 1461 case DO_PENDING_ACTIVITY_LAUNCHES_MSG: { 1462 synchronized (ActivityManagerService.this) { 1463 mStackSupervisor.doPendingActivityLaunchesLocked(true); 1464 } 1465 } break; 1466 case KILL_APPLICATION_MSG: { 1467 synchronized (ActivityManagerService.this) { 1468 int appid = msg.arg1; 1469 boolean restart = (msg.arg2 == 1); 1470 Bundle bundle = (Bundle)msg.obj; 1471 String pkg = bundle.getString("pkg"); 1472 String reason = bundle.getString("reason"); 1473 forceStopPackageLocked(pkg, appid, restart, false, true, false, 1474 false, UserHandle.USER_ALL, reason); 1475 } 1476 } break; 1477 case FINALIZE_PENDING_INTENT_MSG: { 1478 ((PendingIntentRecord)msg.obj).completeFinalize(); 1479 } break; 1480 case POST_HEAVY_NOTIFICATION_MSG: { 1481 INotificationManager inm = NotificationManager.getService(); 1482 if (inm == null) { 1483 return; 1484 } 1485 1486 ActivityRecord root = (ActivityRecord)msg.obj; 1487 ProcessRecord process = root.app; 1488 if (process == null) { 1489 return; 1490 } 1491 1492 try { 1493 Context context = mContext.createPackageContext(process.info.packageName, 0); 1494 String text = mContext.getString(R.string.heavy_weight_notification, 1495 context.getApplicationInfo().loadLabel(context.getPackageManager())); 1496 Notification notification = new Notification(); 1497 notification.icon = com.android.internal.R.drawable.stat_sys_adb; //context.getApplicationInfo().icon; 1498 notification.when = 0; 1499 notification.flags = Notification.FLAG_ONGOING_EVENT; 1500 notification.tickerText = text; 1501 notification.defaults = 0; // please be quiet 1502 notification.sound = null; 1503 notification.vibrate = null; 1504 notification.color = mContext.getResources().getColor( 1505 com.android.internal.R.color.system_notification_accent_color); 1506 notification.setLatestEventInfo(context, text, 1507 mContext.getText(R.string.heavy_weight_notification_detail), 1508 PendingIntent.getActivityAsUser(mContext, 0, root.intent, 1509 PendingIntent.FLAG_CANCEL_CURRENT, null, 1510 new UserHandle(root.userId))); 1511 1512 try { 1513 int[] outId = new int[1]; 1514 inm.enqueueNotificationWithTag("android", "android", null, 1515 R.string.heavy_weight_notification, 1516 notification, outId, root.userId); 1517 } catch (RuntimeException e) { 1518 Slog.w(ActivityManagerService.TAG, 1519 "Error showing notification for heavy-weight app", e); 1520 } catch (RemoteException e) { 1521 } 1522 } catch (NameNotFoundException e) { 1523 Slog.w(TAG, "Unable to create context for heavy notification", e); 1524 } 1525 } break; 1526 case CANCEL_HEAVY_NOTIFICATION_MSG: { 1527 INotificationManager inm = NotificationManager.getService(); 1528 if (inm == null) { 1529 return; 1530 } 1531 try { 1532 inm.cancelNotificationWithTag("android", null, 1533 R.string.heavy_weight_notification, msg.arg1); 1534 } catch (RuntimeException e) { 1535 Slog.w(ActivityManagerService.TAG, 1536 "Error canceling notification for service", e); 1537 } catch (RemoteException e) { 1538 } 1539 } break; 1540 case CHECK_EXCESSIVE_WAKE_LOCKS_MSG: { 1541 synchronized (ActivityManagerService.this) { 1542 checkExcessivePowerUsageLocked(true); 1543 removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1544 Message nmsg = obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1545 sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 1546 } 1547 } break; 1548 case SHOW_COMPAT_MODE_DIALOG_MSG: { 1549 synchronized (ActivityManagerService.this) { 1550 ActivityRecord ar = (ActivityRecord)msg.obj; 1551 if (mCompatModeDialog != null) { 1552 if (mCompatModeDialog.mAppInfo.packageName.equals( 1553 ar.info.applicationInfo.packageName)) { 1554 return; 1555 } 1556 mCompatModeDialog.dismiss(); 1557 mCompatModeDialog = null; 1558 } 1559 if (ar != null && false) { 1560 if (mCompatModePackages.getPackageAskCompatModeLocked( 1561 ar.packageName)) { 1562 int mode = mCompatModePackages.computeCompatModeLocked( 1563 ar.info.applicationInfo); 1564 if (mode == ActivityManager.COMPAT_MODE_DISABLED 1565 || mode == ActivityManager.COMPAT_MODE_ENABLED) { 1566 mCompatModeDialog = new CompatModeDialog( 1567 ActivityManagerService.this, mContext, 1568 ar.info.applicationInfo); 1569 mCompatModeDialog.show(); 1570 } 1571 } 1572 } 1573 } 1574 break; 1575 } 1576 case DISPATCH_PROCESSES_CHANGED: { 1577 dispatchProcessesChanged(); 1578 break; 1579 } 1580 case DISPATCH_PROCESS_DIED: { 1581 final int pid = msg.arg1; 1582 final int uid = msg.arg2; 1583 dispatchProcessDied(pid, uid); 1584 break; 1585 } 1586 case REPORT_MEM_USAGE_MSG: { 1587 final ArrayList<ProcessMemInfo> memInfos = (ArrayList<ProcessMemInfo>)msg.obj; 1588 Thread thread = new Thread() { 1589 @Override public void run() { 1590 final SparseArray<ProcessMemInfo> infoMap 1591 = new SparseArray<ProcessMemInfo>(memInfos.size()); 1592 for (int i=0, N=memInfos.size(); i<N; i++) { 1593 ProcessMemInfo mi = memInfos.get(i); 1594 infoMap.put(mi.pid, mi); 1595 } 1596 updateCpuStatsNow(); 1597 synchronized (mProcessCpuThread) { 1598 final int N = mProcessCpuTracker.countStats(); 1599 for (int i=0; i<N; i++) { 1600 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 1601 if (st.vsize > 0) { 1602 long pss = Debug.getPss(st.pid, null); 1603 if (pss > 0) { 1604 if (infoMap.indexOfKey(st.pid) < 0) { 1605 ProcessMemInfo mi = new ProcessMemInfo(st.name, st.pid, 1606 ProcessList.NATIVE_ADJ, -1, "native", null); 1607 mi.pss = pss; 1608 memInfos.add(mi); 1609 } 1610 } 1611 } 1612 } 1613 } 1614 1615 long totalPss = 0; 1616 for (int i=0, N=memInfos.size(); i<N; i++) { 1617 ProcessMemInfo mi = memInfos.get(i); 1618 if (mi.pss == 0) { 1619 mi.pss = Debug.getPss(mi.pid, null); 1620 } 1621 totalPss += mi.pss; 1622 } 1623 Collections.sort(memInfos, new Comparator<ProcessMemInfo>() { 1624 @Override public int compare(ProcessMemInfo lhs, ProcessMemInfo rhs) { 1625 if (lhs.oomAdj != rhs.oomAdj) { 1626 return lhs.oomAdj < rhs.oomAdj ? -1 : 1; 1627 } 1628 if (lhs.pss != rhs.pss) { 1629 return lhs.pss < rhs.pss ? 1 : -1; 1630 } 1631 return 0; 1632 } 1633 }); 1634 1635 StringBuilder tag = new StringBuilder(128); 1636 StringBuilder stack = new StringBuilder(128); 1637 tag.append("Low on memory -- "); 1638 appendMemBucket(tag, totalPss, "total", false); 1639 appendMemBucket(stack, totalPss, "total", true); 1640 1641 StringBuilder logBuilder = new StringBuilder(1024); 1642 logBuilder.append("Low on memory:\n"); 1643 1644 boolean firstLine = true; 1645 int lastOomAdj = Integer.MIN_VALUE; 1646 for (int i=0, N=memInfos.size(); i<N; i++) { 1647 ProcessMemInfo mi = memInfos.get(i); 1648 1649 if (mi.oomAdj != ProcessList.NATIVE_ADJ 1650 && (mi.oomAdj < ProcessList.SERVICE_ADJ 1651 || mi.oomAdj == ProcessList.HOME_APP_ADJ 1652 || mi.oomAdj == ProcessList.PREVIOUS_APP_ADJ)) { 1653 if (lastOomAdj != mi.oomAdj) { 1654 lastOomAdj = mi.oomAdj; 1655 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1656 tag.append(" / "); 1657 } 1658 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ) { 1659 if (firstLine) { 1660 stack.append(":"); 1661 firstLine = false; 1662 } 1663 stack.append("\n\t at "); 1664 } else { 1665 stack.append("$"); 1666 } 1667 } else { 1668 tag.append(" "); 1669 stack.append("$"); 1670 } 1671 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1672 appendMemBucket(tag, mi.pss, mi.name, false); 1673 } 1674 appendMemBucket(stack, mi.pss, mi.name, true); 1675 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ 1676 && ((i+1) >= N || memInfos.get(i+1).oomAdj != lastOomAdj)) { 1677 stack.append("("); 1678 for (int k=0; k<DUMP_MEM_OOM_ADJ.length; k++) { 1679 if (DUMP_MEM_OOM_ADJ[k] == mi.oomAdj) { 1680 stack.append(DUMP_MEM_OOM_LABEL[k]); 1681 stack.append(":"); 1682 stack.append(DUMP_MEM_OOM_ADJ[k]); 1683 } 1684 } 1685 stack.append(")"); 1686 } 1687 } 1688 1689 logBuilder.append(" "); 1690 logBuilder.append(ProcessList.makeOomAdjString(mi.oomAdj)); 1691 logBuilder.append(' '); 1692 logBuilder.append(ProcessList.makeProcStateString(mi.procState)); 1693 logBuilder.append(' '); 1694 ProcessList.appendRamKb(logBuilder, mi.pss); 1695 logBuilder.append(" kB: "); 1696 logBuilder.append(mi.name); 1697 logBuilder.append(" ("); 1698 logBuilder.append(mi.pid); 1699 logBuilder.append(") "); 1700 logBuilder.append(mi.adjType); 1701 logBuilder.append('\n'); 1702 if (mi.adjReason != null) { 1703 logBuilder.append(" "); 1704 logBuilder.append(mi.adjReason); 1705 logBuilder.append('\n'); 1706 } 1707 } 1708 1709 logBuilder.append(" "); 1710 ProcessList.appendRamKb(logBuilder, totalPss); 1711 logBuilder.append(" kB: TOTAL\n"); 1712 1713 long[] infos = new long[Debug.MEMINFO_COUNT]; 1714 Debug.getMemInfo(infos); 1715 logBuilder.append(" MemInfo: "); 1716 logBuilder.append(infos[Debug.MEMINFO_SLAB]).append(" kB slab, "); 1717 logBuilder.append(infos[Debug.MEMINFO_SHMEM]).append(" kB shmem, "); 1718 logBuilder.append(infos[Debug.MEMINFO_BUFFERS]).append(" kB buffers, "); 1719 logBuilder.append(infos[Debug.MEMINFO_CACHED]).append(" kB cached, "); 1720 logBuilder.append(infos[Debug.MEMINFO_FREE]).append(" kB free\n"); 1721 if (infos[Debug.MEMINFO_ZRAM_TOTAL] != 0) { 1722 logBuilder.append(" ZRAM: "); 1723 logBuilder.append(infos[Debug.MEMINFO_ZRAM_TOTAL]); 1724 logBuilder.append(" kB RAM, "); 1725 logBuilder.append(infos[Debug.MEMINFO_SWAP_TOTAL]); 1726 logBuilder.append(" kB swap total, "); 1727 logBuilder.append(infos[Debug.MEMINFO_SWAP_FREE]); 1728 logBuilder.append(" kB swap free\n"); 1729 } 1730 Slog.i(TAG, logBuilder.toString()); 1731 1732 StringBuilder dropBuilder = new StringBuilder(1024); 1733 /* 1734 StringWriter oomSw = new StringWriter(); 1735 PrintWriter oomPw = new FastPrintWriter(oomSw, false, 256); 1736 StringWriter catSw = new StringWriter(); 1737 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1738 String[] emptyArgs = new String[] { }; 1739 dumpApplicationMemoryUsage(null, oomPw, " ", emptyArgs, true, catPw); 1740 oomPw.flush(); 1741 String oomString = oomSw.toString(); 1742 */ 1743 dropBuilder.append(stack); 1744 dropBuilder.append('\n'); 1745 dropBuilder.append('\n'); 1746 dropBuilder.append(logBuilder); 1747 dropBuilder.append('\n'); 1748 /* 1749 dropBuilder.append(oomString); 1750 dropBuilder.append('\n'); 1751 */ 1752 StringWriter catSw = new StringWriter(); 1753 synchronized (ActivityManagerService.this) { 1754 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1755 String[] emptyArgs = new String[] { }; 1756 catPw.println(); 1757 dumpProcessesLocked(null, catPw, emptyArgs, 0, false, null); 1758 catPw.println(); 1759 mServices.dumpServicesLocked(null, catPw, emptyArgs, 0, 1760 false, false, null); 1761 catPw.println(); 1762 dumpActivitiesLocked(null, catPw, emptyArgs, 0, false, false, null); 1763 catPw.flush(); 1764 } 1765 dropBuilder.append(catSw.toString()); 1766 addErrorToDropBox("lowmem", null, "system_server", null, 1767 null, tag.toString(), dropBuilder.toString(), null, null); 1768 //Slog.i(TAG, "Sent to dropbox:"); 1769 //Slog.i(TAG, dropBuilder.toString()); 1770 synchronized (ActivityManagerService.this) { 1771 long now = SystemClock.uptimeMillis(); 1772 if (mLastMemUsageReportTime < now) { 1773 mLastMemUsageReportTime = now; 1774 } 1775 } 1776 } 1777 }; 1778 thread.start(); 1779 break; 1780 } 1781 case START_USER_SWITCH_MSG: { 1782 showUserSwitchDialog(msg.arg1, (String) msg.obj); 1783 break; 1784 } 1785 case REPORT_USER_SWITCH_MSG: { 1786 dispatchUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1787 break; 1788 } 1789 case CONTINUE_USER_SWITCH_MSG: { 1790 continueUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1791 break; 1792 } 1793 case USER_SWITCH_TIMEOUT_MSG: { 1794 timeoutUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1795 break; 1796 } 1797 case IMMERSIVE_MODE_LOCK_MSG: { 1798 final boolean nextState = (msg.arg1 != 0); 1799 if (mUpdateLock.isHeld() != nextState) { 1800 if (DEBUG_IMMERSIVE) { 1801 final ActivityRecord r = (ActivityRecord) msg.obj; 1802 Slog.d(TAG, "Applying new update lock state '" + nextState + "' for " + r); 1803 } 1804 if (nextState) { 1805 mUpdateLock.acquire(); 1806 } else { 1807 mUpdateLock.release(); 1808 } 1809 } 1810 break; 1811 } 1812 case PERSIST_URI_GRANTS_MSG: { 1813 writeGrantedUriPermissions(); 1814 break; 1815 } 1816 case REQUEST_ALL_PSS_MSG: { 1817 requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, false); 1818 break; 1819 } 1820 case START_PROFILES_MSG: { 1821 synchronized (ActivityManagerService.this) { 1822 startProfilesLocked(); 1823 } 1824 break; 1825 } 1826 case UPDATE_TIME: { 1827 synchronized (ActivityManagerService.this) { 1828 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1829 ProcessRecord r = mLruProcesses.get(i); 1830 if (r.thread != null) { 1831 try { 1832 r.thread.updateTimePrefs(msg.arg1 == 0 ? false : true); 1833 } catch (RemoteException ex) { 1834 Slog.w(TAG, "Failed to update preferences for: " + r.info.processName); 1835 } 1836 } 1837 } 1838 } 1839 break; 1840 } 1841 case SYSTEM_USER_START_MSG: { 1842 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 1843 Integer.toString(msg.arg1), msg.arg1); 1844 mSystemServiceManager.startUser(msg.arg1); 1845 break; 1846 } 1847 case SYSTEM_USER_CURRENT_MSG: { 1848 mBatteryStatsService.noteEvent( 1849 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_FINISH, 1850 Integer.toString(msg.arg2), msg.arg2); 1851 mBatteryStatsService.noteEvent( 1852 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 1853 Integer.toString(msg.arg1), msg.arg1); 1854 mSystemServiceManager.switchUser(msg.arg1); 1855 mLockToAppRequest.clearPrompt(); 1856 break; 1857 } 1858 case ENTER_ANIMATION_COMPLETE_MSG: { 1859 synchronized (ActivityManagerService.this) { 1860 ActivityRecord r = ActivityRecord.forToken((IBinder) msg.obj); 1861 if (r != null && r.app != null && r.app.thread != null) { 1862 try { 1863 r.app.thread.scheduleEnterAnimationComplete(r.appToken); 1864 } catch (RemoteException e) { 1865 } 1866 } 1867 } 1868 break; 1869 } 1870 case ENABLE_SCREEN_AFTER_BOOT_MSG: { 1871 enableScreenAfterBoot(); 1872 break; 1873 } 1874 } 1875 } 1876 }; 1877 1878 static final int COLLECT_PSS_BG_MSG = 1; 1879 1880 final Handler mBgHandler = new Handler(BackgroundThread.getHandler().getLooper()) { 1881 @Override 1882 public void handleMessage(Message msg) { 1883 switch (msg.what) { 1884 case COLLECT_PSS_BG_MSG: { 1885 long start = SystemClock.uptimeMillis(); 1886 MemInfoReader memInfo = null; 1887 synchronized (ActivityManagerService.this) { 1888 if (mFullPssPending) { 1889 mFullPssPending = false; 1890 memInfo = new MemInfoReader(); 1891 } 1892 } 1893 if (memInfo != null) { 1894 updateCpuStatsNow(); 1895 long nativeTotalPss = 0; 1896 synchronized (mProcessCpuThread) { 1897 final int N = mProcessCpuTracker.countStats(); 1898 for (int j=0; j<N; j++) { 1899 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(j); 1900 if (st.vsize <= 0 || st.uid >= Process.FIRST_APPLICATION_UID) { 1901 // This is definitely an application process; skip it. 1902 continue; 1903 } 1904 synchronized (mPidsSelfLocked) { 1905 if (mPidsSelfLocked.indexOfKey(st.pid) >= 0) { 1906 // This is one of our own processes; skip it. 1907 continue; 1908 } 1909 } 1910 nativeTotalPss += Debug.getPss(st.pid, null); 1911 } 1912 } 1913 memInfo.readMemInfo(); 1914 synchronized (this) { 1915 if (DEBUG_PSS) Slog.d(TAG, "Collected native and kernel memory in " 1916 + (SystemClock.uptimeMillis()-start) + "ms"); 1917 mProcessStats.addSysMemUsageLocked(memInfo.getCachedSizeKb(), 1918 memInfo.getFreeSizeKb(), memInfo.getZramTotalSizeKb(), 1919 memInfo.getBuffersSizeKb()+memInfo.getShmemSizeKb() 1920 +memInfo.getSlabSizeKb(), 1921 nativeTotalPss); 1922 } 1923 } 1924 1925 int i=0, num=0; 1926 long[] tmp = new long[1]; 1927 do { 1928 ProcessRecord proc; 1929 int procState; 1930 int pid; 1931 synchronized (ActivityManagerService.this) { 1932 if (i >= mPendingPssProcesses.size()) { 1933 if (DEBUG_PSS) Slog.d(TAG, "Collected PSS of " + num + " of " + i 1934 + " processes in " + (SystemClock.uptimeMillis()-start) + "ms"); 1935 mPendingPssProcesses.clear(); 1936 return; 1937 } 1938 proc = mPendingPssProcesses.get(i); 1939 procState = proc.pssProcState; 1940 if (proc.thread != null && procState == proc.setProcState) { 1941 pid = proc.pid; 1942 } else { 1943 proc = null; 1944 pid = 0; 1945 } 1946 i++; 1947 } 1948 if (proc != null) { 1949 long pss = Debug.getPss(pid, tmp); 1950 synchronized (ActivityManagerService.this) { 1951 if (proc.thread != null && proc.setProcState == procState 1952 && proc.pid == pid) { 1953 num++; 1954 proc.lastPssTime = SystemClock.uptimeMillis(); 1955 proc.baseProcessTracker.addPss(pss, tmp[0], true, proc.pkgList); 1956 if (DEBUG_PSS) Slog.d(TAG, "PSS of " + proc.toShortString() 1957 + ": " + pss + " lastPss=" + proc.lastPss 1958 + " state=" + ProcessList.makeProcStateString(procState)); 1959 if (proc.initialIdlePss == 0) { 1960 proc.initialIdlePss = pss; 1961 } 1962 proc.lastPss = pss; 1963 if (procState >= ActivityManager.PROCESS_STATE_HOME) { 1964 proc.lastCachedPss = pss; 1965 } 1966 } 1967 } 1968 } 1969 } while (true); 1970 } 1971 } 1972 } 1973 }; 1974 1975 /** 1976 * Monitor for package changes and update our internal state. 1977 */ 1978 private final PackageMonitor mPackageMonitor = new PackageMonitor() { 1979 @Override 1980 public void onPackageRemoved(String packageName, int uid) { 1981 // Remove all tasks with activities in the specified package from the list of recent tasks 1982 synchronized (ActivityManagerService.this) { 1983 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 1984 TaskRecord tr = mRecentTasks.get(i); 1985 ComponentName cn = tr.intent.getComponent(); 1986 if (cn != null && cn.getPackageName().equals(packageName)) { 1987 // If the package name matches, remove the task and kill the process 1988 removeTaskByIdLocked(tr.taskId, ActivityManager.REMOVE_TASK_KILL_PROCESS); 1989 } 1990 } 1991 } 1992 } 1993 1994 @Override 1995 public boolean onPackageChanged(String packageName, int uid, String[] components) { 1996 onPackageModified(packageName); 1997 return true; 1998 } 1999 2000 @Override 2001 public void onPackageModified(String packageName) { 2002 final PackageManager pm = mContext.getPackageManager(); 2003 final ArrayList<Pair<Intent, Integer>> recentTaskIntents = 2004 new ArrayList<Pair<Intent, Integer>>(); 2005 final ArrayList<Integer> tasksToRemove = new ArrayList<Integer>(); 2006 // Copy the list of recent tasks so that we don't hold onto the lock on 2007 // ActivityManagerService for long periods while checking if components exist. 2008 synchronized (ActivityManagerService.this) { 2009 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 2010 TaskRecord tr = mRecentTasks.get(i); 2011 recentTaskIntents.add(new Pair<Intent, Integer>(tr.intent, tr.taskId)); 2012 } 2013 } 2014 // Check the recent tasks and filter out all tasks with components that no longer exist. 2015 Intent tmpI = new Intent(); 2016 for (int i = recentTaskIntents.size() - 1; i >= 0; i--) { 2017 Pair<Intent, Integer> p = recentTaskIntents.get(i); 2018 ComponentName cn = p.first.getComponent(); 2019 if (cn != null && cn.getPackageName().equals(packageName)) { 2020 try { 2021 // Add the task to the list to remove if the component no longer exists 2022 tmpI.setComponent(cn); 2023 if (pm.queryIntentActivities(tmpI, PackageManager.MATCH_DEFAULT_ONLY).isEmpty()) { 2024 tasksToRemove.add(p.second); 2025 } 2026 } catch (Exception e) {} 2027 } 2028 } 2029 // Prune all the tasks with removed components from the list of recent tasks 2030 synchronized (ActivityManagerService.this) { 2031 for (int i = tasksToRemove.size() - 1; i >= 0; i--) { 2032 // Remove the task but don't kill the process (since other components in that 2033 // package may still be running and in the background) 2034 removeTaskByIdLocked(tasksToRemove.get(i), 0); 2035 } 2036 } 2037 } 2038 2039 @Override 2040 public boolean onHandleForceStop(Intent intent, String[] packages, int uid, boolean doit) { 2041 // Force stop the specified packages 2042 if (packages != null) { 2043 for (String pkg : packages) { 2044 synchronized (ActivityManagerService.this) { 2045 if (forceStopPackageLocked(pkg, -1, false, false, false, false, false, 0, 2046 "finished booting")) { 2047 return true; 2048 } 2049 } 2050 } 2051 } 2052 return false; 2053 } 2054 }; 2055 2056 public void setSystemProcess() { 2057 try { 2058 ServiceManager.addService(Context.ACTIVITY_SERVICE, this, true); 2059 ServiceManager.addService(ProcessStats.SERVICE_NAME, mProcessStats); 2060 ServiceManager.addService("meminfo", new MemBinder(this)); 2061 ServiceManager.addService("gfxinfo", new GraphicsBinder(this)); 2062 ServiceManager.addService("dbinfo", new DbBinder(this)); 2063 if (MONITOR_CPU_USAGE) { 2064 ServiceManager.addService("cpuinfo", new CpuBinder(this)); 2065 } 2066 ServiceManager.addService("permission", new PermissionController(this)); 2067 2068 ApplicationInfo info = mContext.getPackageManager().getApplicationInfo( 2069 "android", STOCK_PM_FLAGS); 2070 mSystemThread.installSystemApplicationInfo(info, getClass().getClassLoader()); 2071 2072 synchronized (this) { 2073 ProcessRecord app = newProcessRecordLocked(info, info.processName, false, 0); 2074 app.persistent = true; 2075 app.pid = MY_PID; 2076 app.maxAdj = ProcessList.SYSTEM_ADJ; 2077 app.makeActive(mSystemThread.getApplicationThread(), mProcessStats); 2078 mProcessNames.put(app.processName, app.uid, app); 2079 synchronized (mPidsSelfLocked) { 2080 mPidsSelfLocked.put(app.pid, app); 2081 } 2082 updateLruProcessLocked(app, false, null); 2083 updateOomAdjLocked(); 2084 } 2085 } catch (PackageManager.NameNotFoundException e) { 2086 throw new RuntimeException( 2087 "Unable to find android system package", e); 2088 } 2089 } 2090 2091 public void setWindowManager(WindowManagerService wm) { 2092 mWindowManager = wm; 2093 mStackSupervisor.setWindowManager(wm); 2094 } 2095 2096 public void setUsageStatsManager(UsageStatsManagerInternal usageStatsManager) { 2097 mUsageStatsService = usageStatsManager; 2098 } 2099 2100 public void startObservingNativeCrashes() { 2101 final NativeCrashListener ncl = new NativeCrashListener(this); 2102 ncl.start(); 2103 } 2104 2105 public IAppOpsService getAppOpsService() { 2106 return mAppOpsService; 2107 } 2108 2109 static class MemBinder extends Binder { 2110 ActivityManagerService mActivityManagerService; 2111 MemBinder(ActivityManagerService activityManagerService) { 2112 mActivityManagerService = activityManagerService; 2113 } 2114 2115 @Override 2116 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2117 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2118 != PackageManager.PERMISSION_GRANTED) { 2119 pw.println("Permission Denial: can't dump meminfo from from pid=" 2120 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2121 + " without permission " + android.Manifest.permission.DUMP); 2122 return; 2123 } 2124 2125 mActivityManagerService.dumpApplicationMemoryUsage(fd, pw, " ", args, false, null); 2126 } 2127 } 2128 2129 static class GraphicsBinder extends Binder { 2130 ActivityManagerService mActivityManagerService; 2131 GraphicsBinder(ActivityManagerService activityManagerService) { 2132 mActivityManagerService = activityManagerService; 2133 } 2134 2135 @Override 2136 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2137 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2138 != PackageManager.PERMISSION_GRANTED) { 2139 pw.println("Permission Denial: can't dump gfxinfo from from pid=" 2140 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2141 + " without permission " + android.Manifest.permission.DUMP); 2142 return; 2143 } 2144 2145 mActivityManagerService.dumpGraphicsHardwareUsage(fd, pw, args); 2146 } 2147 } 2148 2149 static class DbBinder extends Binder { 2150 ActivityManagerService mActivityManagerService; 2151 DbBinder(ActivityManagerService activityManagerService) { 2152 mActivityManagerService = activityManagerService; 2153 } 2154 2155 @Override 2156 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2157 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2158 != PackageManager.PERMISSION_GRANTED) { 2159 pw.println("Permission Denial: can't dump dbinfo from from pid=" 2160 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2161 + " without permission " + android.Manifest.permission.DUMP); 2162 return; 2163 } 2164 2165 mActivityManagerService.dumpDbInfo(fd, pw, args); 2166 } 2167 } 2168 2169 static class CpuBinder extends Binder { 2170 ActivityManagerService mActivityManagerService; 2171 CpuBinder(ActivityManagerService activityManagerService) { 2172 mActivityManagerService = activityManagerService; 2173 } 2174 2175 @Override 2176 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2177 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2178 != PackageManager.PERMISSION_GRANTED) { 2179 pw.println("Permission Denial: can't dump cpuinfo from from pid=" 2180 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2181 + " without permission " + android.Manifest.permission.DUMP); 2182 return; 2183 } 2184 2185 synchronized (mActivityManagerService.mProcessCpuThread) { 2186 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentLoad()); 2187 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentState( 2188 SystemClock.uptimeMillis())); 2189 } 2190 } 2191 } 2192 2193 public static final class Lifecycle extends SystemService { 2194 private final ActivityManagerService mService; 2195 2196 public Lifecycle(Context context) { 2197 super(context); 2198 mService = new ActivityManagerService(context); 2199 } 2200 2201 @Override 2202 public void onStart() { 2203 mService.start(); 2204 } 2205 2206 public ActivityManagerService getService() { 2207 return mService; 2208 } 2209 } 2210 2211 // Note: This method is invoked on the main thread but may need to attach various 2212 // handlers to other threads. So take care to be explicit about the looper. 2213 public ActivityManagerService(Context systemContext) { 2214 mContext = systemContext; 2215 mFactoryTest = FactoryTest.getMode(); 2216 mSystemThread = ActivityThread.currentActivityThread(); 2217 2218 Slog.i(TAG, "Memory class: " + ActivityManager.staticGetMemoryClass()); 2219 2220 mHandlerThread = new ServiceThread(TAG, 2221 android.os.Process.THREAD_PRIORITY_FOREGROUND, false /*allowIo*/); 2222 mHandlerThread.start(); 2223 mHandler = new MainHandler(mHandlerThread.getLooper()); 2224 2225 mFgBroadcastQueue = new BroadcastQueue(this, mHandler, 2226 "foreground", BROADCAST_FG_TIMEOUT, false); 2227 mBgBroadcastQueue = new BroadcastQueue(this, mHandler, 2228 "background", BROADCAST_BG_TIMEOUT, true); 2229 mBroadcastQueues[0] = mFgBroadcastQueue; 2230 mBroadcastQueues[1] = mBgBroadcastQueue; 2231 2232 mServices = new ActiveServices(this); 2233 mProviderMap = new ProviderMap(this); 2234 2235 // TODO: Move creation of battery stats service outside of activity manager service. 2236 File dataDir = Environment.getDataDirectory(); 2237 File systemDir = new File(dataDir, "system"); 2238 systemDir.mkdirs(); 2239 mBatteryStatsService = new BatteryStatsService(systemDir, mHandler); 2240 mBatteryStatsService.getActiveStatistics().readLocked(); 2241 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2242 mOnBattery = DEBUG_POWER ? true 2243 : mBatteryStatsService.getActiveStatistics().getIsOnBattery(); 2244 mBatteryStatsService.getActiveStatistics().setCallback(this); 2245 2246 mProcessStats = new ProcessStatsService(this, new File(systemDir, "procstats")); 2247 2248 mAppOpsService = new AppOpsService(new File(systemDir, "appops.xml"), mHandler); 2249 2250 mGrantFile = new AtomicFile(new File(systemDir, "urigrants.xml")); 2251 2252 // User 0 is the first and only user that runs at boot. 2253 mStartedUsers.put(0, new UserStartedState(new UserHandle(0), true)); 2254 mUserLru.add(Integer.valueOf(0)); 2255 updateStartedUserArrayLocked(); 2256 2257 GL_ES_VERSION = SystemProperties.getInt("ro.opengles.version", 2258 ConfigurationInfo.GL_ES_VERSION_UNDEFINED); 2259 2260 mConfiguration.setToDefaults(); 2261 mConfiguration.setLocale(Locale.getDefault()); 2262 2263 mConfigurationSeq = mConfiguration.seq = 1; 2264 mProcessCpuTracker.init(); 2265 2266 mCompatModePackages = new CompatModePackages(this, systemDir, mHandler); 2267 mIntentFirewall = new IntentFirewall(new IntentFirewallInterface(), mHandler); 2268 mStackSupervisor = new ActivityStackSupervisor(this); 2269 mTaskPersister = new TaskPersister(systemDir, mStackSupervisor); 2270 2271 mProcessCpuThread = new Thread("CpuTracker") { 2272 @Override 2273 public void run() { 2274 while (true) { 2275 try { 2276 try { 2277 synchronized(this) { 2278 final long now = SystemClock.uptimeMillis(); 2279 long nextCpuDelay = (mLastCpuTime.get()+MONITOR_CPU_MAX_TIME)-now; 2280 long nextWriteDelay = (mLastWriteTime+BATTERY_STATS_TIME)-now; 2281 //Slog.i(TAG, "Cpu delay=" + nextCpuDelay 2282 // + ", write delay=" + nextWriteDelay); 2283 if (nextWriteDelay < nextCpuDelay) { 2284 nextCpuDelay = nextWriteDelay; 2285 } 2286 if (nextCpuDelay > 0) { 2287 mProcessCpuMutexFree.set(true); 2288 this.wait(nextCpuDelay); 2289 } 2290 } 2291 } catch (InterruptedException e) { 2292 } 2293 updateCpuStatsNow(); 2294 } catch (Exception e) { 2295 Slog.e(TAG, "Unexpected exception collecting process stats", e); 2296 } 2297 } 2298 } 2299 }; 2300 2301 mLockToAppRequest = new LockToAppRequestDialog(mContext, this); 2302 2303 Watchdog.getInstance().addMonitor(this); 2304 Watchdog.getInstance().addThread(mHandler); 2305 } 2306 2307 public void setSystemServiceManager(SystemServiceManager mgr) { 2308 mSystemServiceManager = mgr; 2309 } 2310 2311 private void start() { 2312 Process.removeAllProcessGroups(); 2313 mProcessCpuThread.start(); 2314 2315 mBatteryStatsService.publish(mContext); 2316 mAppOpsService.publish(mContext); 2317 Slog.d("AppOps", "AppOpsService published"); 2318 LocalServices.addService(ActivityManagerInternal.class, new LocalService()); 2319 } 2320 2321 public void initPowerManagement() { 2322 mStackSupervisor.initPowerManagement(); 2323 mBatteryStatsService.initPowerManagement(); 2324 } 2325 2326 @Override 2327 public boolean onTransact(int code, Parcel data, Parcel reply, int flags) 2328 throws RemoteException { 2329 if (code == SYSPROPS_TRANSACTION) { 2330 // We need to tell all apps about the system property change. 2331 ArrayList<IBinder> procs = new ArrayList<IBinder>(); 2332 synchronized(this) { 2333 final int NP = mProcessNames.getMap().size(); 2334 for (int ip=0; ip<NP; ip++) { 2335 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 2336 final int NA = apps.size(); 2337 for (int ia=0; ia<NA; ia++) { 2338 ProcessRecord app = apps.valueAt(ia); 2339 if (app.thread != null) { 2340 procs.add(app.thread.asBinder()); 2341 } 2342 } 2343 } 2344 } 2345 2346 int N = procs.size(); 2347 for (int i=0; i<N; i++) { 2348 Parcel data2 = Parcel.obtain(); 2349 try { 2350 procs.get(i).transact(IBinder.SYSPROPS_TRANSACTION, data2, null, 0); 2351 } catch (RemoteException e) { 2352 } 2353 data2.recycle(); 2354 } 2355 } 2356 try { 2357 return super.onTransact(code, data, reply, flags); 2358 } catch (RuntimeException e) { 2359 // The activity manager only throws security exceptions, so let's 2360 // log all others. 2361 if (!(e instanceof SecurityException)) { 2362 Slog.wtf(TAG, "Activity Manager Crash", e); 2363 } 2364 throw e; 2365 } 2366 } 2367 2368 void updateCpuStats() { 2369 final long now = SystemClock.uptimeMillis(); 2370 if (mLastCpuTime.get() >= now - MONITOR_CPU_MIN_TIME) { 2371 return; 2372 } 2373 if (mProcessCpuMutexFree.compareAndSet(true, false)) { 2374 synchronized (mProcessCpuThread) { 2375 mProcessCpuThread.notify(); 2376 } 2377 } 2378 } 2379 2380 void updateCpuStatsNow() { 2381 synchronized (mProcessCpuThread) { 2382 mProcessCpuMutexFree.set(false); 2383 final long now = SystemClock.uptimeMillis(); 2384 boolean haveNewCpuStats = false; 2385 2386 if (MONITOR_CPU_USAGE && 2387 mLastCpuTime.get() < (now-MONITOR_CPU_MIN_TIME)) { 2388 mLastCpuTime.set(now); 2389 haveNewCpuStats = true; 2390 mProcessCpuTracker.update(); 2391 //Slog.i(TAG, mProcessCpu.printCurrentState()); 2392 //Slog.i(TAG, "Total CPU usage: " 2393 // + mProcessCpu.getTotalCpuPercent() + "%"); 2394 2395 // Slog the cpu usage if the property is set. 2396 if ("true".equals(SystemProperties.get("events.cpu"))) { 2397 int user = mProcessCpuTracker.getLastUserTime(); 2398 int system = mProcessCpuTracker.getLastSystemTime(); 2399 int iowait = mProcessCpuTracker.getLastIoWaitTime(); 2400 int irq = mProcessCpuTracker.getLastIrqTime(); 2401 int softIrq = mProcessCpuTracker.getLastSoftIrqTime(); 2402 int idle = mProcessCpuTracker.getLastIdleTime(); 2403 2404 int total = user + system + iowait + irq + softIrq + idle; 2405 if (total == 0) total = 1; 2406 2407 EventLog.writeEvent(EventLogTags.CPU, 2408 ((user+system+iowait+irq+softIrq) * 100) / total, 2409 (user * 100) / total, 2410 (system * 100) / total, 2411 (iowait * 100) / total, 2412 (irq * 100) / total, 2413 (softIrq * 100) / total); 2414 } 2415 } 2416 2417 long[] cpuSpeedTimes = mProcessCpuTracker.getLastCpuSpeedTimes(); 2418 final BatteryStatsImpl bstats = mBatteryStatsService.getActiveStatistics(); 2419 synchronized(bstats) { 2420 synchronized(mPidsSelfLocked) { 2421 if (haveNewCpuStats) { 2422 if (mOnBattery) { 2423 int perc = bstats.startAddingCpuLocked(); 2424 int totalUTime = 0; 2425 int totalSTime = 0; 2426 final int N = mProcessCpuTracker.countStats(); 2427 for (int i=0; i<N; i++) { 2428 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 2429 if (!st.working) { 2430 continue; 2431 } 2432 ProcessRecord pr = mPidsSelfLocked.get(st.pid); 2433 int otherUTime = (st.rel_utime*perc)/100; 2434 int otherSTime = (st.rel_stime*perc)/100; 2435 totalUTime += otherUTime; 2436 totalSTime += otherSTime; 2437 if (pr != null) { 2438 BatteryStatsImpl.Uid.Proc ps = pr.curProcBatteryStats; 2439 if (ps == null || !ps.isActive()) { 2440 pr.curProcBatteryStats = ps = bstats.getProcessStatsLocked( 2441 pr.info.uid, pr.processName); 2442 } 2443 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2444 st.rel_stime-otherSTime); 2445 ps.addSpeedStepTimes(cpuSpeedTimes); 2446 pr.curCpuTime += (st.rel_utime+st.rel_stime) * 10; 2447 } else { 2448 BatteryStatsImpl.Uid.Proc ps = st.batteryStats; 2449 if (ps == null || !ps.isActive()) { 2450 st.batteryStats = ps = bstats.getProcessStatsLocked( 2451 bstats.mapUid(st.uid), st.name); 2452 } 2453 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2454 st.rel_stime-otherSTime); 2455 ps.addSpeedStepTimes(cpuSpeedTimes); 2456 } 2457 } 2458 bstats.finishAddingCpuLocked(perc, totalUTime, 2459 totalSTime, cpuSpeedTimes); 2460 } 2461 } 2462 } 2463 2464 if (mLastWriteTime < (now-BATTERY_STATS_TIME)) { 2465 mLastWriteTime = now; 2466 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2467 } 2468 } 2469 } 2470 } 2471 2472 @Override 2473 public void batteryNeedsCpuUpdate() { 2474 updateCpuStatsNow(); 2475 } 2476 2477 @Override 2478 public void batteryPowerChanged(boolean onBattery) { 2479 // When plugging in, update the CPU stats first before changing 2480 // the plug state. 2481 updateCpuStatsNow(); 2482 synchronized (this) { 2483 synchronized(mPidsSelfLocked) { 2484 mOnBattery = DEBUG_POWER ? true : onBattery; 2485 } 2486 } 2487 } 2488 2489 /** 2490 * Initialize the application bind args. These are passed to each 2491 * process when the bindApplication() IPC is sent to the process. They're 2492 * lazily setup to make sure the services are running when they're asked for. 2493 */ 2494 private HashMap<String, IBinder> getCommonServicesLocked() { 2495 if (mAppBindArgs == null) { 2496 mAppBindArgs = new HashMap<String, IBinder>(); 2497 2498 // Setup the application init args 2499 mAppBindArgs.put("package", ServiceManager.getService("package")); 2500 mAppBindArgs.put("window", ServiceManager.getService("window")); 2501 mAppBindArgs.put(Context.ALARM_SERVICE, 2502 ServiceManager.getService(Context.ALARM_SERVICE)); 2503 } 2504 return mAppBindArgs; 2505 } 2506 2507 final void setFocusedActivityLocked(ActivityRecord r) { 2508 if (mFocusedActivity != r) { 2509 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedActivityLocked: r=" + r); 2510 mFocusedActivity = r; 2511 if (r.task != null && r.task.voiceInteractor != null) { 2512 startRunningVoiceLocked(); 2513 } else { 2514 finishRunningVoiceLocked(); 2515 } 2516 mStackSupervisor.setFocusedStack(r); 2517 if (r != null) { 2518 mWindowManager.setFocusedApp(r.appToken, true); 2519 } 2520 applyUpdateLockStateLocked(r); 2521 } 2522 } 2523 2524 final void clearFocusedActivity(ActivityRecord r) { 2525 if (mFocusedActivity == r) { 2526 mFocusedActivity = null; 2527 } 2528 } 2529 2530 @Override 2531 public void setFocusedStack(int stackId) { 2532 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedStack: stackId=" + stackId); 2533 synchronized (ActivityManagerService.this) { 2534 ActivityStack stack = mStackSupervisor.getStack(stackId); 2535 if (stack != null) { 2536 ActivityRecord r = stack.topRunningActivityLocked(null); 2537 if (r != null) { 2538 setFocusedActivityLocked(r); 2539 } 2540 } 2541 } 2542 } 2543 2544 @Override 2545 public void notifyActivityDrawn(IBinder token) { 2546 if (DEBUG_VISBILITY) Slog.d(TAG, "notifyActivityDrawn: token=" + token); 2547 synchronized (this) { 2548 ActivityRecord r= mStackSupervisor.isInAnyStackLocked(token); 2549 if (r != null) { 2550 r.task.stack.notifyActivityDrawnLocked(r); 2551 } 2552 } 2553 } 2554 2555 final void applyUpdateLockStateLocked(ActivityRecord r) { 2556 // Modifications to the UpdateLock state are done on our handler, outside 2557 // the activity manager's locks. The new state is determined based on the 2558 // state *now* of the relevant activity record. The object is passed to 2559 // the handler solely for logging detail, not to be consulted/modified. 2560 final boolean nextState = r != null && r.immersive; 2561 mHandler.sendMessage( 2562 mHandler.obtainMessage(IMMERSIVE_MODE_LOCK_MSG, (nextState) ? 1 : 0, 0, r)); 2563 } 2564 2565 final void showAskCompatModeDialogLocked(ActivityRecord r) { 2566 Message msg = Message.obtain(); 2567 msg.what = SHOW_COMPAT_MODE_DIALOG_MSG; 2568 msg.obj = r.task.askedCompatMode ? null : r; 2569 mHandler.sendMessage(msg); 2570 } 2571 2572 private final int updateLruProcessInternalLocked(ProcessRecord app, long now, int index, 2573 String what, Object obj, ProcessRecord srcApp) { 2574 app.lastActivityTime = now; 2575 2576 if (app.activities.size() > 0) { 2577 // Don't want to touch dependent processes that are hosting activities. 2578 return index; 2579 } 2580 2581 int lrui = mLruProcesses.lastIndexOf(app); 2582 if (lrui < 0) { 2583 Slog.wtf(TAG, "Adding dependent process " + app + " not on LRU list: " 2584 + what + " " + obj + " from " + srcApp); 2585 return index; 2586 } 2587 2588 if (lrui >= index) { 2589 // Don't want to cause this to move dependent processes *back* in the 2590 // list as if they were less frequently used. 2591 return index; 2592 } 2593 2594 if (lrui >= mLruProcessActivityStart) { 2595 // Don't want to touch dependent processes that are hosting activities. 2596 return index; 2597 } 2598 2599 mLruProcesses.remove(lrui); 2600 if (index > 0) { 2601 index--; 2602 } 2603 if (DEBUG_LRU) Slog.d(TAG, "Moving dep from " + lrui + " to " + index 2604 + " in LRU list: " + app); 2605 mLruProcesses.add(index, app); 2606 return index; 2607 } 2608 2609 final void removeLruProcessLocked(ProcessRecord app) { 2610 int lrui = mLruProcesses.lastIndexOf(app); 2611 if (lrui >= 0) { 2612 if (lrui <= mLruProcessActivityStart) { 2613 mLruProcessActivityStart--; 2614 } 2615 if (lrui <= mLruProcessServiceStart) { 2616 mLruProcessServiceStart--; 2617 } 2618 mLruProcesses.remove(lrui); 2619 } 2620 } 2621 2622 final void updateLruProcessLocked(ProcessRecord app, boolean activityChange, 2623 ProcessRecord client) { 2624 final boolean hasActivity = app.activities.size() > 0 || app.hasClientActivities 2625 || app.treatLikeActivity; 2626 final boolean hasService = false; // not impl yet. app.services.size() > 0; 2627 if (!activityChange && hasActivity) { 2628 // The process has activities, so we are only allowing activity-based adjustments 2629 // to move it. It should be kept in the front of the list with other 2630 // processes that have activities, and we don't want those to change their 2631 // order except due to activity operations. 2632 return; 2633 } 2634 2635 mLruSeq++; 2636 final long now = SystemClock.uptimeMillis(); 2637 app.lastActivityTime = now; 2638 2639 // First a quick reject: if the app is already at the position we will 2640 // put it, then there is nothing to do. 2641 if (hasActivity) { 2642 final int N = mLruProcesses.size(); 2643 if (N > 0 && mLruProcesses.get(N-1) == app) { 2644 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top activity: " + app); 2645 return; 2646 } 2647 } else { 2648 if (mLruProcessServiceStart > 0 2649 && mLruProcesses.get(mLruProcessServiceStart-1) == app) { 2650 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top other: " + app); 2651 return; 2652 } 2653 } 2654 2655 int lrui = mLruProcesses.lastIndexOf(app); 2656 2657 if (app.persistent && lrui >= 0) { 2658 // We don't care about the position of persistent processes, as long as 2659 // they are in the list. 2660 if (DEBUG_LRU) Slog.d(TAG, "Not moving, persistent: " + app); 2661 return; 2662 } 2663 2664 /* In progress: compute new position first, so we can avoid doing work 2665 if the process is not actually going to move. Not yet working. 2666 int addIndex; 2667 int nextIndex; 2668 boolean inActivity = false, inService = false; 2669 if (hasActivity) { 2670 // Process has activities, put it at the very tipsy-top. 2671 addIndex = mLruProcesses.size(); 2672 nextIndex = mLruProcessServiceStart; 2673 inActivity = true; 2674 } else if (hasService) { 2675 // Process has services, put it at the top of the service list. 2676 addIndex = mLruProcessActivityStart; 2677 nextIndex = mLruProcessServiceStart; 2678 inActivity = true; 2679 inService = true; 2680 } else { 2681 // Process not otherwise of interest, it goes to the top of the non-service area. 2682 addIndex = mLruProcessServiceStart; 2683 if (client != null) { 2684 int clientIndex = mLruProcesses.lastIndexOf(client); 2685 if (clientIndex < 0) Slog.d(TAG, "Unknown client " + client + " when updating " 2686 + app); 2687 if (clientIndex >= 0 && addIndex > clientIndex) { 2688 addIndex = clientIndex; 2689 } 2690 } 2691 nextIndex = addIndex > 0 ? addIndex-1 : addIndex; 2692 } 2693 2694 Slog.d(TAG, "Update LRU at " + lrui + " to " + addIndex + " (act=" 2695 + mLruProcessActivityStart + "): " + app); 2696 */ 2697 2698 if (lrui >= 0) { 2699 if (lrui < mLruProcessActivityStart) { 2700 mLruProcessActivityStart--; 2701 } 2702 if (lrui < mLruProcessServiceStart) { 2703 mLruProcessServiceStart--; 2704 } 2705 /* 2706 if (addIndex > lrui) { 2707 addIndex--; 2708 } 2709 if (nextIndex > lrui) { 2710 nextIndex--; 2711 } 2712 */ 2713 mLruProcesses.remove(lrui); 2714 } 2715 2716 /* 2717 mLruProcesses.add(addIndex, app); 2718 if (inActivity) { 2719 mLruProcessActivityStart++; 2720 } 2721 if (inService) { 2722 mLruProcessActivityStart++; 2723 } 2724 */ 2725 2726 int nextIndex; 2727 if (hasActivity) { 2728 final int N = mLruProcesses.size(); 2729 if (app.activities.size() == 0 && mLruProcessActivityStart < (N-1)) { 2730 // Process doesn't have activities, but has clients with 2731 // activities... move it up, but one below the top (the top 2732 // should always have a real activity). 2733 if (DEBUG_LRU) Slog.d(TAG, "Adding to second-top of LRU activity list: " + app); 2734 mLruProcesses.add(N-1, app); 2735 // To keep it from spamming the LRU list (by making a bunch of clients), 2736 // we will push down any other entries owned by the app. 2737 final int uid = app.info.uid; 2738 for (int i=N-2; i>mLruProcessActivityStart; i--) { 2739 ProcessRecord subProc = mLruProcesses.get(i); 2740 if (subProc.info.uid == uid) { 2741 // We want to push this one down the list. If the process after 2742 // it is for the same uid, however, don't do so, because we don't 2743 // want them internally to be re-ordered. 2744 if (mLruProcesses.get(i-1).info.uid != uid) { 2745 if (DEBUG_LRU) Slog.d(TAG, "Pushing uid " + uid + " swapping at " + i 2746 + ": " + mLruProcesses.get(i) + " : " + mLruProcesses.get(i-1)); 2747 ProcessRecord tmp = mLruProcesses.get(i); 2748 mLruProcesses.set(i, mLruProcesses.get(i-1)); 2749 mLruProcesses.set(i-1, tmp); 2750 i--; 2751 } 2752 } else { 2753 // A gap, we can stop here. 2754 break; 2755 } 2756 } 2757 } else { 2758 // Process has activities, put it at the very tipsy-top. 2759 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU activity list: " + app); 2760 mLruProcesses.add(app); 2761 } 2762 nextIndex = mLruProcessServiceStart; 2763 } else if (hasService) { 2764 // Process has services, put it at the top of the service list. 2765 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU service list: " + app); 2766 mLruProcesses.add(mLruProcessActivityStart, app); 2767 nextIndex = mLruProcessServiceStart; 2768 mLruProcessActivityStart++; 2769 } else { 2770 // Process not otherwise of interest, it goes to the top of the non-service area. 2771 int index = mLruProcessServiceStart; 2772 if (client != null) { 2773 // If there is a client, don't allow the process to be moved up higher 2774 // in the list than that client. 2775 int clientIndex = mLruProcesses.lastIndexOf(client); 2776 if (DEBUG_LRU && clientIndex < 0) Slog.d(TAG, "Unknown client " + client 2777 + " when updating " + app); 2778 if (clientIndex <= lrui) { 2779 // Don't allow the client index restriction to push it down farther in the 2780 // list than it already is. 2781 clientIndex = lrui; 2782 } 2783 if (clientIndex >= 0 && index > clientIndex) { 2784 index = clientIndex; 2785 } 2786 } 2787 if (DEBUG_LRU) Slog.d(TAG, "Adding at " + index + " of LRU list: " + app); 2788 mLruProcesses.add(index, app); 2789 nextIndex = index-1; 2790 mLruProcessActivityStart++; 2791 mLruProcessServiceStart++; 2792 } 2793 2794 // If the app is currently using a content provider or service, 2795 // bump those processes as well. 2796 for (int j=app.connections.size()-1; j>=0; j--) { 2797 ConnectionRecord cr = app.connections.valueAt(j); 2798 if (cr.binding != null && !cr.serviceDead && cr.binding.service != null 2799 && cr.binding.service.app != null 2800 && cr.binding.service.app.lruSeq != mLruSeq 2801 && !cr.binding.service.app.persistent) { 2802 nextIndex = updateLruProcessInternalLocked(cr.binding.service.app, now, nextIndex, 2803 "service connection", cr, app); 2804 } 2805 } 2806 for (int j=app.conProviders.size()-1; j>=0; j--) { 2807 ContentProviderRecord cpr = app.conProviders.get(j).provider; 2808 if (cpr.proc != null && cpr.proc.lruSeq != mLruSeq && !cpr.proc.persistent) { 2809 nextIndex = updateLruProcessInternalLocked(cpr.proc, now, nextIndex, 2810 "provider reference", cpr, app); 2811 } 2812 } 2813 } 2814 2815 final ProcessRecord getProcessRecordLocked(String processName, int uid, boolean keepIfLarge) { 2816 if (uid == Process.SYSTEM_UID) { 2817 // The system gets to run in any process. If there are multiple 2818 // processes with the same uid, just pick the first (this 2819 // should never happen). 2820 SparseArray<ProcessRecord> procs = mProcessNames.getMap().get(processName); 2821 if (procs == null) return null; 2822 final int N = procs.size(); 2823 for (int i = 0; i < N; i++) { 2824 if (UserHandle.isSameUser(procs.keyAt(i), uid)) return procs.valueAt(i); 2825 } 2826 } 2827 ProcessRecord proc = mProcessNames.get(processName, uid); 2828 if (false && proc != null && !keepIfLarge 2829 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY 2830 && proc.lastCachedPss >= 4000) { 2831 // Turn this condition on to cause killing to happen regularly, for testing. 2832 if (proc.baseProcessTracker != null) { 2833 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2834 } 2835 proc.kill(Long.toString(proc.lastCachedPss) + "k from cached", true); 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 proc.kill(Long.toString(proc.lastCachedPss) + "k from cached", true); 2845 } 2846 } 2847 return proc; 2848 } 2849 2850 void ensurePackageDexOpt(String packageName) { 2851 IPackageManager pm = AppGlobals.getPackageManager(); 2852 try { 2853 if (pm.performDexOptIfNeeded(packageName, null /* instruction set */)) { 2854 mDidDexOpt = true; 2855 } 2856 } catch (RemoteException e) { 2857 } 2858 } 2859 2860 boolean isNextTransitionForward() { 2861 int transit = mWindowManager.getPendingAppTransition(); 2862 return transit == AppTransition.TRANSIT_ACTIVITY_OPEN 2863 || transit == AppTransition.TRANSIT_TASK_OPEN 2864 || transit == AppTransition.TRANSIT_TASK_TO_FRONT; 2865 } 2866 2867 int startIsolatedProcess(String entryPoint, String[] entryPointArgs, 2868 String processName, String abiOverride, int uid, Runnable crashHandler) { 2869 synchronized(this) { 2870 ApplicationInfo info = new ApplicationInfo(); 2871 // In general the ApplicationInfo.uid isn't neccesarily equal to ProcessRecord.uid. 2872 // For isolated processes, the former contains the parent's uid and the latter the 2873 // actual uid of the isolated process. 2874 // In the special case introduced by this method (which is, starting an isolated 2875 // process directly from the SystemServer without an actual parent app process) the 2876 // closest thing to a parent's uid is SYSTEM_UID. 2877 // The only important thing here is to keep AI.uid != PR.uid, in order to trigger 2878 // the |isolated| logic in the ProcessRecord constructor. 2879 info.uid = Process.SYSTEM_UID; 2880 info.processName = processName; 2881 info.className = entryPoint; 2882 info.packageName = "android"; 2883 ProcessRecord proc = startProcessLocked(processName, info /* info */, 2884 false /* knownToBeDead */, 0 /* intentFlags */, "" /* hostingType */, 2885 null /* hostingName */, true /* allowWhileBooting */, true /* isolated */, 2886 uid, true /* keepIfLarge */, abiOverride, entryPoint, entryPointArgs, 2887 crashHandler); 2888 return proc != null ? proc.pid : 0; 2889 } 2890 } 2891 2892 final ProcessRecord startProcessLocked(String processName, 2893 ApplicationInfo info, boolean knownToBeDead, int intentFlags, 2894 String hostingType, ComponentName hostingName, boolean allowWhileBooting, 2895 boolean isolated, boolean keepIfLarge) { 2896 return startProcessLocked(processName, info, knownToBeDead, intentFlags, hostingType, 2897 hostingName, allowWhileBooting, isolated, 0 /* isolatedUid */, keepIfLarge, 2898 null /* ABI override */, null /* entryPoint */, null /* entryPointArgs */, 2899 null /* crashHandler */); 2900 } 2901 2902 final ProcessRecord startProcessLocked(String processName, ApplicationInfo info, 2903 boolean knownToBeDead, int intentFlags, String hostingType, ComponentName hostingName, 2904 boolean allowWhileBooting, boolean isolated, int isolatedUid, boolean keepIfLarge, 2905 String abiOverride, String entryPoint, String[] entryPointArgs, Runnable crashHandler) { 2906 long startTime = SystemClock.elapsedRealtime(); 2907 ProcessRecord app; 2908 if (!isolated) { 2909 app = getProcessRecordLocked(processName, info.uid, keepIfLarge); 2910 checkTime(startTime, "startProcess: after getProcessRecord"); 2911 } else { 2912 // If this is an isolated process, it can't re-use an existing process. 2913 app = null; 2914 } 2915 // We don't have to do anything more if: 2916 // (1) There is an existing application record; and 2917 // (2) The caller doesn't think it is dead, OR there is no thread 2918 // object attached to it so we know it couldn't have crashed; and 2919 // (3) There is a pid assigned to it, so it is either starting or 2920 // already running. 2921 if (DEBUG_PROCESSES) Slog.v(TAG, "startProcess: name=" + processName 2922 + " app=" + app + " knownToBeDead=" + knownToBeDead 2923 + " thread=" + (app != null ? app.thread : null) 2924 + " pid=" + (app != null ? app.pid : -1)); 2925 if (app != null && app.pid > 0) { 2926 if (!knownToBeDead || app.thread == null) { 2927 // We already have the app running, or are waiting for it to 2928 // come up (we have a pid but not yet its thread), so keep it. 2929 if (DEBUG_PROCESSES) Slog.v(TAG, "App already running: " + app); 2930 // If this is a new package in the process, add the package to the list 2931 app.addPackage(info.packageName, info.versionCode, mProcessStats); 2932 checkTime(startTime, "startProcess: done, added package to proc"); 2933 return app; 2934 } 2935 2936 // An application record is attached to a previous process, 2937 // clean it up now. 2938 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, "App died: " + app); 2939 checkTime(startTime, "startProcess: bad proc running, killing"); 2940 Process.killProcessGroup(app.info.uid, app.pid); 2941 handleAppDiedLocked(app, true, true); 2942 checkTime(startTime, "startProcess: done killing old proc"); 2943 } 2944 2945 String hostingNameStr = hostingName != null 2946 ? hostingName.flattenToShortString() : null; 2947 2948 if (!isolated) { 2949 if ((intentFlags&Intent.FLAG_FROM_BACKGROUND) != 0) { 2950 // If we are in the background, then check to see if this process 2951 // is bad. If so, we will just silently fail. 2952 if (mBadProcesses.get(info.processName, info.uid) != null) { 2953 if (DEBUG_PROCESSES) Slog.v(TAG, "Bad process: " + info.uid 2954 + "/" + info.processName); 2955 return null; 2956 } 2957 } else { 2958 // When the user is explicitly starting a process, then clear its 2959 // crash count so that we won't make it bad until they see at 2960 // least one crash dialog again, and make the process good again 2961 // if it had been bad. 2962 if (DEBUG_PROCESSES) Slog.v(TAG, "Clearing bad process: " + info.uid 2963 + "/" + info.processName); 2964 mProcessCrashTimes.remove(info.processName, info.uid); 2965 if (mBadProcesses.get(info.processName, info.uid) != null) { 2966 EventLog.writeEvent(EventLogTags.AM_PROC_GOOD, 2967 UserHandle.getUserId(info.uid), info.uid, 2968 info.processName); 2969 mBadProcesses.remove(info.processName, info.uid); 2970 if (app != null) { 2971 app.bad = false; 2972 } 2973 } 2974 } 2975 } 2976 2977 if (app == null) { 2978 checkTime(startTime, "startProcess: creating new process record"); 2979 app = newProcessRecordLocked(info, processName, isolated, isolatedUid); 2980 app.crashHandler = crashHandler; 2981 if (app == null) { 2982 Slog.w(TAG, "Failed making new process record for " 2983 + processName + "/" + info.uid + " isolated=" + isolated); 2984 return null; 2985 } 2986 mProcessNames.put(processName, app.uid, app); 2987 if (isolated) { 2988 mIsolatedProcesses.put(app.uid, app); 2989 } 2990 checkTime(startTime, "startProcess: done creating new process record"); 2991 } else { 2992 // If this is a new package in the process, add the package to the list 2993 app.addPackage(info.packageName, info.versionCode, mProcessStats); 2994 checkTime(startTime, "startProcess: added package to existing proc"); 2995 } 2996 2997 // If the system is not ready yet, then hold off on starting this 2998 // process until it is. 2999 if (!mProcessesReady 3000 && !isAllowedWhileBooting(info) 3001 && !allowWhileBooting) { 3002 if (!mProcessesOnHold.contains(app)) { 3003 mProcessesOnHold.add(app); 3004 } 3005 if (DEBUG_PROCESSES) Slog.v(TAG, "System not ready, putting on hold: " + app); 3006 checkTime(startTime, "startProcess: returning with proc on hold"); 3007 return app; 3008 } 3009 3010 checkTime(startTime, "startProcess: stepping in to startProcess"); 3011 startProcessLocked( 3012 app, hostingType, hostingNameStr, abiOverride, entryPoint, entryPointArgs); 3013 checkTime(startTime, "startProcess: done starting proc!"); 3014 return (app.pid != 0) ? app : null; 3015 } 3016 3017 boolean isAllowedWhileBooting(ApplicationInfo ai) { 3018 return (ai.flags&ApplicationInfo.FLAG_PERSISTENT) != 0; 3019 } 3020 3021 private final void startProcessLocked(ProcessRecord app, 3022 String hostingType, String hostingNameStr) { 3023 startProcessLocked(app, hostingType, hostingNameStr, null /* abiOverride */, 3024 null /* entryPoint */, null /* entryPointArgs */); 3025 } 3026 3027 private final void startProcessLocked(ProcessRecord app, String hostingType, 3028 String hostingNameStr, String abiOverride, String entryPoint, String[] entryPointArgs) { 3029 long startTime = SystemClock.elapsedRealtime(); 3030 if (app.pid > 0 && app.pid != MY_PID) { 3031 checkTime(startTime, "startProcess: removing from pids map"); 3032 synchronized (mPidsSelfLocked) { 3033 mPidsSelfLocked.remove(app.pid); 3034 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 3035 } 3036 checkTime(startTime, "startProcess: done removing from pids map"); 3037 app.setPid(0); 3038 } 3039 3040 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 3041 "startProcessLocked removing on hold: " + app); 3042 mProcessesOnHold.remove(app); 3043 3044 checkTime(startTime, "startProcess: starting to update cpu stats"); 3045 updateCpuStats(); 3046 checkTime(startTime, "startProcess: done updating cpu stats"); 3047 3048 try { 3049 int uid = app.uid; 3050 3051 int[] gids = null; 3052 int mountExternal = Zygote.MOUNT_EXTERNAL_NONE; 3053 if (!app.isolated) { 3054 int[] permGids = null; 3055 try { 3056 checkTime(startTime, "startProcess: getting gids from package manager"); 3057 final PackageManager pm = mContext.getPackageManager(); 3058 permGids = pm.getPackageGids(app.info.packageName); 3059 3060 if (Environment.isExternalStorageEmulated()) { 3061 checkTime(startTime, "startProcess: checking external storage perm"); 3062 if (pm.checkPermission( 3063 android.Manifest.permission.ACCESS_ALL_EXTERNAL_STORAGE, 3064 app.info.packageName) == PERMISSION_GRANTED) { 3065 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER_ALL; 3066 } else { 3067 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER; 3068 } 3069 } 3070 } catch (PackageManager.NameNotFoundException e) { 3071 Slog.w(TAG, "Unable to retrieve gids", e); 3072 } 3073 3074 /* 3075 * Add shared application and profile GIDs so applications can share some 3076 * resources like shared libraries and access user-wide resources 3077 */ 3078 if (permGids == null) { 3079 gids = new int[2]; 3080 } else { 3081 gids = new int[permGids.length + 2]; 3082 System.arraycopy(permGids, 0, gids, 2, permGids.length); 3083 } 3084 gids[0] = UserHandle.getSharedAppGid(UserHandle.getAppId(uid)); 3085 gids[1] = UserHandle.getUserGid(UserHandle.getUserId(uid)); 3086 } 3087 checkTime(startTime, "startProcess: building args"); 3088 if (mFactoryTest != FactoryTest.FACTORY_TEST_OFF) { 3089 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3090 && mTopComponent != null 3091 && app.processName.equals(mTopComponent.getPackageName())) { 3092 uid = 0; 3093 } 3094 if (mFactoryTest == FactoryTest.FACTORY_TEST_HIGH_LEVEL 3095 && (app.info.flags&ApplicationInfo.FLAG_FACTORY_TEST) != 0) { 3096 uid = 0; 3097 } 3098 } 3099 int debugFlags = 0; 3100 if ((app.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 3101 debugFlags |= Zygote.DEBUG_ENABLE_DEBUGGER; 3102 // Also turn on CheckJNI for debuggable apps. It's quite 3103 // awkward to turn on otherwise. 3104 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 3105 } 3106 // Run the app in safe mode if its manifest requests so or the 3107 // system is booted in safe mode. 3108 if ((app.info.flags & ApplicationInfo.FLAG_VM_SAFE_MODE) != 0 || 3109 mSafeMode == true) { 3110 debugFlags |= Zygote.DEBUG_ENABLE_SAFEMODE; 3111 } 3112 if ("1".equals(SystemProperties.get("debug.checkjni"))) { 3113 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 3114 } 3115 if ("1".equals(SystemProperties.get("debug.jni.logging"))) { 3116 debugFlags |= Zygote.DEBUG_ENABLE_JNI_LOGGING; 3117 } 3118 if ("1".equals(SystemProperties.get("debug.assert"))) { 3119 debugFlags |= Zygote.DEBUG_ENABLE_ASSERT; 3120 } 3121 3122 String requiredAbi = (abiOverride != null) ? abiOverride : app.info.primaryCpuAbi; 3123 if (requiredAbi == null) { 3124 requiredAbi = Build.SUPPORTED_ABIS[0]; 3125 } 3126 3127 // Start the process. It will either succeed and return a result containing 3128 // the PID of the new process, or else throw a RuntimeException. 3129 boolean isActivityProcess = (entryPoint == null); 3130 if (entryPoint == null) entryPoint = "android.app.ActivityThread"; 3131 checkTime(startTime, "startProcess: asking zygote to start proc"); 3132 Process.ProcessStartResult startResult = Process.start(entryPoint, 3133 app.processName, uid, uid, gids, debugFlags, mountExternal, 3134 app.info.targetSdkVersion, app.info.seinfo, requiredAbi, entryPointArgs); 3135 checkTime(startTime, "startProcess: returned from zygote!"); 3136 3137 if (app.isolated) { 3138 mBatteryStatsService.addIsolatedUid(app.uid, app.info.uid); 3139 } 3140 mBatteryStatsService.noteProcessStart(app.processName, app.info.uid); 3141 checkTime(startTime, "startProcess: done updating battery stats"); 3142 3143 EventLog.writeEvent(EventLogTags.AM_PROC_START, 3144 UserHandle.getUserId(uid), startResult.pid, uid, 3145 app.processName, hostingType, 3146 hostingNameStr != null ? hostingNameStr : ""); 3147 3148 if (app.persistent) { 3149 Watchdog.getInstance().processStarted(app.processName, startResult.pid); 3150 } 3151 3152 checkTime(startTime, "startProcess: building log message"); 3153 StringBuilder buf = mStringBuilder; 3154 buf.setLength(0); 3155 buf.append("Start proc "); 3156 buf.append(app.processName); 3157 if (!isActivityProcess) { 3158 buf.append(" ["); 3159 buf.append(entryPoint); 3160 buf.append("]"); 3161 } 3162 buf.append(" for "); 3163 buf.append(hostingType); 3164 if (hostingNameStr != null) { 3165 buf.append(" "); 3166 buf.append(hostingNameStr); 3167 } 3168 buf.append(": pid="); 3169 buf.append(startResult.pid); 3170 buf.append(" uid="); 3171 buf.append(uid); 3172 buf.append(" gids={"); 3173 if (gids != null) { 3174 for (int gi=0; gi<gids.length; gi++) { 3175 if (gi != 0) buf.append(", "); 3176 buf.append(gids[gi]); 3177 3178 } 3179 } 3180 buf.append("}"); 3181 if (requiredAbi != null) { 3182 buf.append(" abi="); 3183 buf.append(requiredAbi); 3184 } 3185 Slog.i(TAG, buf.toString()); 3186 app.setPid(startResult.pid); 3187 app.usingWrapper = startResult.usingWrapper; 3188 app.removed = false; 3189 app.killedByAm = false; 3190 checkTime(startTime, "startProcess: starting to update pids map"); 3191 synchronized (mPidsSelfLocked) { 3192 this.mPidsSelfLocked.put(startResult.pid, app); 3193 if (isActivityProcess) { 3194 Message msg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 3195 msg.obj = app; 3196 mHandler.sendMessageDelayed(msg, startResult.usingWrapper 3197 ? PROC_START_TIMEOUT_WITH_WRAPPER : PROC_START_TIMEOUT); 3198 } 3199 } 3200 checkTime(startTime, "startProcess: done updating pids map"); 3201 } catch (RuntimeException e) { 3202 // XXX do better error recovery. 3203 app.setPid(0); 3204 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 3205 if (app.isolated) { 3206 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 3207 } 3208 Slog.e(TAG, "Failure starting process " + app.processName, e); 3209 } 3210 } 3211 3212 void updateUsageStats(ActivityRecord component, boolean resumed) { 3213 if (DEBUG_SWITCH) Slog.d(TAG, "updateUsageStats: comp=" + component + "res=" + resumed); 3214 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 3215 if (resumed) { 3216 if (mUsageStatsService != null) { 3217 mUsageStatsService.reportEvent(component.realActivity, component.userId, 3218 UsageEvents.Event.MOVE_TO_FOREGROUND); 3219 } 3220 synchronized (stats) { 3221 stats.noteActivityResumedLocked(component.app.uid); 3222 } 3223 } else { 3224 if (mUsageStatsService != null) { 3225 mUsageStatsService.reportEvent(component.realActivity, component.userId, 3226 UsageEvents.Event.MOVE_TO_BACKGROUND); 3227 } 3228 synchronized (stats) { 3229 stats.noteActivityPausedLocked(component.app.uid); 3230 } 3231 } 3232 } 3233 3234 Intent getHomeIntent() { 3235 Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null); 3236 intent.setComponent(mTopComponent); 3237 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 3238 intent.addCategory(Intent.CATEGORY_HOME); 3239 } 3240 return intent; 3241 } 3242 3243 boolean startHomeActivityLocked(int userId) { 3244 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3245 && mTopAction == null) { 3246 // We are running in factory test mode, but unable to find 3247 // the factory test app, so just sit around displaying the 3248 // error message and don't try to start anything. 3249 return false; 3250 } 3251 Intent intent = getHomeIntent(); 3252 ActivityInfo aInfo = 3253 resolveActivityInfo(intent, STOCK_PM_FLAGS, userId); 3254 if (aInfo != null) { 3255 intent.setComponent(new ComponentName( 3256 aInfo.applicationInfo.packageName, aInfo.name)); 3257 // Don't do this if the home app is currently being 3258 // instrumented. 3259 aInfo = new ActivityInfo(aInfo); 3260 aInfo.applicationInfo = getAppInfoForUser(aInfo.applicationInfo, userId); 3261 ProcessRecord app = getProcessRecordLocked(aInfo.processName, 3262 aInfo.applicationInfo.uid, true); 3263 if (app == null || app.instrumentationClass == null) { 3264 intent.setFlags(intent.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK); 3265 mStackSupervisor.startHomeActivity(intent, aInfo); 3266 } 3267 } 3268 3269 return true; 3270 } 3271 3272 private ActivityInfo resolveActivityInfo(Intent intent, int flags, int userId) { 3273 ActivityInfo ai = null; 3274 ComponentName comp = intent.getComponent(); 3275 try { 3276 if (comp != null) { 3277 ai = AppGlobals.getPackageManager().getActivityInfo(comp, flags, userId); 3278 } else { 3279 ResolveInfo info = AppGlobals.getPackageManager().resolveIntent( 3280 intent, 3281 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 3282 flags, userId); 3283 3284 if (info != null) { 3285 ai = info.activityInfo; 3286 } 3287 } 3288 } catch (RemoteException e) { 3289 // ignore 3290 } 3291 3292 return ai; 3293 } 3294 3295 /** 3296 * Starts the "new version setup screen" if appropriate. 3297 */ 3298 void startSetupActivityLocked() { 3299 // Only do this once per boot. 3300 if (mCheckedForSetup) { 3301 return; 3302 } 3303 3304 // We will show this screen if the current one is a different 3305 // version than the last one shown, and we are not running in 3306 // low-level factory test mode. 3307 final ContentResolver resolver = mContext.getContentResolver(); 3308 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL && 3309 Settings.Global.getInt(resolver, 3310 Settings.Global.DEVICE_PROVISIONED, 0) != 0) { 3311 mCheckedForSetup = true; 3312 3313 // See if we should be showing the platform update setup UI. 3314 Intent intent = new Intent(Intent.ACTION_UPGRADE_SETUP); 3315 List<ResolveInfo> ris = mContext.getPackageManager() 3316 .queryIntentActivities(intent, PackageManager.GET_META_DATA); 3317 3318 // We don't allow third party apps to replace this. 3319 ResolveInfo ri = null; 3320 for (int i=0; ris != null && i<ris.size(); i++) { 3321 if ((ris.get(i).activityInfo.applicationInfo.flags 3322 & ApplicationInfo.FLAG_SYSTEM) != 0) { 3323 ri = ris.get(i); 3324 break; 3325 } 3326 } 3327 3328 if (ri != null) { 3329 String vers = ri.activityInfo.metaData != null 3330 ? ri.activityInfo.metaData.getString(Intent.METADATA_SETUP_VERSION) 3331 : null; 3332 if (vers == null && ri.activityInfo.applicationInfo.metaData != null) { 3333 vers = ri.activityInfo.applicationInfo.metaData.getString( 3334 Intent.METADATA_SETUP_VERSION); 3335 } 3336 String lastVers = Settings.Secure.getString( 3337 resolver, Settings.Secure.LAST_SETUP_SHOWN); 3338 if (vers != null && !vers.equals(lastVers)) { 3339 intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 3340 intent.setComponent(new ComponentName( 3341 ri.activityInfo.packageName, ri.activityInfo.name)); 3342 mStackSupervisor.startActivityLocked(null, intent, null, ri.activityInfo, 3343 null, null, null, null, 0, 0, 0, null, 0, null, false, null, null, 3344 null); 3345 } 3346 } 3347 } 3348 } 3349 3350 CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) { 3351 return mCompatModePackages.compatibilityInfoForPackageLocked(ai); 3352 } 3353 3354 void enforceNotIsolatedCaller(String caller) { 3355 if (UserHandle.isIsolated(Binder.getCallingUid())) { 3356 throw new SecurityException("Isolated process not allowed to call " + caller); 3357 } 3358 } 3359 3360 @Override 3361 public int getFrontActivityScreenCompatMode() { 3362 enforceNotIsolatedCaller("getFrontActivityScreenCompatMode"); 3363 synchronized (this) { 3364 return mCompatModePackages.getFrontActivityScreenCompatModeLocked(); 3365 } 3366 } 3367 3368 @Override 3369 public void setFrontActivityScreenCompatMode(int mode) { 3370 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3371 "setFrontActivityScreenCompatMode"); 3372 synchronized (this) { 3373 mCompatModePackages.setFrontActivityScreenCompatModeLocked(mode); 3374 } 3375 } 3376 3377 @Override 3378 public int getPackageScreenCompatMode(String packageName) { 3379 enforceNotIsolatedCaller("getPackageScreenCompatMode"); 3380 synchronized (this) { 3381 return mCompatModePackages.getPackageScreenCompatModeLocked(packageName); 3382 } 3383 } 3384 3385 @Override 3386 public void setPackageScreenCompatMode(String packageName, int mode) { 3387 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3388 "setPackageScreenCompatMode"); 3389 synchronized (this) { 3390 mCompatModePackages.setPackageScreenCompatModeLocked(packageName, mode); 3391 } 3392 } 3393 3394 @Override 3395 public boolean getPackageAskScreenCompat(String packageName) { 3396 enforceNotIsolatedCaller("getPackageAskScreenCompat"); 3397 synchronized (this) { 3398 return mCompatModePackages.getPackageAskCompatModeLocked(packageName); 3399 } 3400 } 3401 3402 @Override 3403 public void setPackageAskScreenCompat(String packageName, boolean ask) { 3404 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3405 "setPackageAskScreenCompat"); 3406 synchronized (this) { 3407 mCompatModePackages.setPackageAskCompatModeLocked(packageName, ask); 3408 } 3409 } 3410 3411 private void dispatchProcessesChanged() { 3412 int N; 3413 synchronized (this) { 3414 N = mPendingProcessChanges.size(); 3415 if (mActiveProcessChanges.length < N) { 3416 mActiveProcessChanges = new ProcessChangeItem[N]; 3417 } 3418 mPendingProcessChanges.toArray(mActiveProcessChanges); 3419 mAvailProcessChanges.addAll(mPendingProcessChanges); 3420 mPendingProcessChanges.clear(); 3421 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "*** Delivering " + N + " process changes"); 3422 } 3423 3424 int i = mProcessObservers.beginBroadcast(); 3425 while (i > 0) { 3426 i--; 3427 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3428 if (observer != null) { 3429 try { 3430 for (int j=0; j<N; j++) { 3431 ProcessChangeItem item = mActiveProcessChanges[j]; 3432 if ((item.changes&ProcessChangeItem.CHANGE_ACTIVITIES) != 0) { 3433 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "ACTIVITIES CHANGED pid=" 3434 + item.pid + " uid=" + item.uid + ": " 3435 + item.foregroundActivities); 3436 observer.onForegroundActivitiesChanged(item.pid, item.uid, 3437 item.foregroundActivities); 3438 } 3439 if ((item.changes&ProcessChangeItem.CHANGE_PROCESS_STATE) != 0) { 3440 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "PROCSTATE CHANGED pid=" 3441 + item.pid + " uid=" + item.uid + ": " + item.processState); 3442 observer.onProcessStateChanged(item.pid, item.uid, item.processState); 3443 } 3444 } 3445 } catch (RemoteException e) { 3446 } 3447 } 3448 } 3449 mProcessObservers.finishBroadcast(); 3450 } 3451 3452 private void dispatchProcessDied(int pid, int uid) { 3453 int i = mProcessObservers.beginBroadcast(); 3454 while (i > 0) { 3455 i--; 3456 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3457 if (observer != null) { 3458 try { 3459 observer.onProcessDied(pid, uid); 3460 } catch (RemoteException e) { 3461 } 3462 } 3463 } 3464 mProcessObservers.finishBroadcast(); 3465 } 3466 3467 @Override 3468 public final int startActivity(IApplicationThread caller, String callingPackage, 3469 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3470 int startFlags, ProfilerInfo profilerInfo, Bundle options) { 3471 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo, 3472 resultWho, requestCode, startFlags, profilerInfo, options, 3473 UserHandle.getCallingUserId()); 3474 } 3475 3476 @Override 3477 public final int startActivityAsUser(IApplicationThread caller, String callingPackage, 3478 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3479 int startFlags, ProfilerInfo profilerInfo, Bundle options, int userId) { 3480 enforceNotIsolatedCaller("startActivity"); 3481 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3482 false, ALLOW_FULL_ONLY, "startActivity", null); 3483 // TODO: Switch to user app stacks here. 3484 return mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, 3485 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3486 profilerInfo, null, null, options, userId, null, null); 3487 } 3488 3489 @Override 3490 public final int startActivityAsCaller(IApplicationThread caller, String callingPackage, 3491 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3492 int startFlags, ProfilerInfo profilerInfo, Bundle options) { 3493 3494 // This is very dangerous -- it allows you to perform a start activity (including 3495 // permission grants) as any app that may launch one of your own activities. So 3496 // we will only allow this to be done from activities that are part of the core framework, 3497 // and then only when they are running as the system. 3498 final ActivityRecord sourceRecord; 3499 final int targetUid; 3500 final String targetPackage; 3501 synchronized (this) { 3502 if (resultTo == null) { 3503 throw new SecurityException("Must be called from an activity"); 3504 } 3505 sourceRecord = mStackSupervisor.isInAnyStackLocked(resultTo); 3506 if (sourceRecord == null) { 3507 throw new SecurityException("Called with bad activity token: " + resultTo); 3508 } 3509 if (!sourceRecord.info.packageName.equals("android")) { 3510 throw new SecurityException( 3511 "Must be called from an activity that is declared in the android package"); 3512 } 3513 if (sourceRecord.app == null) { 3514 throw new SecurityException("Called without a process attached to activity"); 3515 } 3516 if (UserHandle.getAppId(sourceRecord.app.uid) != Process.SYSTEM_UID) { 3517 // This is still okay, as long as this activity is running under the 3518 // uid of the original calling activity. 3519 if (sourceRecord.app.uid != sourceRecord.launchedFromUid) { 3520 throw new SecurityException( 3521 "Calling activity in uid " + sourceRecord.app.uid 3522 + " must be system uid or original calling uid " 3523 + sourceRecord.launchedFromUid); 3524 } 3525 } 3526 targetUid = sourceRecord.launchedFromUid; 3527 targetPackage = sourceRecord.launchedFromPackage; 3528 } 3529 3530 // TODO: Switch to user app stacks here. 3531 try { 3532 int ret = mStackSupervisor.startActivityMayWait(null, targetUid, targetPackage, intent, 3533 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, null, 3534 null, null, options, UserHandle.getUserId(sourceRecord.app.uid), null, null); 3535 return ret; 3536 } catch (SecurityException e) { 3537 // XXX need to figure out how to propagate to original app. 3538 // A SecurityException here is generally actually a fault of the original 3539 // calling activity (such as a fairly granting permissions), so propagate it 3540 // back to them. 3541 /* 3542 StringBuilder msg = new StringBuilder(); 3543 msg.append("While launching"); 3544 msg.append(intent.toString()); 3545 msg.append(": "); 3546 msg.append(e.getMessage()); 3547 */ 3548 throw e; 3549 } 3550 } 3551 3552 @Override 3553 public final WaitResult startActivityAndWait(IApplicationThread caller, String callingPackage, 3554 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3555 int startFlags, ProfilerInfo profilerInfo, Bundle options, int userId) { 3556 enforceNotIsolatedCaller("startActivityAndWait"); 3557 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3558 false, ALLOW_FULL_ONLY, "startActivityAndWait", null); 3559 WaitResult res = new WaitResult(); 3560 // TODO: Switch to user app stacks here. 3561 mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 3562 null, null, resultTo, resultWho, requestCode, startFlags, profilerInfo, res, null, 3563 options, userId, null, null); 3564 return res; 3565 } 3566 3567 @Override 3568 public final int startActivityWithConfig(IApplicationThread caller, String callingPackage, 3569 Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, 3570 int startFlags, Configuration config, Bundle options, int userId) { 3571 enforceNotIsolatedCaller("startActivityWithConfig"); 3572 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3573 false, ALLOW_FULL_ONLY, "startActivityWithConfig", null); 3574 // TODO: Switch to user app stacks here. 3575 int ret = mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, 3576 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3577 null, null, config, options, userId, null, null); 3578 return ret; 3579 } 3580 3581 @Override 3582 public int startActivityIntentSender(IApplicationThread caller, 3583 IntentSender intent, Intent fillInIntent, String resolvedType, 3584 IBinder resultTo, String resultWho, int requestCode, 3585 int flagsMask, int flagsValues, Bundle options) { 3586 enforceNotIsolatedCaller("startActivityIntentSender"); 3587 // Refuse possible leaked file descriptors 3588 if (fillInIntent != null && fillInIntent.hasFileDescriptors()) { 3589 throw new IllegalArgumentException("File descriptors passed in Intent"); 3590 } 3591 3592 IIntentSender sender = intent.getTarget(); 3593 if (!(sender instanceof PendingIntentRecord)) { 3594 throw new IllegalArgumentException("Bad PendingIntent object"); 3595 } 3596 3597 PendingIntentRecord pir = (PendingIntentRecord)sender; 3598 3599 synchronized (this) { 3600 // If this is coming from the currently resumed activity, it is 3601 // effectively saying that app switches are allowed at this point. 3602 final ActivityStack stack = getFocusedStack(); 3603 if (stack.mResumedActivity != null && 3604 stack.mResumedActivity.info.applicationInfo.uid == Binder.getCallingUid()) { 3605 mAppSwitchesAllowedTime = 0; 3606 } 3607 } 3608 int ret = pir.sendInner(0, fillInIntent, resolvedType, null, null, 3609 resultTo, resultWho, requestCode, flagsMask, flagsValues, options, null); 3610 return ret; 3611 } 3612 3613 @Override 3614 public int startVoiceActivity(String callingPackage, int callingPid, int callingUid, 3615 Intent intent, String resolvedType, IVoiceInteractionSession session, 3616 IVoiceInteractor interactor, int startFlags, ProfilerInfo profilerInfo, 3617 Bundle options, int userId) { 3618 if (checkCallingPermission(Manifest.permission.BIND_VOICE_INTERACTION) 3619 != PackageManager.PERMISSION_GRANTED) { 3620 String msg = "Permission Denial: startVoiceActivity() from pid=" 3621 + Binder.getCallingPid() 3622 + ", uid=" + Binder.getCallingUid() 3623 + " requires " + android.Manifest.permission.BIND_VOICE_INTERACTION; 3624 Slog.w(TAG, msg); 3625 throw new SecurityException(msg); 3626 } 3627 if (session == null || interactor == null) { 3628 throw new NullPointerException("null session or interactor"); 3629 } 3630 userId = handleIncomingUser(callingPid, callingUid, userId, 3631 false, ALLOW_FULL_ONLY, "startVoiceActivity", null); 3632 // TODO: Switch to user app stacks here. 3633 return mStackSupervisor.startActivityMayWait(null, callingUid, callingPackage, intent, 3634 resolvedType, session, interactor, null, null, 0, startFlags, profilerInfo, null, 3635 null, options, userId, null, null); 3636 } 3637 3638 @Override 3639 public boolean startNextMatchingActivity(IBinder callingActivity, 3640 Intent intent, Bundle options) { 3641 // Refuse possible leaked file descriptors 3642 if (intent != null && intent.hasFileDescriptors() == true) { 3643 throw new IllegalArgumentException("File descriptors passed in Intent"); 3644 } 3645 3646 synchronized (this) { 3647 final ActivityRecord r = ActivityRecord.isInStackLocked(callingActivity); 3648 if (r == null) { 3649 ActivityOptions.abort(options); 3650 return false; 3651 } 3652 if (r.app == null || r.app.thread == null) { 3653 // The caller is not running... d'oh! 3654 ActivityOptions.abort(options); 3655 return false; 3656 } 3657 intent = new Intent(intent); 3658 // The caller is not allowed to change the data. 3659 intent.setDataAndType(r.intent.getData(), r.intent.getType()); 3660 // And we are resetting to find the next component... 3661 intent.setComponent(null); 3662 3663 final boolean debug = ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0); 3664 3665 ActivityInfo aInfo = null; 3666 try { 3667 List<ResolveInfo> resolves = 3668 AppGlobals.getPackageManager().queryIntentActivities( 3669 intent, r.resolvedType, 3670 PackageManager.MATCH_DEFAULT_ONLY | STOCK_PM_FLAGS, 3671 UserHandle.getCallingUserId()); 3672 3673 // Look for the original activity in the list... 3674 final int N = resolves != null ? resolves.size() : 0; 3675 for (int i=0; i<N; i++) { 3676 ResolveInfo rInfo = resolves.get(i); 3677 if (rInfo.activityInfo.packageName.equals(r.packageName) 3678 && rInfo.activityInfo.name.equals(r.info.name)) { 3679 // We found the current one... the next matching is 3680 // after it. 3681 i++; 3682 if (i<N) { 3683 aInfo = resolves.get(i).activityInfo; 3684 } 3685 if (debug) { 3686 Slog.v(TAG, "Next matching activity: found current " + r.packageName 3687 + "/" + r.info.name); 3688 Slog.v(TAG, "Next matching activity: next is " + aInfo.packageName 3689 + "/" + aInfo.name); 3690 } 3691 break; 3692 } 3693 } 3694 } catch (RemoteException e) { 3695 } 3696 3697 if (aInfo == null) { 3698 // Nobody who is next! 3699 ActivityOptions.abort(options); 3700 if (debug) Slog.d(TAG, "Next matching activity: nothing found"); 3701 return false; 3702 } 3703 3704 intent.setComponent(new ComponentName( 3705 aInfo.applicationInfo.packageName, aInfo.name)); 3706 intent.setFlags(intent.getFlags()&~( 3707 Intent.FLAG_ACTIVITY_FORWARD_RESULT| 3708 Intent.FLAG_ACTIVITY_CLEAR_TOP| 3709 Intent.FLAG_ACTIVITY_MULTIPLE_TASK| 3710 Intent.FLAG_ACTIVITY_NEW_TASK)); 3711 3712 // Okay now we need to start the new activity, replacing the 3713 // currently running activity. This is a little tricky because 3714 // we want to start the new one as if the current one is finished, 3715 // but not finish the current one first so that there is no flicker. 3716 // And thus... 3717 final boolean wasFinishing = r.finishing; 3718 r.finishing = true; 3719 3720 // Propagate reply information over to the new activity. 3721 final ActivityRecord resultTo = r.resultTo; 3722 final String resultWho = r.resultWho; 3723 final int requestCode = r.requestCode; 3724 r.resultTo = null; 3725 if (resultTo != null) { 3726 resultTo.removeResultsLocked(r, resultWho, requestCode); 3727 } 3728 3729 final long origId = Binder.clearCallingIdentity(); 3730 int res = mStackSupervisor.startActivityLocked(r.app.thread, intent, 3731 r.resolvedType, aInfo, null, null, resultTo != null ? resultTo.appToken : null, 3732 resultWho, requestCode, -1, r.launchedFromUid, r.launchedFromPackage, 0, 3733 options, false, null, null, null); 3734 Binder.restoreCallingIdentity(origId); 3735 3736 r.finishing = wasFinishing; 3737 if (res != ActivityManager.START_SUCCESS) { 3738 return false; 3739 } 3740 return true; 3741 } 3742 } 3743 3744 @Override 3745 public final int startActivityFromRecents(int taskId, Bundle options) { 3746 if (checkCallingPermission(START_TASKS_FROM_RECENTS) != PackageManager.PERMISSION_GRANTED) { 3747 String msg = "Permission Denial: startActivityFromRecents called without " + 3748 START_TASKS_FROM_RECENTS; 3749 Slog.w(TAG, msg); 3750 throw new SecurityException(msg); 3751 } 3752 return startActivityFromRecentsInner(taskId, options); 3753 } 3754 3755 final int startActivityFromRecentsInner(int taskId, Bundle options) { 3756 final TaskRecord task; 3757 final int callingUid; 3758 final String callingPackage; 3759 final Intent intent; 3760 final int userId; 3761 synchronized (this) { 3762 task = recentTaskForIdLocked(taskId); 3763 if (task == null) { 3764 throw new IllegalArgumentException("Task " + taskId + " not found."); 3765 } 3766 callingUid = task.mCallingUid; 3767 callingPackage = task.mCallingPackage; 3768 intent = task.intent; 3769 intent.addFlags(Intent.FLAG_ACTIVITY_LAUNCHED_FROM_HISTORY); 3770 userId = task.userId; 3771 } 3772 return startActivityInPackage(callingUid, callingPackage, intent, null, null, null, 0, 0, 3773 options, userId, null, task); 3774 } 3775 3776 final int startActivityInPackage(int uid, String callingPackage, 3777 Intent intent, String resolvedType, IBinder resultTo, 3778 String resultWho, int requestCode, int startFlags, Bundle options, int userId, 3779 IActivityContainer container, TaskRecord inTask) { 3780 3781 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3782 false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 3783 3784 // TODO: Switch to user app stacks here. 3785 int ret = mStackSupervisor.startActivityMayWait(null, uid, callingPackage, intent, 3786 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3787 null, null, null, options, userId, container, inTask); 3788 return ret; 3789 } 3790 3791 @Override 3792 public final int startActivities(IApplicationThread caller, String callingPackage, 3793 Intent[] intents, String[] resolvedTypes, IBinder resultTo, Bundle options, 3794 int userId) { 3795 enforceNotIsolatedCaller("startActivities"); 3796 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3797 false, ALLOW_FULL_ONLY, "startActivity", null); 3798 // TODO: Switch to user app stacks here. 3799 int ret = mStackSupervisor.startActivities(caller, -1, callingPackage, intents, 3800 resolvedTypes, resultTo, options, userId); 3801 return ret; 3802 } 3803 3804 final int startActivitiesInPackage(int uid, String callingPackage, 3805 Intent[] intents, String[] resolvedTypes, IBinder resultTo, 3806 Bundle options, int userId) { 3807 3808 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3809 false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 3810 // TODO: Switch to user app stacks here. 3811 int ret = mStackSupervisor.startActivities(null, uid, callingPackage, intents, resolvedTypes, 3812 resultTo, options, userId); 3813 return ret; 3814 } 3815 3816 //explicitly remove thd old information in mRecentTasks when removing existing user. 3817 private void removeRecentTasksForUserLocked(int userId) { 3818 if(userId <= 0) { 3819 Slog.i(TAG, "Can't remove recent task on user " + userId); 3820 return; 3821 } 3822 3823 for (int i = mRecentTasks.size() - 1; i >= 0; --i) { 3824 TaskRecord tr = mRecentTasks.get(i); 3825 if (tr.userId == userId) { 3826 if(DEBUG_TASKS) Slog.i(TAG, "remove RecentTask " + tr 3827 + " when finishing user" + userId); 3828 mRecentTasks.remove(i); 3829 tr.removedFromRecents(mTaskPersister); 3830 } 3831 } 3832 3833 // Remove tasks from persistent storage. 3834 mTaskPersister.wakeup(null, true); 3835 } 3836 3837 /** 3838 * Update the recent tasks lists: make sure tasks should still be here (their 3839 * applications / activities still exist), update their availability, fixup ordering 3840 * of affiliations. 3841 */ 3842 void cleanupRecentTasksLocked(int userId) { 3843 if (mRecentTasks == null) { 3844 // Happens when called from the packagemanager broadcast before boot. 3845 return; 3846 } 3847 3848 final HashMap<ComponentName, ActivityInfo> availActCache = new HashMap<>(); 3849 final HashMap<String, ApplicationInfo> availAppCache = new HashMap<>(); 3850 final IPackageManager pm = AppGlobals.getPackageManager(); 3851 final ActivityInfo dummyAct = new ActivityInfo(); 3852 final ApplicationInfo dummyApp = new ApplicationInfo(); 3853 3854 int N = mRecentTasks.size(); 3855 3856 int[] users = userId == UserHandle.USER_ALL 3857 ? getUsersLocked() : new int[] { userId }; 3858 for (int user : users) { 3859 for (int i = 0; i < N; i++) { 3860 TaskRecord task = mRecentTasks.get(i); 3861 if (task.userId != user) { 3862 // Only look at tasks for the user ID of interest. 3863 continue; 3864 } 3865 if (task.autoRemoveRecents && task.getTopActivity() == null) { 3866 // This situation is broken, and we should just get rid of it now. 3867 mRecentTasks.remove(i); 3868 task.removedFromRecents(mTaskPersister); 3869 i--; 3870 N--; 3871 Slog.w(TAG, "Removing auto-remove without activity: " + task); 3872 continue; 3873 } 3874 // Check whether this activity is currently available. 3875 if (task.realActivity != null) { 3876 ActivityInfo ai = availActCache.get(task.realActivity); 3877 if (ai == null) { 3878 try { 3879 ai = pm.getActivityInfo(task.realActivity, 3880 PackageManager.GET_UNINSTALLED_PACKAGES 3881 | PackageManager.GET_DISABLED_COMPONENTS, user); 3882 } catch (RemoteException e) { 3883 // Will never happen. 3884 continue; 3885 } 3886 if (ai == null) { 3887 ai = dummyAct; 3888 } 3889 availActCache.put(task.realActivity, ai); 3890 } 3891 if (ai == dummyAct) { 3892 // This could be either because the activity no longer exists, or the 3893 // app is temporarily gone. For the former we want to remove the recents 3894 // entry; for the latter we want to mark it as unavailable. 3895 ApplicationInfo app = availAppCache.get(task.realActivity.getPackageName()); 3896 if (app == null) { 3897 try { 3898 app = pm.getApplicationInfo(task.realActivity.getPackageName(), 3899 PackageManager.GET_UNINSTALLED_PACKAGES 3900 | PackageManager.GET_DISABLED_COMPONENTS, user); 3901 } catch (RemoteException e) { 3902 // Will never happen. 3903 continue; 3904 } 3905 if (app == null) { 3906 app = dummyApp; 3907 } 3908 availAppCache.put(task.realActivity.getPackageName(), app); 3909 } 3910 if (app == dummyApp || (app.flags&ApplicationInfo.FLAG_INSTALLED) == 0) { 3911 // Doesn't exist any more! Good-bye. 3912 mRecentTasks.remove(i); 3913 task.removedFromRecents(mTaskPersister); 3914 i--; 3915 N--; 3916 Slog.w(TAG, "Removing no longer valid recent: " + task); 3917 continue; 3918 } else { 3919 // Otherwise just not available for now. 3920 if (task.isAvailable) { 3921 if (DEBUG_RECENTS) Slog.d(TAG, "Making recent unavailable: " 3922 + task); 3923 } 3924 task.isAvailable = false; 3925 } 3926 } else { 3927 if (!ai.enabled || !ai.applicationInfo.enabled 3928 || (ai.applicationInfo.flags&ApplicationInfo.FLAG_INSTALLED) == 0) { 3929 if (task.isAvailable) { 3930 if (DEBUG_RECENTS) Slog.d(TAG, "Making recent unavailable: " 3931 + task + " (enabled=" + ai.enabled + "/" 3932 + ai.applicationInfo.enabled + " flags=" 3933 + Integer.toHexString(ai.applicationInfo.flags) + ")"); 3934 } 3935 task.isAvailable = false; 3936 } else { 3937 if (!task.isAvailable) { 3938 if (DEBUG_RECENTS) Slog.d(TAG, "Making recent available: " 3939 + task); 3940 } 3941 task.isAvailable = true; 3942 } 3943 } 3944 } 3945 } 3946 } 3947 3948 // Verify the affiliate chain for each task. 3949 for (int i = 0; i < N; ) { 3950 TaskRecord task = mRecentTasks.remove(i); 3951 if (mTmpRecents.contains(task)) { 3952 continue; 3953 } 3954 int affiliatedTaskId = task.mAffiliatedTaskId; 3955 while (true) { 3956 TaskRecord next = task.mNextAffiliate; 3957 if (next == null) { 3958 break; 3959 } 3960 if (next.mAffiliatedTaskId != affiliatedTaskId) { 3961 Slog.e(TAG, "Error in Recents: next.affiliatedTaskId=" + 3962 next.mAffiliatedTaskId + " affiliatedTaskId=" + affiliatedTaskId); 3963 task.setNextAffiliate(null); 3964 if (next.mPrevAffiliate == task) { 3965 next.setPrevAffiliate(null); 3966 } 3967 break; 3968 } 3969 if (next.mPrevAffiliate != task) { 3970 Slog.e(TAG, "Error in Recents chain prev.mNextAffiliate=" + 3971 next.mPrevAffiliate + " task=" + task); 3972 next.setPrevAffiliate(null); 3973 task.setNextAffiliate(null); 3974 break; 3975 } 3976 if (!mRecentTasks.contains(next)) { 3977 Slog.e(TAG, "Error in Recents: next=" + next + " not in mRecentTasks"); 3978 task.setNextAffiliate(null); 3979 // We know that next.mPrevAffiliate is always task, from above, so clear 3980 // its previous affiliate. 3981 next.setPrevAffiliate(null); 3982 break; 3983 } 3984 task = next; 3985 } 3986 // task is now the end of the list 3987 do { 3988 mRecentTasks.remove(task); 3989 mRecentTasks.add(i++, task); 3990 mTmpRecents.add(task); 3991 task.inRecents = true; 3992 } while ((task = task.mPrevAffiliate) != null); 3993 } 3994 mTmpRecents.clear(); 3995 // mRecentTasks is now in sorted, affiliated order. 3996 } 3997 3998 private final boolean moveAffiliatedTasksToFront(TaskRecord task, int taskIndex) { 3999 int N = mRecentTasks.size(); 4000 TaskRecord top = task; 4001 int topIndex = taskIndex; 4002 while (top.mNextAffiliate != null && topIndex > 0) { 4003 top = top.mNextAffiliate; 4004 topIndex--; 4005 } 4006 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: adding affilliates starting at " 4007 + topIndex + " from intial " + taskIndex); 4008 // Find the end of the chain, doing a sanity check along the way. 4009 boolean sane = top.mAffiliatedTaskId == task.mAffiliatedTaskId; 4010 int endIndex = topIndex; 4011 TaskRecord prev = top; 4012 while (endIndex < N) { 4013 TaskRecord cur = mRecentTasks.get(endIndex); 4014 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: looking at next chain @" 4015 + endIndex + " " + cur); 4016 if (cur == top) { 4017 // Verify start of the chain. 4018 if (cur.mNextAffiliate != null || cur.mNextAffiliateTaskId != -1) { 4019 Slog.wtf(TAG, "Bad chain @" + endIndex 4020 + ": first task has next affiliate: " + prev); 4021 sane = false; 4022 break; 4023 } 4024 } else { 4025 // Verify middle of the chain's next points back to the one before. 4026 if (cur.mNextAffiliate != prev 4027 || cur.mNextAffiliateTaskId != prev.taskId) { 4028 Slog.wtf(TAG, "Bad chain @" + endIndex 4029 + ": middle task " + cur + " @" + endIndex 4030 + " has bad next affiliate " 4031 + cur.mNextAffiliate + " id " + cur.mNextAffiliateTaskId 4032 + ", expected " + prev); 4033 sane = false; 4034 break; 4035 } 4036 } 4037 if (cur.mPrevAffiliateTaskId == -1) { 4038 // Chain ends here. 4039 if (cur.mPrevAffiliate != null) { 4040 Slog.wtf(TAG, "Bad chain @" + endIndex 4041 + ": last task " + cur + " has previous affiliate " 4042 + cur.mPrevAffiliate); 4043 sane = false; 4044 } 4045 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: end of chain @" + endIndex); 4046 break; 4047 } else { 4048 // Verify middle of the chain's prev points to a valid item. 4049 if (cur.mPrevAffiliate == null) { 4050 Slog.wtf(TAG, "Bad chain @" + endIndex 4051 + ": task " + cur + " has previous affiliate " 4052 + cur.mPrevAffiliate + " but should be id " 4053 + cur.mPrevAffiliate); 4054 sane = false; 4055 break; 4056 } 4057 } 4058 if (cur.mAffiliatedTaskId != task.mAffiliatedTaskId) { 4059 Slog.wtf(TAG, "Bad chain @" + endIndex 4060 + ": task " + cur + " has affiliated id " 4061 + cur.mAffiliatedTaskId + " but should be " 4062 + task.mAffiliatedTaskId); 4063 sane = false; 4064 break; 4065 } 4066 prev = cur; 4067 endIndex++; 4068 if (endIndex >= N) { 4069 Slog.wtf(TAG, "Bad chain ran off index " + endIndex 4070 + ": last task " + prev); 4071 sane = false; 4072 break; 4073 } 4074 } 4075 if (sane) { 4076 if (endIndex < taskIndex) { 4077 Slog.wtf(TAG, "Bad chain @" + endIndex 4078 + ": did not extend to task " + task + " @" + taskIndex); 4079 sane = false; 4080 } 4081 } 4082 if (sane) { 4083 // All looks good, we can just move all of the affiliated tasks 4084 // to the top. 4085 for (int i=topIndex; i<=endIndex; i++) { 4086 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: moving affiliated " + task 4087 + " from " + i + " to " + (i-topIndex)); 4088 TaskRecord cur = mRecentTasks.remove(i); 4089 mRecentTasks.add(i-topIndex, cur); 4090 } 4091 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: done moving tasks " + topIndex 4092 + " to " + endIndex); 4093 return true; 4094 } 4095 4096 // Whoops, couldn't do it. 4097 return false; 4098 } 4099 4100 final void addRecentTaskLocked(TaskRecord task) { 4101 final boolean isAffiliated = task.mAffiliatedTaskId != task.taskId 4102 || task.mNextAffiliateTaskId != -1 || task.mPrevAffiliateTaskId != -1; 4103 4104 int N = mRecentTasks.size(); 4105 // Quick case: check if the top-most recent task is the same. 4106 if (!isAffiliated && N > 0 && mRecentTasks.get(0) == task) { 4107 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: already at top: " + task); 4108 return; 4109 } 4110 // Another quick case: check if this is part of a set of affiliated 4111 // tasks that are at the top. 4112 if (isAffiliated && N > 0 && task.inRecents 4113 && task.mAffiliatedTaskId == mRecentTasks.get(0).mAffiliatedTaskId) { 4114 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: affiliated " + mRecentTasks.get(0) 4115 + " at top when adding " + task); 4116 return; 4117 } 4118 // Another quick case: never add voice sessions. 4119 if (task.voiceSession != null) { 4120 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: not adding voice interaction " + task); 4121 return; 4122 } 4123 4124 boolean needAffiliationFix = false; 4125 4126 // Slightly less quick case: the task is already in recents, so all we need 4127 // to do is move it. 4128 if (task.inRecents) { 4129 int taskIndex = mRecentTasks.indexOf(task); 4130 if (taskIndex >= 0) { 4131 if (!isAffiliated) { 4132 // Simple case: this is not an affiliated task, so we just move it to the front. 4133 mRecentTasks.remove(taskIndex); 4134 mRecentTasks.add(0, task); 4135 notifyTaskPersisterLocked(task, false); 4136 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: moving to top " + task 4137 + " from " + taskIndex); 4138 return; 4139 } else { 4140 // More complicated: need to keep all affiliated tasks together. 4141 if (moveAffiliatedTasksToFront(task, taskIndex)) { 4142 // All went well. 4143 return; 4144 } 4145 4146 // Uh oh... something bad in the affiliation chain, try to rebuild 4147 // everything and then go through our general path of adding a new task. 4148 needAffiliationFix = true; 4149 } 4150 } else { 4151 Slog.wtf(TAG, "Task with inRecent not in recents: " + task); 4152 needAffiliationFix = true; 4153 } 4154 } 4155 4156 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: trimming tasks for " + task); 4157 trimRecentsForTask(task, true); 4158 4159 N = mRecentTasks.size(); 4160 while (N >= ActivityManager.getMaxRecentTasksStatic()) { 4161 final TaskRecord tr = mRecentTasks.remove(N - 1); 4162 tr.removedFromRecents(mTaskPersister); 4163 N--; 4164 } 4165 task.inRecents = true; 4166 if (!isAffiliated || needAffiliationFix) { 4167 // If this is a simple non-affiliated task, or we had some failure trying to 4168 // handle it as part of an affilated task, then just place it at the top. 4169 mRecentTasks.add(0, task); 4170 } else if (isAffiliated) { 4171 // If this is a new affiliated task, then move all of the affiliated tasks 4172 // to the front and insert this new one. 4173 TaskRecord other = task.mNextAffiliate; 4174 if (other == null) { 4175 other = task.mPrevAffiliate; 4176 } 4177 if (other != null) { 4178 int otherIndex = mRecentTasks.indexOf(other); 4179 if (otherIndex >= 0) { 4180 // Insert new task at appropriate location. 4181 int taskIndex; 4182 if (other == task.mNextAffiliate) { 4183 // We found the index of our next affiliation, which is who is 4184 // before us in the list, so add after that point. 4185 taskIndex = otherIndex+1; 4186 } else { 4187 // We found the index of our previous affiliation, which is who is 4188 // after us in the list, so add at their position. 4189 taskIndex = otherIndex; 4190 } 4191 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: new affiliated task added at " 4192 + taskIndex + ": " + task); 4193 mRecentTasks.add(taskIndex, task); 4194 4195 // Now move everything to the front. 4196 if (moveAffiliatedTasksToFront(task, taskIndex)) { 4197 // All went well. 4198 return; 4199 } 4200 4201 // Uh oh... something bad in the affiliation chain, try to rebuild 4202 // everything and then go through our general path of adding a new task. 4203 needAffiliationFix = true; 4204 } else { 4205 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: couldn't find other affiliation " 4206 + other); 4207 needAffiliationFix = true; 4208 } 4209 } else { 4210 if (DEBUG_RECENTS) Slog.d(TAG, 4211 "addRecent: adding affiliated task without next/prev:" + task); 4212 needAffiliationFix = true; 4213 } 4214 } 4215 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: adding " + task); 4216 4217 if (needAffiliationFix) { 4218 if (DEBUG_RECENTS) Slog.d(TAG, "addRecent: regrouping affiliations"); 4219 cleanupRecentTasksLocked(task.userId); 4220 } 4221 } 4222 4223 /** 4224 * If needed, remove oldest existing entries in recents that are for the same kind 4225 * of task as the given one. 4226 */ 4227 int trimRecentsForTask(TaskRecord task, boolean doTrim) { 4228 int N = mRecentTasks.size(); 4229 final Intent intent = task.intent; 4230 final boolean document = intent != null && intent.isDocument(); 4231 4232 int maxRecents = task.maxRecents - 1; 4233 for (int i=0; i<N; i++) { 4234 final TaskRecord tr = mRecentTasks.get(i); 4235 if (task != tr) { 4236 if (task.userId != tr.userId) { 4237 continue; 4238 } 4239 if (i > MAX_RECENT_BITMAPS) { 4240 tr.freeLastThumbnail(); 4241 } 4242 final Intent trIntent = tr.intent; 4243 if ((task.affinity == null || !task.affinity.equals(tr.affinity)) && 4244 (intent == null || !intent.filterEquals(trIntent))) { 4245 continue; 4246 } 4247 final boolean trIsDocument = trIntent != null && trIntent.isDocument(); 4248 if (document && trIsDocument) { 4249 // These are the same document activity (not necessarily the same doc). 4250 if (maxRecents > 0) { 4251 --maxRecents; 4252 continue; 4253 } 4254 // Hit the maximum number of documents for this task. Fall through 4255 // and remove this document from recents. 4256 } else if (document || trIsDocument) { 4257 // Only one of these is a document. Not the droid we're looking for. 4258 continue; 4259 } 4260 } 4261 4262 if (!doTrim) { 4263 // If the caller is not actually asking for a trim, just tell them we reached 4264 // a point where the trim would happen. 4265 return i; 4266 } 4267 4268 // Either task and tr are the same or, their affinities match or their intents match 4269 // and neither of them is a document, or they are documents using the same activity 4270 // and their maxRecents has been reached. 4271 tr.disposeThumbnail(); 4272 mRecentTasks.remove(i); 4273 if (task != tr) { 4274 tr.removedFromRecents(mTaskPersister); 4275 } 4276 i--; 4277 N--; 4278 if (task.intent == null) { 4279 // If the new recent task we are adding is not fully 4280 // specified, then replace it with the existing recent task. 4281 task = tr; 4282 } 4283 notifyTaskPersisterLocked(tr, false); 4284 } 4285 4286 return -1; 4287 } 4288 4289 @Override 4290 public void reportActivityFullyDrawn(IBinder token) { 4291 synchronized (this) { 4292 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4293 if (r == null) { 4294 return; 4295 } 4296 r.reportFullyDrawnLocked(); 4297 } 4298 } 4299 4300 @Override 4301 public void setRequestedOrientation(IBinder token, int requestedOrientation) { 4302 synchronized (this) { 4303 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4304 if (r == null) { 4305 return; 4306 } 4307 final long origId = Binder.clearCallingIdentity(); 4308 mWindowManager.setAppOrientation(r.appToken, requestedOrientation); 4309 Configuration config = mWindowManager.updateOrientationFromAppTokens( 4310 mConfiguration, r.mayFreezeScreenLocked(r.app) ? r.appToken : null); 4311 if (config != null) { 4312 r.frozenBeforeDestroy = true; 4313 if (!updateConfigurationLocked(config, r, false, false)) { 4314 mStackSupervisor.resumeTopActivitiesLocked(); 4315 } 4316 } 4317 Binder.restoreCallingIdentity(origId); 4318 } 4319 } 4320 4321 @Override 4322 public int getRequestedOrientation(IBinder token) { 4323 synchronized (this) { 4324 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4325 if (r == null) { 4326 return ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED; 4327 } 4328 return mWindowManager.getAppOrientation(r.appToken); 4329 } 4330 } 4331 4332 /** 4333 * This is the internal entry point for handling Activity.finish(). 4334 * 4335 * @param token The Binder token referencing the Activity we want to finish. 4336 * @param resultCode Result code, if any, from this Activity. 4337 * @param resultData Result data (Intent), if any, from this Activity. 4338 * @param finishTask Whether to finish the task associated with this Activity. Only applies to 4339 * the root Activity in the task. 4340 * 4341 * @return Returns true if the activity successfully finished, or false if it is still running. 4342 */ 4343 @Override 4344 public final boolean finishActivity(IBinder token, int resultCode, Intent resultData, 4345 boolean finishTask) { 4346 // Refuse possible leaked file descriptors 4347 if (resultData != null && resultData.hasFileDescriptors() == true) { 4348 throw new IllegalArgumentException("File descriptors passed in Intent"); 4349 } 4350 4351 synchronized(this) { 4352 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4353 if (r == null) { 4354 return true; 4355 } 4356 // Keep track of the root activity of the task before we finish it 4357 TaskRecord tr = r.task; 4358 ActivityRecord rootR = tr.getRootActivity(); 4359 // Do not allow task to finish in Lock Task mode. 4360 if (tr == mStackSupervisor.mLockTaskModeTask) { 4361 if (rootR == r) { 4362 mStackSupervisor.showLockTaskToast(); 4363 return false; 4364 } 4365 } 4366 if (mController != null) { 4367 // Find the first activity that is not finishing. 4368 ActivityRecord next = r.task.stack.topRunningActivityLocked(token, 0); 4369 if (next != null) { 4370 // ask watcher if this is allowed 4371 boolean resumeOK = true; 4372 try { 4373 resumeOK = mController.activityResuming(next.packageName); 4374 } catch (RemoteException e) { 4375 mController = null; 4376 Watchdog.getInstance().setActivityController(null); 4377 } 4378 4379 if (!resumeOK) { 4380 return false; 4381 } 4382 } 4383 } 4384 final long origId = Binder.clearCallingIdentity(); 4385 try { 4386 boolean res; 4387 if (finishTask && r == rootR) { 4388 // If requested, remove the task that is associated to this activity only if it 4389 // was the root activity in the task. The result code and data is ignored because 4390 // we don't support returning them across task boundaries. 4391 res = removeTaskByIdLocked(tr.taskId, 0); 4392 } else { 4393 res = tr.stack.requestFinishActivityLocked(token, resultCode, 4394 resultData, "app-request", true); 4395 } 4396 return res; 4397 } finally { 4398 Binder.restoreCallingIdentity(origId); 4399 } 4400 } 4401 } 4402 4403 @Override 4404 public final void finishHeavyWeightApp() { 4405 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4406 != PackageManager.PERMISSION_GRANTED) { 4407 String msg = "Permission Denial: finishHeavyWeightApp() from pid=" 4408 + Binder.getCallingPid() 4409 + ", uid=" + Binder.getCallingUid() 4410 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4411 Slog.w(TAG, msg); 4412 throw new SecurityException(msg); 4413 } 4414 4415 synchronized(this) { 4416 if (mHeavyWeightProcess == null) { 4417 return; 4418 } 4419 4420 ArrayList<ActivityRecord> activities = new ArrayList<ActivityRecord>( 4421 mHeavyWeightProcess.activities); 4422 for (int i=0; i<activities.size(); i++) { 4423 ActivityRecord r = activities.get(i); 4424 if (!r.finishing) { 4425 r.task.stack.finishActivityLocked(r, Activity.RESULT_CANCELED, 4426 null, "finish-heavy", true); 4427 } 4428 } 4429 4430 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 4431 mHeavyWeightProcess.userId, 0)); 4432 mHeavyWeightProcess = null; 4433 } 4434 } 4435 4436 @Override 4437 public void crashApplication(int uid, int initialPid, String packageName, 4438 String message) { 4439 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4440 != PackageManager.PERMISSION_GRANTED) { 4441 String msg = "Permission Denial: crashApplication() from pid=" 4442 + Binder.getCallingPid() 4443 + ", uid=" + Binder.getCallingUid() 4444 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4445 Slog.w(TAG, msg); 4446 throw new SecurityException(msg); 4447 } 4448 4449 synchronized(this) { 4450 ProcessRecord proc = null; 4451 4452 // Figure out which process to kill. We don't trust that initialPid 4453 // still has any relation to current pids, so must scan through the 4454 // list. 4455 synchronized (mPidsSelfLocked) { 4456 for (int i=0; i<mPidsSelfLocked.size(); i++) { 4457 ProcessRecord p = mPidsSelfLocked.valueAt(i); 4458 if (p.uid != uid) { 4459 continue; 4460 } 4461 if (p.pid == initialPid) { 4462 proc = p; 4463 break; 4464 } 4465 if (p.pkgList.containsKey(packageName)) { 4466 proc = p; 4467 } 4468 } 4469 } 4470 4471 if (proc == null) { 4472 Slog.w(TAG, "crashApplication: nothing for uid=" + uid 4473 + " initialPid=" + initialPid 4474 + " packageName=" + packageName); 4475 return; 4476 } 4477 4478 if (proc.thread != null) { 4479 if (proc.pid == Process.myPid()) { 4480 Log.w(TAG, "crashApplication: trying to crash self!"); 4481 return; 4482 } 4483 long ident = Binder.clearCallingIdentity(); 4484 try { 4485 proc.thread.scheduleCrash(message); 4486 } catch (RemoteException e) { 4487 } 4488 Binder.restoreCallingIdentity(ident); 4489 } 4490 } 4491 } 4492 4493 @Override 4494 public final void finishSubActivity(IBinder token, String resultWho, 4495 int requestCode) { 4496 synchronized(this) { 4497 final long origId = Binder.clearCallingIdentity(); 4498 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4499 if (r != null) { 4500 r.task.stack.finishSubActivityLocked(r, resultWho, requestCode); 4501 } 4502 Binder.restoreCallingIdentity(origId); 4503 } 4504 } 4505 4506 @Override 4507 public boolean finishActivityAffinity(IBinder token) { 4508 synchronized(this) { 4509 final long origId = Binder.clearCallingIdentity(); 4510 try { 4511 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4512 4513 ActivityRecord rootR = r.task.getRootActivity(); 4514 // Do not allow task to finish in Lock Task mode. 4515 if (r.task == mStackSupervisor.mLockTaskModeTask) { 4516 if (rootR == r) { 4517 mStackSupervisor.showLockTaskToast(); 4518 return false; 4519 } 4520 } 4521 boolean res = false; 4522 if (r != null) { 4523 res = r.task.stack.finishActivityAffinityLocked(r); 4524 } 4525 return res; 4526 } finally { 4527 Binder.restoreCallingIdentity(origId); 4528 } 4529 } 4530 } 4531 4532 @Override 4533 public void finishVoiceTask(IVoiceInteractionSession session) { 4534 synchronized(this) { 4535 final long origId = Binder.clearCallingIdentity(); 4536 try { 4537 mStackSupervisor.finishVoiceTask(session); 4538 } finally { 4539 Binder.restoreCallingIdentity(origId); 4540 } 4541 } 4542 4543 } 4544 4545 @Override 4546 public boolean releaseActivityInstance(IBinder token) { 4547 synchronized(this) { 4548 final long origId = Binder.clearCallingIdentity(); 4549 try { 4550 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4551 if (r.task == null || r.task.stack == null) { 4552 return false; 4553 } 4554 return r.task.stack.safelyDestroyActivityLocked(r, "app-req"); 4555 } finally { 4556 Binder.restoreCallingIdentity(origId); 4557 } 4558 } 4559 } 4560 4561 @Override 4562 public void releaseSomeActivities(IApplicationThread appInt) { 4563 synchronized(this) { 4564 final long origId = Binder.clearCallingIdentity(); 4565 try { 4566 ProcessRecord app = getRecordForAppLocked(appInt); 4567 mStackSupervisor.releaseSomeActivitiesLocked(app, "low-mem"); 4568 } finally { 4569 Binder.restoreCallingIdentity(origId); 4570 } 4571 } 4572 } 4573 4574 @Override 4575 public boolean willActivityBeVisible(IBinder token) { 4576 synchronized(this) { 4577 ActivityStack stack = ActivityRecord.getStackLocked(token); 4578 if (stack != null) { 4579 return stack.willActivityBeVisibleLocked(token); 4580 } 4581 return false; 4582 } 4583 } 4584 4585 @Override 4586 public void overridePendingTransition(IBinder token, String packageName, 4587 int enterAnim, int exitAnim) { 4588 synchronized(this) { 4589 ActivityRecord self = ActivityRecord.isInStackLocked(token); 4590 if (self == null) { 4591 return; 4592 } 4593 4594 final long origId = Binder.clearCallingIdentity(); 4595 4596 if (self.state == ActivityState.RESUMED 4597 || self.state == ActivityState.PAUSING) { 4598 mWindowManager.overridePendingAppTransition(packageName, 4599 enterAnim, exitAnim, null); 4600 } 4601 4602 Binder.restoreCallingIdentity(origId); 4603 } 4604 } 4605 4606 /** 4607 * Main function for removing an existing process from the activity manager 4608 * as a result of that process going away. Clears out all connections 4609 * to the process. 4610 */ 4611 private final void handleAppDiedLocked(ProcessRecord app, 4612 boolean restarting, boolean allowRestart) { 4613 int pid = app.pid; 4614 cleanUpApplicationRecordLocked(app, restarting, allowRestart, -1); 4615 if (!restarting) { 4616 removeLruProcessLocked(app); 4617 if (pid > 0) { 4618 ProcessList.remove(pid); 4619 } 4620 } 4621 4622 if (mProfileProc == app) { 4623 clearProfilerLocked(); 4624 } 4625 4626 // Remove this application's activities from active lists. 4627 boolean hasVisibleActivities = mStackSupervisor.handleAppDiedLocked(app); 4628 4629 app.activities.clear(); 4630 4631 if (app.instrumentationClass != null) { 4632 Slog.w(TAG, "Crash of app " + app.processName 4633 + " running instrumentation " + app.instrumentationClass); 4634 Bundle info = new Bundle(); 4635 info.putString("shortMsg", "Process crashed."); 4636 finishInstrumentationLocked(app, Activity.RESULT_CANCELED, info); 4637 } 4638 4639 if (!restarting) { 4640 if (!mStackSupervisor.resumeTopActivitiesLocked()) { 4641 // If there was nothing to resume, and we are not already 4642 // restarting this process, but there is a visible activity that 4643 // is hosted by the process... then make sure all visible 4644 // activities are running, taking care of restarting this 4645 // process. 4646 if (hasVisibleActivities) { 4647 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 4648 } 4649 } 4650 } 4651 } 4652 4653 private final int getLRURecordIndexForAppLocked(IApplicationThread thread) { 4654 IBinder threadBinder = thread.asBinder(); 4655 // Find the application record. 4656 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4657 ProcessRecord rec = mLruProcesses.get(i); 4658 if (rec.thread != null && rec.thread.asBinder() == threadBinder) { 4659 return i; 4660 } 4661 } 4662 return -1; 4663 } 4664 4665 final ProcessRecord getRecordForAppLocked( 4666 IApplicationThread thread) { 4667 if (thread == null) { 4668 return null; 4669 } 4670 4671 int appIndex = getLRURecordIndexForAppLocked(thread); 4672 return appIndex >= 0 ? mLruProcesses.get(appIndex) : null; 4673 } 4674 4675 final void doLowMemReportIfNeededLocked(ProcessRecord dyingProc) { 4676 // If there are no longer any background processes running, 4677 // and the app that died was not running instrumentation, 4678 // then tell everyone we are now low on memory. 4679 boolean haveBg = false; 4680 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4681 ProcessRecord rec = mLruProcesses.get(i); 4682 if (rec.thread != null 4683 && rec.setProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 4684 haveBg = true; 4685 break; 4686 } 4687 } 4688 4689 if (!haveBg) { 4690 boolean doReport = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 4691 if (doReport) { 4692 long now = SystemClock.uptimeMillis(); 4693 if (now < (mLastMemUsageReportTime+5*60*1000)) { 4694 doReport = false; 4695 } else { 4696 mLastMemUsageReportTime = now; 4697 } 4698 } 4699 final ArrayList<ProcessMemInfo> memInfos 4700 = doReport ? new ArrayList<ProcessMemInfo>(mLruProcesses.size()) : null; 4701 EventLog.writeEvent(EventLogTags.AM_LOW_MEMORY, mLruProcesses.size()); 4702 long now = SystemClock.uptimeMillis(); 4703 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4704 ProcessRecord rec = mLruProcesses.get(i); 4705 if (rec == dyingProc || rec.thread == null) { 4706 continue; 4707 } 4708 if (doReport) { 4709 memInfos.add(new ProcessMemInfo(rec.processName, rec.pid, rec.setAdj, 4710 rec.setProcState, rec.adjType, rec.makeAdjReason())); 4711 } 4712 if ((rec.lastLowMemory+GC_MIN_INTERVAL) <= now) { 4713 // The low memory report is overriding any current 4714 // state for a GC request. Make sure to do 4715 // heavy/important/visible/foreground processes first. 4716 if (rec.setAdj <= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 4717 rec.lastRequestedGc = 0; 4718 } else { 4719 rec.lastRequestedGc = rec.lastLowMemory; 4720 } 4721 rec.reportLowMemory = true; 4722 rec.lastLowMemory = now; 4723 mProcessesToGc.remove(rec); 4724 addProcessToGcListLocked(rec); 4725 } 4726 } 4727 if (doReport) { 4728 Message msg = mHandler.obtainMessage(REPORT_MEM_USAGE_MSG, memInfos); 4729 mHandler.sendMessage(msg); 4730 } 4731 scheduleAppGcsLocked(); 4732 } 4733 } 4734 4735 final void appDiedLocked(ProcessRecord app) { 4736 appDiedLocked(app, app.pid, app.thread); 4737 } 4738 4739 final void appDiedLocked(ProcessRecord app, int pid, 4740 IApplicationThread thread) { 4741 4742 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 4743 synchronized (stats) { 4744 stats.noteProcessDiedLocked(app.info.uid, pid); 4745 } 4746 4747 Process.killProcessGroup(app.info.uid, pid); 4748 4749 // Clean up already done if the process has been re-started. 4750 if (app.pid == pid && app.thread != null && 4751 app.thread.asBinder() == thread.asBinder()) { 4752 boolean doLowMem = app.instrumentationClass == null; 4753 boolean doOomAdj = doLowMem; 4754 if (!app.killedByAm) { 4755 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4756 + ") has died."); 4757 mAllowLowerMemLevel = true; 4758 } else { 4759 // Note that we always want to do oom adj to update our state with the 4760 // new number of procs. 4761 mAllowLowerMemLevel = false; 4762 doLowMem = false; 4763 } 4764 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4765 if (DEBUG_CLEANUP) Slog.v( 4766 TAG, "Dying app: " + app + ", pid: " + pid 4767 + ", thread: " + thread.asBinder()); 4768 handleAppDiedLocked(app, false, true); 4769 4770 if (doOomAdj) { 4771 updateOomAdjLocked(); 4772 } 4773 if (doLowMem) { 4774 doLowMemReportIfNeededLocked(app); 4775 } 4776 } else if (app.pid != pid) { 4777 // A new process has already been started. 4778 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4779 + ") has died and restarted (pid " + app.pid + ")."); 4780 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4781 } else if (DEBUG_PROCESSES) { 4782 Slog.d(TAG, "Received spurious death notification for thread " 4783 + thread.asBinder()); 4784 } 4785 } 4786 4787 /** 4788 * If a stack trace dump file is configured, dump process stack traces. 4789 * @param clearTraces causes the dump file to be erased prior to the new 4790 * traces being written, if true; when false, the new traces will be 4791 * appended to any existing file content. 4792 * @param firstPids of dalvik VM processes to dump stack traces for first 4793 * @param lastPids of dalvik VM processes to dump stack traces for last 4794 * @param nativeProcs optional list of native process names to dump stack crawls 4795 * @return file containing stack traces, or null if no dump file is configured 4796 */ 4797 public static File dumpStackTraces(boolean clearTraces, ArrayList<Integer> firstPids, 4798 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4799 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4800 if (tracesPath == null || tracesPath.length() == 0) { 4801 return null; 4802 } 4803 4804 File tracesFile = new File(tracesPath); 4805 try { 4806 File tracesDir = tracesFile.getParentFile(); 4807 if (!tracesDir.exists()) { 4808 tracesFile.mkdirs(); 4809 if (!SELinux.restorecon(tracesDir)) { 4810 return null; 4811 } 4812 } 4813 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4814 4815 if (clearTraces && tracesFile.exists()) tracesFile.delete(); 4816 tracesFile.createNewFile(); 4817 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4818 } catch (IOException e) { 4819 Slog.w(TAG, "Unable to prepare ANR traces file: " + tracesPath, e); 4820 return null; 4821 } 4822 4823 dumpStackTraces(tracesPath, firstPids, processCpuTracker, lastPids, nativeProcs); 4824 return tracesFile; 4825 } 4826 4827 private static void dumpStackTraces(String tracesPath, ArrayList<Integer> firstPids, 4828 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4829 // Use a FileObserver to detect when traces finish writing. 4830 // The order of traces is considered important to maintain for legibility. 4831 FileObserver observer = new FileObserver(tracesPath, FileObserver.CLOSE_WRITE) { 4832 @Override 4833 public synchronized void onEvent(int event, String path) { notify(); } 4834 }; 4835 4836 try { 4837 observer.startWatching(); 4838 4839 // First collect all of the stacks of the most important pids. 4840 if (firstPids != null) { 4841 try { 4842 int num = firstPids.size(); 4843 for (int i = 0; i < num; i++) { 4844 synchronized (observer) { 4845 Process.sendSignal(firstPids.get(i), Process.SIGNAL_QUIT); 4846 observer.wait(200); // Wait for write-close, give up after 200msec 4847 } 4848 } 4849 } catch (InterruptedException e) { 4850 Log.wtf(TAG, e); 4851 } 4852 } 4853 4854 // Next collect the stacks of the native pids 4855 if (nativeProcs != null) { 4856 int[] pids = Process.getPidsForCommands(nativeProcs); 4857 if (pids != null) { 4858 for (int pid : pids) { 4859 Debug.dumpNativeBacktraceToFile(pid, tracesPath); 4860 } 4861 } 4862 } 4863 4864 // Lastly, measure CPU usage. 4865 if (processCpuTracker != null) { 4866 processCpuTracker.init(); 4867 System.gc(); 4868 processCpuTracker.update(); 4869 try { 4870 synchronized (processCpuTracker) { 4871 processCpuTracker.wait(500); // measure over 1/2 second. 4872 } 4873 } catch (InterruptedException e) { 4874 } 4875 processCpuTracker.update(); 4876 4877 // We'll take the stack crawls of just the top apps using CPU. 4878 final int N = processCpuTracker.countWorkingStats(); 4879 int numProcs = 0; 4880 for (int i=0; i<N && numProcs<5; i++) { 4881 ProcessCpuTracker.Stats stats = processCpuTracker.getWorkingStats(i); 4882 if (lastPids.indexOfKey(stats.pid) >= 0) { 4883 numProcs++; 4884 try { 4885 synchronized (observer) { 4886 Process.sendSignal(stats.pid, Process.SIGNAL_QUIT); 4887 observer.wait(200); // Wait for write-close, give up after 200msec 4888 } 4889 } catch (InterruptedException e) { 4890 Log.wtf(TAG, e); 4891 } 4892 4893 } 4894 } 4895 } 4896 } finally { 4897 observer.stopWatching(); 4898 } 4899 } 4900 4901 final void logAppTooSlow(ProcessRecord app, long startTime, String msg) { 4902 if (true || IS_USER_BUILD) { 4903 return; 4904 } 4905 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4906 if (tracesPath == null || tracesPath.length() == 0) { 4907 return; 4908 } 4909 4910 StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads(); 4911 StrictMode.allowThreadDiskWrites(); 4912 try { 4913 final File tracesFile = new File(tracesPath); 4914 final File tracesDir = tracesFile.getParentFile(); 4915 final File tracesTmp = new File(tracesDir, "__tmp__"); 4916 try { 4917 if (!tracesDir.exists()) { 4918 tracesFile.mkdirs(); 4919 if (!SELinux.restorecon(tracesDir.getPath())) { 4920 return; 4921 } 4922 } 4923 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4924 4925 if (tracesFile.exists()) { 4926 tracesTmp.delete(); 4927 tracesFile.renameTo(tracesTmp); 4928 } 4929 StringBuilder sb = new StringBuilder(); 4930 Time tobj = new Time(); 4931 tobj.set(System.currentTimeMillis()); 4932 sb.append(tobj.format("%Y-%m-%d %H:%M:%S")); 4933 sb.append(": "); 4934 TimeUtils.formatDuration(SystemClock.uptimeMillis()-startTime, sb); 4935 sb.append(" since "); 4936 sb.append(msg); 4937 FileOutputStream fos = new FileOutputStream(tracesFile); 4938 fos.write(sb.toString().getBytes()); 4939 if (app == null) { 4940 fos.write("\n*** No application process!".getBytes()); 4941 } 4942 fos.close(); 4943 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4944 } catch (IOException e) { 4945 Slog.w(TAG, "Unable to prepare slow app traces file: " + tracesPath, e); 4946 return; 4947 } 4948 4949 if (app != null) { 4950 ArrayList<Integer> firstPids = new ArrayList<Integer>(); 4951 firstPids.add(app.pid); 4952 dumpStackTraces(tracesPath, firstPids, null, null, null); 4953 } 4954 4955 File lastTracesFile = null; 4956 File curTracesFile = null; 4957 for (int i=9; i>=0; i--) { 4958 String name = String.format(Locale.US, "slow%02d.txt", i); 4959 curTracesFile = new File(tracesDir, name); 4960 if (curTracesFile.exists()) { 4961 if (lastTracesFile != null) { 4962 curTracesFile.renameTo(lastTracesFile); 4963 } else { 4964 curTracesFile.delete(); 4965 } 4966 } 4967 lastTracesFile = curTracesFile; 4968 } 4969 tracesFile.renameTo(curTracesFile); 4970 if (tracesTmp.exists()) { 4971 tracesTmp.renameTo(tracesFile); 4972 } 4973 } finally { 4974 StrictMode.setThreadPolicy(oldPolicy); 4975 } 4976 } 4977 4978 final void appNotResponding(ProcessRecord app, ActivityRecord activity, 4979 ActivityRecord parent, boolean aboveSystem, final String annotation) { 4980 ArrayList<Integer> firstPids = new ArrayList<Integer>(5); 4981 SparseArray<Boolean> lastPids = new SparseArray<Boolean>(20); 4982 4983 if (mController != null) { 4984 try { 4985 // 0 == continue, -1 = kill process immediately 4986 int res = mController.appEarlyNotResponding(app.processName, app.pid, annotation); 4987 if (res < 0 && app.pid != MY_PID) { 4988 app.kill("anr", true); 4989 } 4990 } catch (RemoteException e) { 4991 mController = null; 4992 Watchdog.getInstance().setActivityController(null); 4993 } 4994 } 4995 4996 long anrTime = SystemClock.uptimeMillis(); 4997 if (MONITOR_CPU_USAGE) { 4998 updateCpuStatsNow(); 4999 } 5000 5001 synchronized (this) { 5002 // PowerManager.reboot() can block for a long time, so ignore ANRs while shutting down. 5003 if (mShuttingDown) { 5004 Slog.i(TAG, "During shutdown skipping ANR: " + app + " " + annotation); 5005 return; 5006 } else if (app.notResponding) { 5007 Slog.i(TAG, "Skipping duplicate ANR: " + app + " " + annotation); 5008 return; 5009 } else if (app.crashing) { 5010 Slog.i(TAG, "Crashing app skipping ANR: " + app + " " + annotation); 5011 return; 5012 } 5013 5014 // In case we come through here for the same app before completing 5015 // this one, mark as anring now so we will bail out. 5016 app.notResponding = true; 5017 5018 // Log the ANR to the event log. 5019 EventLog.writeEvent(EventLogTags.AM_ANR, app.userId, app.pid, 5020 app.processName, app.info.flags, annotation); 5021 5022 // Dump thread traces as quickly as we can, starting with "interesting" processes. 5023 firstPids.add(app.pid); 5024 5025 int parentPid = app.pid; 5026 if (parent != null && parent.app != null && parent.app.pid > 0) parentPid = parent.app.pid; 5027 if (parentPid != app.pid) firstPids.add(parentPid); 5028 5029 if (MY_PID != app.pid && MY_PID != parentPid) firstPids.add(MY_PID); 5030 5031 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 5032 ProcessRecord r = mLruProcesses.get(i); 5033 if (r != null && r.thread != null) { 5034 int pid = r.pid; 5035 if (pid > 0 && pid != app.pid && pid != parentPid && pid != MY_PID) { 5036 if (r.persistent) { 5037 firstPids.add(pid); 5038 } else { 5039 lastPids.put(pid, Boolean.TRUE); 5040 } 5041 } 5042 } 5043 } 5044 } 5045 5046 // Log the ANR to the main log. 5047 StringBuilder info = new StringBuilder(); 5048 info.setLength(0); 5049 info.append("ANR in ").append(app.processName); 5050 if (activity != null && activity.shortComponentName != null) { 5051 info.append(" (").append(activity.shortComponentName).append(")"); 5052 } 5053 info.append("\n"); 5054 info.append("PID: ").append(app.pid).append("\n"); 5055 if (annotation != null) { 5056 info.append("Reason: ").append(annotation).append("\n"); 5057 } 5058 if (parent != null && parent != activity) { 5059 info.append("Parent: ").append(parent.shortComponentName).append("\n"); 5060 } 5061 5062 final ProcessCpuTracker processCpuTracker = new ProcessCpuTracker(true); 5063 5064 File tracesFile = dumpStackTraces(true, firstPids, processCpuTracker, lastPids, 5065 NATIVE_STACKS_OF_INTEREST); 5066 5067 String cpuInfo = null; 5068 if (MONITOR_CPU_USAGE) { 5069 updateCpuStatsNow(); 5070 synchronized (mProcessCpuThread) { 5071 cpuInfo = mProcessCpuTracker.printCurrentState(anrTime); 5072 } 5073 info.append(processCpuTracker.printCurrentLoad()); 5074 info.append(cpuInfo); 5075 } 5076 5077 info.append(processCpuTracker.printCurrentState(anrTime)); 5078 5079 Slog.e(TAG, info.toString()); 5080 if (tracesFile == null) { 5081 // There is no trace file, so dump (only) the alleged culprit's threads to the log 5082 Process.sendSignal(app.pid, Process.SIGNAL_QUIT); 5083 } 5084 5085 addErrorToDropBox("anr", app, app.processName, activity, parent, annotation, 5086 cpuInfo, tracesFile, null); 5087 5088 if (mController != null) { 5089 try { 5090 // 0 == show dialog, 1 = keep waiting, -1 = kill process immediately 5091 int res = mController.appNotResponding(app.processName, app.pid, info.toString()); 5092 if (res != 0) { 5093 if (res < 0 && app.pid != MY_PID) { 5094 app.kill("anr", true); 5095 } else { 5096 synchronized (this) { 5097 mServices.scheduleServiceTimeoutLocked(app); 5098 } 5099 } 5100 return; 5101 } 5102 } catch (RemoteException e) { 5103 mController = null; 5104 Watchdog.getInstance().setActivityController(null); 5105 } 5106 } 5107 5108 // Unless configured otherwise, swallow ANRs in background processes & kill the process. 5109 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 5110 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 5111 5112 synchronized (this) { 5113 if (!showBackground && !app.isInterestingToUserLocked() && app.pid != MY_PID) { 5114 app.kill("bg anr", true); 5115 return; 5116 } 5117 5118 // Set the app's notResponding state, and look up the errorReportReceiver 5119 makeAppNotRespondingLocked(app, 5120 activity != null ? activity.shortComponentName : null, 5121 annotation != null ? "ANR " + annotation : "ANR", 5122 info.toString()); 5123 5124 // Bring up the infamous App Not Responding dialog 5125 Message msg = Message.obtain(); 5126 HashMap<String, Object> map = new HashMap<String, Object>(); 5127 msg.what = SHOW_NOT_RESPONDING_MSG; 5128 msg.obj = map; 5129 msg.arg1 = aboveSystem ? 1 : 0; 5130 map.put("app", app); 5131 if (activity != null) { 5132 map.put("activity", activity); 5133 } 5134 5135 mHandler.sendMessage(msg); 5136 } 5137 } 5138 5139 final void showLaunchWarningLocked(final ActivityRecord cur, final ActivityRecord next) { 5140 if (!mLaunchWarningShown) { 5141 mLaunchWarningShown = true; 5142 mHandler.post(new Runnable() { 5143 @Override 5144 public void run() { 5145 synchronized (ActivityManagerService.this) { 5146 final Dialog d = new LaunchWarningWindow(mContext, cur, next); 5147 d.show(); 5148 mHandler.postDelayed(new Runnable() { 5149 @Override 5150 public void run() { 5151 synchronized (ActivityManagerService.this) { 5152 d.dismiss(); 5153 mLaunchWarningShown = false; 5154 } 5155 } 5156 }, 4000); 5157 } 5158 } 5159 }); 5160 } 5161 } 5162 5163 @Override 5164 public boolean clearApplicationUserData(final String packageName, 5165 final IPackageDataObserver observer, int userId) { 5166 enforceNotIsolatedCaller("clearApplicationUserData"); 5167 int uid = Binder.getCallingUid(); 5168 int pid = Binder.getCallingPid(); 5169 userId = handleIncomingUser(pid, uid, 5170 userId, false, ALLOW_FULL_ONLY, "clearApplicationUserData", null); 5171 long callingId = Binder.clearCallingIdentity(); 5172 try { 5173 IPackageManager pm = AppGlobals.getPackageManager(); 5174 int pkgUid = -1; 5175 synchronized(this) { 5176 try { 5177 pkgUid = pm.getPackageUid(packageName, userId); 5178 } catch (RemoteException e) { 5179 } 5180 if (pkgUid == -1) { 5181 Slog.w(TAG, "Invalid packageName: " + packageName); 5182 if (observer != null) { 5183 try { 5184 observer.onRemoveCompleted(packageName, false); 5185 } catch (RemoteException e) { 5186 Slog.i(TAG, "Observer no longer exists."); 5187 } 5188 } 5189 return false; 5190 } 5191 if (uid == pkgUid || checkComponentPermission( 5192 android.Manifest.permission.CLEAR_APP_USER_DATA, 5193 pid, uid, -1, true) 5194 == PackageManager.PERMISSION_GRANTED) { 5195 forceStopPackageLocked(packageName, pkgUid, "clear data"); 5196 } else { 5197 throw new SecurityException("PID " + pid + " does not have permission " 5198 + android.Manifest.permission.CLEAR_APP_USER_DATA + " to clear data" 5199 + " of package " + packageName); 5200 } 5201 5202 // Remove all tasks match the cleared application package and user 5203 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 5204 final TaskRecord tr = mRecentTasks.get(i); 5205 final String taskPackageName = 5206 tr.getBaseIntent().getComponent().getPackageName(); 5207 if (tr.userId != userId) continue; 5208 if (!taskPackageName.equals(packageName)) continue; 5209 removeTaskByIdLocked(tr.taskId, 0); 5210 } 5211 } 5212 5213 try { 5214 // Clear application user data 5215 pm.clearApplicationUserData(packageName, observer, userId); 5216 5217 synchronized(this) { 5218 // Remove all permissions granted from/to this package 5219 removeUriPermissionsForPackageLocked(packageName, userId, true); 5220 } 5221 5222 Intent intent = new Intent(Intent.ACTION_PACKAGE_DATA_CLEARED, 5223 Uri.fromParts("package", packageName, null)); 5224 intent.putExtra(Intent.EXTRA_UID, pkgUid); 5225 broadcastIntentInPackage("android", Process.SYSTEM_UID, intent, 5226 null, null, 0, null, null, null, false, false, userId); 5227 } catch (RemoteException e) { 5228 } 5229 } finally { 5230 Binder.restoreCallingIdentity(callingId); 5231 } 5232 return true; 5233 } 5234 5235 @Override 5236 public void killBackgroundProcesses(final String packageName, int userId) { 5237 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 5238 != PackageManager.PERMISSION_GRANTED && 5239 checkCallingPermission(android.Manifest.permission.RESTART_PACKAGES) 5240 != PackageManager.PERMISSION_GRANTED) { 5241 String msg = "Permission Denial: killBackgroundProcesses() from pid=" 5242 + Binder.getCallingPid() 5243 + ", uid=" + Binder.getCallingUid() 5244 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 5245 Slog.w(TAG, msg); 5246 throw new SecurityException(msg); 5247 } 5248 5249 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 5250 userId, true, ALLOW_FULL_ONLY, "killBackgroundProcesses", null); 5251 long callingId = Binder.clearCallingIdentity(); 5252 try { 5253 IPackageManager pm = AppGlobals.getPackageManager(); 5254 synchronized(this) { 5255 int appId = -1; 5256 try { 5257 appId = UserHandle.getAppId(pm.getPackageUid(packageName, 0)); 5258 } catch (RemoteException e) { 5259 } 5260 if (appId == -1) { 5261 Slog.w(TAG, "Invalid packageName: " + packageName); 5262 return; 5263 } 5264 killPackageProcessesLocked(packageName, appId, userId, 5265 ProcessList.SERVICE_ADJ, false, true, true, false, "kill background"); 5266 } 5267 } finally { 5268 Binder.restoreCallingIdentity(callingId); 5269 } 5270 } 5271 5272 @Override 5273 public void killAllBackgroundProcesses() { 5274 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 5275 != PackageManager.PERMISSION_GRANTED) { 5276 String msg = "Permission Denial: killAllBackgroundProcesses() from pid=" 5277 + Binder.getCallingPid() 5278 + ", uid=" + Binder.getCallingUid() 5279 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 5280 Slog.w(TAG, msg); 5281 throw new SecurityException(msg); 5282 } 5283 5284 long callingId = Binder.clearCallingIdentity(); 5285 try { 5286 synchronized(this) { 5287 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 5288 final int NP = mProcessNames.getMap().size(); 5289 for (int ip=0; ip<NP; ip++) { 5290 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 5291 final int NA = apps.size(); 5292 for (int ia=0; ia<NA; ia++) { 5293 ProcessRecord app = apps.valueAt(ia); 5294 if (app.persistent) { 5295 // we don't kill persistent processes 5296 continue; 5297 } 5298 if (app.removed) { 5299 procs.add(app); 5300 } else if (app.setAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 5301 app.removed = true; 5302 procs.add(app); 5303 } 5304 } 5305 } 5306 5307 int N = procs.size(); 5308 for (int i=0; i<N; i++) { 5309 removeProcessLocked(procs.get(i), false, true, "kill all background"); 5310 } 5311 mAllowLowerMemLevel = true; 5312 updateOomAdjLocked(); 5313 doLowMemReportIfNeededLocked(null); 5314 } 5315 } finally { 5316 Binder.restoreCallingIdentity(callingId); 5317 } 5318 } 5319 5320 @Override 5321 public void forceStopPackage(final String packageName, int userId) { 5322 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 5323 != PackageManager.PERMISSION_GRANTED) { 5324 String msg = "Permission Denial: forceStopPackage() from pid=" 5325 + Binder.getCallingPid() 5326 + ", uid=" + Binder.getCallingUid() 5327 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 5328 Slog.w(TAG, msg); 5329 throw new SecurityException(msg); 5330 } 5331 final int callingPid = Binder.getCallingPid(); 5332 userId = handleIncomingUser(callingPid, Binder.getCallingUid(), 5333 userId, true, ALLOW_FULL_ONLY, "forceStopPackage", null); 5334 long callingId = Binder.clearCallingIdentity(); 5335 try { 5336 IPackageManager pm = AppGlobals.getPackageManager(); 5337 synchronized(this) { 5338 int[] users = userId == UserHandle.USER_ALL 5339 ? getUsersLocked() : new int[] { userId }; 5340 for (int user : users) { 5341 int pkgUid = -1; 5342 try { 5343 pkgUid = pm.getPackageUid(packageName, user); 5344 } catch (RemoteException e) { 5345 } 5346 if (pkgUid == -1) { 5347 Slog.w(TAG, "Invalid packageName: " + packageName); 5348 continue; 5349 } 5350 try { 5351 pm.setPackageStoppedState(packageName, true, user); 5352 } catch (RemoteException e) { 5353 } catch (IllegalArgumentException e) { 5354 Slog.w(TAG, "Failed trying to unstop package " 5355 + packageName + ": " + e); 5356 } 5357 if (isUserRunningLocked(user, false)) { 5358 forceStopPackageLocked(packageName, pkgUid, "from pid " + callingPid); 5359 } 5360 } 5361 } 5362 } finally { 5363 Binder.restoreCallingIdentity(callingId); 5364 } 5365 } 5366 5367 @Override 5368 public void addPackageDependency(String packageName) { 5369 synchronized (this) { 5370 int callingPid = Binder.getCallingPid(); 5371 if (callingPid == Process.myPid()) { 5372 // Yeah, um, no. 5373 Slog.w(TAG, "Can't addPackageDependency on system process"); 5374 return; 5375 } 5376 ProcessRecord proc; 5377 synchronized (mPidsSelfLocked) { 5378 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 5379 } 5380 if (proc != null) { 5381 if (proc.pkgDeps == null) { 5382 proc.pkgDeps = new ArraySet<String>(1); 5383 } 5384 proc.pkgDeps.add(packageName); 5385 } 5386 } 5387 } 5388 5389 /* 5390 * The pkg name and app id have to be specified. 5391 */ 5392 @Override 5393 public void killApplicationWithAppId(String pkg, int appid, String reason) { 5394 if (pkg == null) { 5395 return; 5396 } 5397 // Make sure the uid is valid. 5398 if (appid < 0) { 5399 Slog.w(TAG, "Invalid appid specified for pkg : " + pkg); 5400 return; 5401 } 5402 int callerUid = Binder.getCallingUid(); 5403 // Only the system server can kill an application 5404 if (callerUid == Process.SYSTEM_UID) { 5405 // Post an aysnc message to kill the application 5406 Message msg = mHandler.obtainMessage(KILL_APPLICATION_MSG); 5407 msg.arg1 = appid; 5408 msg.arg2 = 0; 5409 Bundle bundle = new Bundle(); 5410 bundle.putString("pkg", pkg); 5411 bundle.putString("reason", reason); 5412 msg.obj = bundle; 5413 mHandler.sendMessage(msg); 5414 } else { 5415 throw new SecurityException(callerUid + " cannot kill pkg: " + 5416 pkg); 5417 } 5418 } 5419 5420 @Override 5421 public void closeSystemDialogs(String reason) { 5422 enforceNotIsolatedCaller("closeSystemDialogs"); 5423 5424 final int pid = Binder.getCallingPid(); 5425 final int uid = Binder.getCallingUid(); 5426 final long origId = Binder.clearCallingIdentity(); 5427 try { 5428 synchronized (this) { 5429 // Only allow this from foreground processes, so that background 5430 // applications can't abuse it to prevent system UI from being shown. 5431 if (uid >= Process.FIRST_APPLICATION_UID) { 5432 ProcessRecord proc; 5433 synchronized (mPidsSelfLocked) { 5434 proc = mPidsSelfLocked.get(pid); 5435 } 5436 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 5437 Slog.w(TAG, "Ignoring closeSystemDialogs " + reason 5438 + " from background process " + proc); 5439 return; 5440 } 5441 } 5442 closeSystemDialogsLocked(reason); 5443 } 5444 } finally { 5445 Binder.restoreCallingIdentity(origId); 5446 } 5447 } 5448 5449 void closeSystemDialogsLocked(String reason) { 5450 Intent intent = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS); 5451 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5452 | Intent.FLAG_RECEIVER_FOREGROUND); 5453 if (reason != null) { 5454 intent.putExtra("reason", reason); 5455 } 5456 mWindowManager.closeSystemDialogs(reason); 5457 5458 mStackSupervisor.closeSystemDialogsLocked(); 5459 5460 broadcastIntentLocked(null, null, intent, null, 5461 null, 0, null, null, null, AppOpsManager.OP_NONE, false, false, -1, 5462 Process.SYSTEM_UID, UserHandle.USER_ALL); 5463 } 5464 5465 @Override 5466 public Debug.MemoryInfo[] getProcessMemoryInfo(int[] pids) { 5467 enforceNotIsolatedCaller("getProcessMemoryInfo"); 5468 Debug.MemoryInfo[] infos = new Debug.MemoryInfo[pids.length]; 5469 for (int i=pids.length-1; i>=0; i--) { 5470 ProcessRecord proc; 5471 int oomAdj; 5472 synchronized (this) { 5473 synchronized (mPidsSelfLocked) { 5474 proc = mPidsSelfLocked.get(pids[i]); 5475 oomAdj = proc != null ? proc.setAdj : 0; 5476 } 5477 } 5478 infos[i] = new Debug.MemoryInfo(); 5479 Debug.getMemoryInfo(pids[i], infos[i]); 5480 if (proc != null) { 5481 synchronized (this) { 5482 if (proc.thread != null && proc.setAdj == oomAdj) { 5483 // Record this for posterity if the process has been stable. 5484 proc.baseProcessTracker.addPss(infos[i].getTotalPss(), 5485 infos[i].getTotalUss(), false, proc.pkgList); 5486 } 5487 } 5488 } 5489 } 5490 return infos; 5491 } 5492 5493 @Override 5494 public long[] getProcessPss(int[] pids) { 5495 enforceNotIsolatedCaller("getProcessPss"); 5496 long[] pss = new long[pids.length]; 5497 for (int i=pids.length-1; i>=0; i--) { 5498 ProcessRecord proc; 5499 int oomAdj; 5500 synchronized (this) { 5501 synchronized (mPidsSelfLocked) { 5502 proc = mPidsSelfLocked.get(pids[i]); 5503 oomAdj = proc != null ? proc.setAdj : 0; 5504 } 5505 } 5506 long[] tmpUss = new long[1]; 5507 pss[i] = Debug.getPss(pids[i], tmpUss); 5508 if (proc != null) { 5509 synchronized (this) { 5510 if (proc.thread != null && proc.setAdj == oomAdj) { 5511 // Record this for posterity if the process has been stable. 5512 proc.baseProcessTracker.addPss(pss[i], tmpUss[0], false, proc.pkgList); 5513 } 5514 } 5515 } 5516 } 5517 return pss; 5518 } 5519 5520 @Override 5521 public void killApplicationProcess(String processName, int uid) { 5522 if (processName == null) { 5523 return; 5524 } 5525 5526 int callerUid = Binder.getCallingUid(); 5527 // Only the system server can kill an application 5528 if (callerUid == Process.SYSTEM_UID) { 5529 synchronized (this) { 5530 ProcessRecord app = getProcessRecordLocked(processName, uid, true); 5531 if (app != null && app.thread != null) { 5532 try { 5533 app.thread.scheduleSuicide(); 5534 } catch (RemoteException e) { 5535 // If the other end already died, then our work here is done. 5536 } 5537 } else { 5538 Slog.w(TAG, "Process/uid not found attempting kill of " 5539 + processName + " / " + uid); 5540 } 5541 } 5542 } else { 5543 throw new SecurityException(callerUid + " cannot kill app process: " + 5544 processName); 5545 } 5546 } 5547 5548 private void forceStopPackageLocked(final String packageName, int uid, String reason) { 5549 forceStopPackageLocked(packageName, UserHandle.getAppId(uid), false, 5550 false, true, false, false, UserHandle.getUserId(uid), reason); 5551 Intent intent = new Intent(Intent.ACTION_PACKAGE_RESTARTED, 5552 Uri.fromParts("package", packageName, null)); 5553 if (!mProcessesReady) { 5554 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5555 | Intent.FLAG_RECEIVER_FOREGROUND); 5556 } 5557 intent.putExtra(Intent.EXTRA_UID, uid); 5558 intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(uid)); 5559 broadcastIntentLocked(null, null, intent, 5560 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 5561 false, false, 5562 MY_PID, Process.SYSTEM_UID, UserHandle.getUserId(uid)); 5563 } 5564 5565 private void forceStopUserLocked(int userId, String reason) { 5566 forceStopPackageLocked(null, -1, false, false, true, false, false, userId, reason); 5567 Intent intent = new Intent(Intent.ACTION_USER_STOPPED); 5568 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5569 | Intent.FLAG_RECEIVER_FOREGROUND); 5570 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 5571 broadcastIntentLocked(null, null, intent, 5572 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 5573 false, false, 5574 MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 5575 } 5576 5577 private final boolean killPackageProcessesLocked(String packageName, int appId, 5578 int userId, int minOomAdj, boolean callerWillRestart, boolean allowRestart, 5579 boolean doit, boolean evenPersistent, String reason) { 5580 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 5581 5582 // Remove all processes this package may have touched: all with the 5583 // same UID (except for the system or root user), and all whose name 5584 // matches the package name. 5585 final int NP = mProcessNames.getMap().size(); 5586 for (int ip=0; ip<NP; ip++) { 5587 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 5588 final int NA = apps.size(); 5589 for (int ia=0; ia<NA; ia++) { 5590 ProcessRecord app = apps.valueAt(ia); 5591 if (app.persistent && !evenPersistent) { 5592 // we don't kill persistent processes 5593 continue; 5594 } 5595 if (app.removed) { 5596 if (doit) { 5597 procs.add(app); 5598 } 5599 continue; 5600 } 5601 5602 // Skip process if it doesn't meet our oom adj requirement. 5603 if (app.setAdj < minOomAdj) { 5604 continue; 5605 } 5606 5607 // If no package is specified, we call all processes under the 5608 // give user id. 5609 if (packageName == null) { 5610 if (app.userId != userId) { 5611 continue; 5612 } 5613 if (appId >= 0 && UserHandle.getAppId(app.uid) != appId) { 5614 continue; 5615 } 5616 // Package has been specified, we want to hit all processes 5617 // that match it. We need to qualify this by the processes 5618 // that are running under the specified app and user ID. 5619 } else { 5620 final boolean isDep = app.pkgDeps != null 5621 && app.pkgDeps.contains(packageName); 5622 if (!isDep && UserHandle.getAppId(app.uid) != appId) { 5623 continue; 5624 } 5625 if (userId != UserHandle.USER_ALL && app.userId != userId) { 5626 continue; 5627 } 5628 if (!app.pkgList.containsKey(packageName) && !isDep) { 5629 continue; 5630 } 5631 } 5632 5633 // Process has passed all conditions, kill it! 5634 if (!doit) { 5635 return true; 5636 } 5637 app.removed = true; 5638 procs.add(app); 5639 } 5640 } 5641 5642 int N = procs.size(); 5643 for (int i=0; i<N; i++) { 5644 removeProcessLocked(procs.get(i), callerWillRestart, allowRestart, reason); 5645 } 5646 updateOomAdjLocked(); 5647 return N > 0; 5648 } 5649 5650 private final boolean forceStopPackageLocked(String name, int appId, 5651 boolean callerWillRestart, boolean purgeCache, boolean doit, 5652 boolean evenPersistent, boolean uninstalling, int userId, String reason) { 5653 int i; 5654 int N; 5655 5656 if (userId == UserHandle.USER_ALL && name == null) { 5657 Slog.w(TAG, "Can't force stop all processes of all users, that is insane!"); 5658 } 5659 5660 if (appId < 0 && name != null) { 5661 try { 5662 appId = UserHandle.getAppId( 5663 AppGlobals.getPackageManager().getPackageUid(name, 0)); 5664 } catch (RemoteException e) { 5665 } 5666 } 5667 5668 if (doit) { 5669 if (name != null) { 5670 Slog.i(TAG, "Force stopping " + name + " appid=" + appId 5671 + " user=" + userId + ": " + reason); 5672 } else { 5673 Slog.i(TAG, "Force stopping u" + userId + ": " + reason); 5674 } 5675 5676 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 5677 for (int ip=pmap.size()-1; ip>=0; ip--) { 5678 SparseArray<Long> ba = pmap.valueAt(ip); 5679 for (i=ba.size()-1; i>=0; i--) { 5680 boolean remove = false; 5681 final int entUid = ba.keyAt(i); 5682 if (name != null) { 5683 if (userId == UserHandle.USER_ALL) { 5684 if (UserHandle.getAppId(entUid) == appId) { 5685 remove = true; 5686 } 5687 } else { 5688 if (entUid == UserHandle.getUid(userId, appId)) { 5689 remove = true; 5690 } 5691 } 5692 } else if (UserHandle.getUserId(entUid) == userId) { 5693 remove = true; 5694 } 5695 if (remove) { 5696 ba.removeAt(i); 5697 } 5698 } 5699 if (ba.size() == 0) { 5700 pmap.removeAt(ip); 5701 } 5702 } 5703 } 5704 5705 boolean didSomething = killPackageProcessesLocked(name, appId, userId, 5706 -100, callerWillRestart, true, doit, evenPersistent, 5707 name == null ? ("stop user " + userId) : ("stop " + name)); 5708 5709 if (mStackSupervisor.forceStopPackageLocked(name, doit, evenPersistent, userId)) { 5710 if (!doit) { 5711 return true; 5712 } 5713 didSomething = true; 5714 } 5715 5716 if (mServices.forceStopLocked(name, userId, evenPersistent, doit)) { 5717 if (!doit) { 5718 return true; 5719 } 5720 didSomething = true; 5721 } 5722 5723 if (name == null) { 5724 // Remove all sticky broadcasts from this user. 5725 mStickyBroadcasts.remove(userId); 5726 } 5727 5728 ArrayList<ContentProviderRecord> providers = new ArrayList<ContentProviderRecord>(); 5729 if (mProviderMap.collectForceStopProviders(name, appId, doit, evenPersistent, 5730 userId, providers)) { 5731 if (!doit) { 5732 return true; 5733 } 5734 didSomething = true; 5735 } 5736 N = providers.size(); 5737 for (i=0; i<N; i++) { 5738 removeDyingProviderLocked(null, providers.get(i), true); 5739 } 5740 5741 // Remove transient permissions granted from/to this package/user 5742 removeUriPermissionsForPackageLocked(name, userId, false); 5743 5744 if (name == null || uninstalling) { 5745 // Remove pending intents. For now we only do this when force 5746 // stopping users, because we have some problems when doing this 5747 // for packages -- app widgets are not currently cleaned up for 5748 // such packages, so they can be left with bad pending intents. 5749 if (mIntentSenderRecords.size() > 0) { 5750 Iterator<WeakReference<PendingIntentRecord>> it 5751 = mIntentSenderRecords.values().iterator(); 5752 while (it.hasNext()) { 5753 WeakReference<PendingIntentRecord> wpir = it.next(); 5754 if (wpir == null) { 5755 it.remove(); 5756 continue; 5757 } 5758 PendingIntentRecord pir = wpir.get(); 5759 if (pir == null) { 5760 it.remove(); 5761 continue; 5762 } 5763 if (name == null) { 5764 // Stopping user, remove all objects for the user. 5765 if (pir.key.userId != userId) { 5766 // Not the same user, skip it. 5767 continue; 5768 } 5769 } else { 5770 if (UserHandle.getAppId(pir.uid) != appId) { 5771 // Different app id, skip it. 5772 continue; 5773 } 5774 if (userId != UserHandle.USER_ALL && pir.key.userId != userId) { 5775 // Different user, skip it. 5776 continue; 5777 } 5778 if (!pir.key.packageName.equals(name)) { 5779 // Different package, skip it. 5780 continue; 5781 } 5782 } 5783 if (!doit) { 5784 return true; 5785 } 5786 didSomething = true; 5787 it.remove(); 5788 pir.canceled = true; 5789 if (pir.key.activity != null) { 5790 pir.key.activity.pendingResults.remove(pir.ref); 5791 } 5792 } 5793 } 5794 } 5795 5796 if (doit) { 5797 if (purgeCache && name != null) { 5798 AttributeCache ac = AttributeCache.instance(); 5799 if (ac != null) { 5800 ac.removePackage(name); 5801 } 5802 } 5803 if (mBooted) { 5804 mStackSupervisor.resumeTopActivitiesLocked(); 5805 mStackSupervisor.scheduleIdleLocked(); 5806 } 5807 } 5808 5809 return didSomething; 5810 } 5811 5812 private final boolean removeProcessLocked(ProcessRecord app, 5813 boolean callerWillRestart, boolean allowRestart, String reason) { 5814 final String name = app.processName; 5815 final int uid = app.uid; 5816 if (DEBUG_PROCESSES) Slog.d( 5817 TAG, "Force removing proc " + app.toShortString() + " (" + name 5818 + "/" + uid + ")"); 5819 5820 mProcessNames.remove(name, uid); 5821 mIsolatedProcesses.remove(app.uid); 5822 if (mHeavyWeightProcess == app) { 5823 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5824 mHeavyWeightProcess.userId, 0)); 5825 mHeavyWeightProcess = null; 5826 } 5827 boolean needRestart = false; 5828 if (app.pid > 0 && app.pid != MY_PID) { 5829 int pid = app.pid; 5830 synchronized (mPidsSelfLocked) { 5831 mPidsSelfLocked.remove(pid); 5832 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5833 } 5834 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 5835 if (app.isolated) { 5836 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5837 } 5838 app.kill(reason, true); 5839 handleAppDiedLocked(app, true, allowRestart); 5840 removeLruProcessLocked(app); 5841 5842 if (app.persistent && !app.isolated) { 5843 if (!callerWillRestart) { 5844 addAppLocked(app.info, false, null /* ABI override */); 5845 } else { 5846 needRestart = true; 5847 } 5848 } 5849 } else { 5850 mRemovedProcesses.add(app); 5851 } 5852 5853 return needRestart; 5854 } 5855 5856 private final void processStartTimedOutLocked(ProcessRecord app) { 5857 final int pid = app.pid; 5858 boolean gone = false; 5859 synchronized (mPidsSelfLocked) { 5860 ProcessRecord knownApp = mPidsSelfLocked.get(pid); 5861 if (knownApp != null && knownApp.thread == null) { 5862 mPidsSelfLocked.remove(pid); 5863 gone = true; 5864 } 5865 } 5866 5867 if (gone) { 5868 Slog.w(TAG, "Process " + app + " failed to attach"); 5869 EventLog.writeEvent(EventLogTags.AM_PROCESS_START_TIMEOUT, app.userId, 5870 pid, app.uid, app.processName); 5871 mProcessNames.remove(app.processName, app.uid); 5872 mIsolatedProcesses.remove(app.uid); 5873 if (mHeavyWeightProcess == app) { 5874 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5875 mHeavyWeightProcess.userId, 0)); 5876 mHeavyWeightProcess = null; 5877 } 5878 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 5879 if (app.isolated) { 5880 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5881 } 5882 // Take care of any launching providers waiting for this process. 5883 checkAppInLaunchingProvidersLocked(app, true); 5884 // Take care of any services that are waiting for the process. 5885 mServices.processStartTimedOutLocked(app); 5886 app.kill("start timeout", true); 5887 if (mBackupTarget != null && mBackupTarget.app.pid == pid) { 5888 Slog.w(TAG, "Unattached app died before backup, skipping"); 5889 try { 5890 IBackupManager bm = IBackupManager.Stub.asInterface( 5891 ServiceManager.getService(Context.BACKUP_SERVICE)); 5892 bm.agentDisconnected(app.info.packageName); 5893 } catch (RemoteException e) { 5894 // Can't happen; the backup manager is local 5895 } 5896 } 5897 if (isPendingBroadcastProcessLocked(pid)) { 5898 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 5899 skipPendingBroadcastLocked(pid); 5900 } 5901 } else { 5902 Slog.w(TAG, "Spurious process start timeout - pid not known for " + app); 5903 } 5904 } 5905 5906 private final boolean attachApplicationLocked(IApplicationThread thread, 5907 int pid) { 5908 5909 // Find the application record that is being attached... either via 5910 // the pid if we are running in multiple processes, or just pull the 5911 // next app record if we are emulating process with anonymous threads. 5912 ProcessRecord app; 5913 if (pid != MY_PID && pid >= 0) { 5914 synchronized (mPidsSelfLocked) { 5915 app = mPidsSelfLocked.get(pid); 5916 } 5917 } else { 5918 app = null; 5919 } 5920 5921 if (app == null) { 5922 Slog.w(TAG, "No pending application record for pid " + pid 5923 + " (IApplicationThread " + thread + "); dropping process"); 5924 EventLog.writeEvent(EventLogTags.AM_DROP_PROCESS, pid); 5925 if (pid > 0 && pid != MY_PID) { 5926 Process.killProcessQuiet(pid); 5927 //TODO: Process.killProcessGroup(app.info.uid, pid); 5928 } else { 5929 try { 5930 thread.scheduleExit(); 5931 } catch (Exception e) { 5932 // Ignore exceptions. 5933 } 5934 } 5935 return false; 5936 } 5937 5938 // If this application record is still attached to a previous 5939 // process, clean it up now. 5940 if (app.thread != null) { 5941 handleAppDiedLocked(app, true, true); 5942 } 5943 5944 // Tell the process all about itself. 5945 5946 if (localLOGV) Slog.v( 5947 TAG, "Binding process pid " + pid + " to record " + app); 5948 5949 final String processName = app.processName; 5950 try { 5951 AppDeathRecipient adr = new AppDeathRecipient( 5952 app, pid, thread); 5953 thread.asBinder().linkToDeath(adr, 0); 5954 app.deathRecipient = adr; 5955 } catch (RemoteException e) { 5956 app.resetPackageList(mProcessStats); 5957 startProcessLocked(app, "link fail", processName); 5958 return false; 5959 } 5960 5961 EventLog.writeEvent(EventLogTags.AM_PROC_BOUND, app.userId, app.pid, app.processName); 5962 5963 app.makeActive(thread, mProcessStats); 5964 app.curAdj = app.setAdj = -100; 5965 app.curSchedGroup = app.setSchedGroup = Process.THREAD_GROUP_DEFAULT; 5966 app.forcingToForeground = null; 5967 updateProcessForegroundLocked(app, false, false); 5968 app.hasShownUi = false; 5969 app.debugging = false; 5970 app.cached = false; 5971 5972 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5973 5974 boolean normalMode = mProcessesReady || isAllowedWhileBooting(app.info); 5975 List<ProviderInfo> providers = normalMode ? generateApplicationProvidersLocked(app) : null; 5976 5977 if (!normalMode) { 5978 Slog.i(TAG, "Launching preboot mode app: " + app); 5979 } 5980 5981 if (localLOGV) Slog.v( 5982 TAG, "New app record " + app 5983 + " thread=" + thread.asBinder() + " pid=" + pid); 5984 try { 5985 int testMode = IApplicationThread.DEBUG_OFF; 5986 if (mDebugApp != null && mDebugApp.equals(processName)) { 5987 testMode = mWaitForDebugger 5988 ? IApplicationThread.DEBUG_WAIT 5989 : IApplicationThread.DEBUG_ON; 5990 app.debugging = true; 5991 if (mDebugTransient) { 5992 mDebugApp = mOrigDebugApp; 5993 mWaitForDebugger = mOrigWaitForDebugger; 5994 } 5995 } 5996 String profileFile = app.instrumentationProfileFile; 5997 ParcelFileDescriptor profileFd = null; 5998 int samplingInterval = 0; 5999 boolean profileAutoStop = false; 6000 if (mProfileApp != null && mProfileApp.equals(processName)) { 6001 mProfileProc = app; 6002 profileFile = mProfileFile; 6003 profileFd = mProfileFd; 6004 samplingInterval = mSamplingInterval; 6005 profileAutoStop = mAutoStopProfiler; 6006 } 6007 boolean enableOpenGlTrace = false; 6008 if (mOpenGlTraceApp != null && mOpenGlTraceApp.equals(processName)) { 6009 enableOpenGlTrace = true; 6010 mOpenGlTraceApp = null; 6011 } 6012 6013 // If the app is being launched for restore or full backup, set it up specially 6014 boolean isRestrictedBackupMode = false; 6015 if (mBackupTarget != null && mBackupAppName.equals(processName)) { 6016 isRestrictedBackupMode = (mBackupTarget.backupMode == BackupRecord.RESTORE) 6017 || (mBackupTarget.backupMode == BackupRecord.RESTORE_FULL) 6018 || (mBackupTarget.backupMode == BackupRecord.BACKUP_FULL); 6019 } 6020 6021 ensurePackageDexOpt(app.instrumentationInfo != null 6022 ? app.instrumentationInfo.packageName 6023 : app.info.packageName); 6024 if (app.instrumentationClass != null) { 6025 ensurePackageDexOpt(app.instrumentationClass.getPackageName()); 6026 } 6027 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Binding proc " 6028 + processName + " with config " + mConfiguration); 6029 ApplicationInfo appInfo = app.instrumentationInfo != null 6030 ? app.instrumentationInfo : app.info; 6031 app.compat = compatibilityInfoForPackageLocked(appInfo); 6032 if (profileFd != null) { 6033 profileFd = profileFd.dup(); 6034 } 6035 ProfilerInfo profilerInfo = profileFile == null ? null 6036 : new ProfilerInfo(profileFile, profileFd, samplingInterval, profileAutoStop); 6037 thread.bindApplication(processName, appInfo, providers, app.instrumentationClass, 6038 profilerInfo, app.instrumentationArguments, app.instrumentationWatcher, 6039 app.instrumentationUiAutomationConnection, testMode, enableOpenGlTrace, 6040 isRestrictedBackupMode || !normalMode, app.persistent, 6041 new Configuration(mConfiguration), app.compat, getCommonServicesLocked(), 6042 mCoreSettingsObserver.getCoreSettingsLocked()); 6043 updateLruProcessLocked(app, false, null); 6044 app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis(); 6045 } catch (Exception e) { 6046 // todo: Yikes! What should we do? For now we will try to 6047 // start another process, but that could easily get us in 6048 // an infinite loop of restarting processes... 6049 Slog.w(TAG, "Exception thrown during bind!", e); 6050 6051 app.resetPackageList(mProcessStats); 6052 app.unlinkDeathRecipient(); 6053 startProcessLocked(app, "bind fail", processName); 6054 return false; 6055 } 6056 6057 // Remove this record from the list of starting applications. 6058 mPersistentStartingProcesses.remove(app); 6059 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 6060 "Attach application locked removing on hold: " + app); 6061 mProcessesOnHold.remove(app); 6062 6063 boolean badApp = false; 6064 boolean didSomething = false; 6065 6066 // See if the top visible activity is waiting to run in this process... 6067 if (normalMode) { 6068 try { 6069 if (mStackSupervisor.attachApplicationLocked(app)) { 6070 didSomething = true; 6071 } 6072 } catch (Exception e) { 6073 badApp = true; 6074 } 6075 } 6076 6077 // Find any services that should be running in this process... 6078 if (!badApp) { 6079 try { 6080 didSomething |= mServices.attachApplicationLocked(app, processName); 6081 } catch (Exception e) { 6082 badApp = true; 6083 } 6084 } 6085 6086 // Check if a next-broadcast receiver is in this process... 6087 if (!badApp && isPendingBroadcastProcessLocked(pid)) { 6088 try { 6089 didSomething |= sendPendingBroadcastsLocked(app); 6090 } catch (Exception e) { 6091 // If the app died trying to launch the receiver we declare it 'bad' 6092 badApp = true; 6093 } 6094 } 6095 6096 // Check whether the next backup agent is in this process... 6097 if (!badApp && mBackupTarget != null && mBackupTarget.appInfo.uid == app.uid) { 6098 if (DEBUG_BACKUP) Slog.v(TAG, "New app is backup target, launching agent for " + app); 6099 ensurePackageDexOpt(mBackupTarget.appInfo.packageName); 6100 try { 6101 thread.scheduleCreateBackupAgent(mBackupTarget.appInfo, 6102 compatibilityInfoForPackageLocked(mBackupTarget.appInfo), 6103 mBackupTarget.backupMode); 6104 } catch (Exception e) { 6105 Slog.w(TAG, "Exception scheduling backup agent creation: "); 6106 e.printStackTrace(); 6107 } 6108 } 6109 6110 if (badApp) { 6111 // todo: Also need to kill application to deal with all 6112 // kinds of exceptions. 6113 handleAppDiedLocked(app, false, true); 6114 return false; 6115 } 6116 6117 if (!didSomething) { 6118 updateOomAdjLocked(); 6119 } 6120 6121 return true; 6122 } 6123 6124 @Override 6125 public final void attachApplication(IApplicationThread thread) { 6126 synchronized (this) { 6127 int callingPid = Binder.getCallingPid(); 6128 final long origId = Binder.clearCallingIdentity(); 6129 attachApplicationLocked(thread, callingPid); 6130 Binder.restoreCallingIdentity(origId); 6131 } 6132 } 6133 6134 @Override 6135 public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) { 6136 final long origId = Binder.clearCallingIdentity(); 6137 synchronized (this) { 6138 ActivityStack stack = ActivityRecord.getStackLocked(token); 6139 if (stack != null) { 6140 ActivityRecord r = 6141 mStackSupervisor.activityIdleInternalLocked(token, false, config); 6142 if (stopProfiling) { 6143 if ((mProfileProc == r.app) && (mProfileFd != null)) { 6144 try { 6145 mProfileFd.close(); 6146 } catch (IOException e) { 6147 } 6148 clearProfilerLocked(); 6149 } 6150 } 6151 } 6152 } 6153 Binder.restoreCallingIdentity(origId); 6154 } 6155 6156 void postEnableScreenAfterBootLocked() { 6157 mHandler.sendEmptyMessage(ENABLE_SCREEN_AFTER_BOOT_MSG); 6158 } 6159 6160 void enableScreenAfterBoot() { 6161 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN, 6162 SystemClock.uptimeMillis()); 6163 mWindowManager.enableScreenAfterBoot(); 6164 6165 synchronized (this) { 6166 updateEventDispatchingLocked(); 6167 } 6168 } 6169 6170 @Override 6171 public void showBootMessage(final CharSequence msg, final boolean always) { 6172 enforceNotIsolatedCaller("showBootMessage"); 6173 mWindowManager.showBootMessage(msg, always); 6174 } 6175 6176 @Override 6177 public void keyguardWaitingForActivityDrawn() { 6178 enforceNotIsolatedCaller("keyguardWaitingForActivityDrawn"); 6179 final long token = Binder.clearCallingIdentity(); 6180 try { 6181 synchronized (this) { 6182 if (DEBUG_LOCKSCREEN) logLockScreen(""); 6183 mWindowManager.keyguardWaitingForActivityDrawn(); 6184 } 6185 } finally { 6186 Binder.restoreCallingIdentity(token); 6187 } 6188 } 6189 6190 final void finishBooting() { 6191 // Register receivers to handle package update events 6192 mPackageMonitor.register(mContext, Looper.getMainLooper(), false); 6193 6194 // Let system services know. 6195 mSystemServiceManager.startBootPhase(SystemService.PHASE_BOOT_COMPLETED); 6196 6197 synchronized (this) { 6198 // Ensure that any processes we had put on hold are now started 6199 // up. 6200 final int NP = mProcessesOnHold.size(); 6201 if (NP > 0) { 6202 ArrayList<ProcessRecord> procs = 6203 new ArrayList<ProcessRecord>(mProcessesOnHold); 6204 for (int ip=0; ip<NP; ip++) { 6205 if (DEBUG_PROCESSES) Slog.v(TAG, "Starting process on hold: " 6206 + procs.get(ip)); 6207 startProcessLocked(procs.get(ip), "on-hold", null); 6208 } 6209 } 6210 6211 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 6212 // Start looking for apps that are abusing wake locks. 6213 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 6214 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 6215 // Tell anyone interested that we are done booting! 6216 SystemProperties.set("sys.boot_completed", "1"); 6217 SystemProperties.set("dev.bootcomplete", "1"); 6218 for (int i=0; i<mStartedUsers.size(); i++) { 6219 UserStartedState uss = mStartedUsers.valueAt(i); 6220 if (uss.mState == UserStartedState.STATE_BOOTING) { 6221 uss.mState = UserStartedState.STATE_RUNNING; 6222 final int userId = mStartedUsers.keyAt(i); 6223 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 6224 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 6225 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 6226 broadcastIntentLocked(null, null, intent, null, 6227 new IIntentReceiver.Stub() { 6228 @Override 6229 public void performReceive(Intent intent, int resultCode, 6230 String data, Bundle extras, boolean ordered, 6231 boolean sticky, int sendingUser) { 6232 synchronized (ActivityManagerService.this) { 6233 requestPssAllProcsLocked(SystemClock.uptimeMillis(), 6234 true, false); 6235 } 6236 } 6237 }, 6238 0, null, null, 6239 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, 6240 AppOpsManager.OP_NONE, true, false, MY_PID, Process.SYSTEM_UID, 6241 userId); 6242 } 6243 } 6244 scheduleStartProfilesLocked(); 6245 } 6246 } 6247 } 6248 6249 final void ensureBootCompleted() { 6250 boolean booting; 6251 boolean enableScreen; 6252 synchronized (this) { 6253 booting = mBooting; 6254 mBooting = false; 6255 enableScreen = !mBooted; 6256 mBooted = true; 6257 } 6258 6259 if (booting) { 6260 finishBooting(); 6261 } 6262 6263 if (enableScreen) { 6264 enableScreenAfterBoot(); 6265 } 6266 } 6267 6268 @Override 6269 public final void activityResumed(IBinder token) { 6270 final long origId = Binder.clearCallingIdentity(); 6271 synchronized(this) { 6272 ActivityStack stack = ActivityRecord.getStackLocked(token); 6273 if (stack != null) { 6274 ActivityRecord.activityResumedLocked(token); 6275 } 6276 } 6277 Binder.restoreCallingIdentity(origId); 6278 } 6279 6280 @Override 6281 public final void activityPaused(IBinder token) { 6282 final long origId = Binder.clearCallingIdentity(); 6283 synchronized(this) { 6284 ActivityStack stack = ActivityRecord.getStackLocked(token); 6285 if (stack != null) { 6286 stack.activityPausedLocked(token, false); 6287 } 6288 } 6289 Binder.restoreCallingIdentity(origId); 6290 } 6291 6292 @Override 6293 public final void activityStopped(IBinder token, Bundle icicle, 6294 PersistableBundle persistentState, CharSequence description) { 6295 if (localLOGV) Slog.v(TAG, "Activity stopped: token=" + token); 6296 6297 // Refuse possible leaked file descriptors 6298 if (icicle != null && icicle.hasFileDescriptors()) { 6299 throw new IllegalArgumentException("File descriptors passed in Bundle"); 6300 } 6301 6302 final long origId = Binder.clearCallingIdentity(); 6303 6304 synchronized (this) { 6305 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6306 if (r != null) { 6307 r.task.stack.activityStoppedLocked(r, icicle, persistentState, description); 6308 } 6309 } 6310 6311 trimApplications(); 6312 6313 Binder.restoreCallingIdentity(origId); 6314 } 6315 6316 @Override 6317 public final void activityDestroyed(IBinder token) { 6318 if (DEBUG_SWITCH) Slog.v(TAG, "ACTIVITY DESTROYED: " + token); 6319 synchronized (this) { 6320 ActivityStack stack = ActivityRecord.getStackLocked(token); 6321 if (stack != null) { 6322 stack.activityDestroyedLocked(token); 6323 } 6324 } 6325 } 6326 6327 @Override 6328 public final void backgroundResourcesReleased(IBinder token) { 6329 final long origId = Binder.clearCallingIdentity(); 6330 try { 6331 synchronized (this) { 6332 ActivityStack stack = ActivityRecord.getStackLocked(token); 6333 if (stack != null) { 6334 stack.backgroundResourcesReleased(token); 6335 } 6336 } 6337 } finally { 6338 Binder.restoreCallingIdentity(origId); 6339 } 6340 } 6341 6342 @Override 6343 public final void notifyLaunchTaskBehindComplete(IBinder token) { 6344 mStackSupervisor.scheduleLaunchTaskBehindComplete(token); 6345 } 6346 6347 @Override 6348 public final void notifyEnterAnimationComplete(IBinder token) { 6349 mHandler.sendMessage(mHandler.obtainMessage(ENTER_ANIMATION_COMPLETE_MSG, token)); 6350 } 6351 6352 @Override 6353 public String getCallingPackage(IBinder token) { 6354 synchronized (this) { 6355 ActivityRecord r = getCallingRecordLocked(token); 6356 return r != null ? r.info.packageName : null; 6357 } 6358 } 6359 6360 @Override 6361 public ComponentName getCallingActivity(IBinder token) { 6362 synchronized (this) { 6363 ActivityRecord r = getCallingRecordLocked(token); 6364 return r != null ? r.intent.getComponent() : null; 6365 } 6366 } 6367 6368 private ActivityRecord getCallingRecordLocked(IBinder token) { 6369 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6370 if (r == null) { 6371 return null; 6372 } 6373 return r.resultTo; 6374 } 6375 6376 @Override 6377 public ComponentName getActivityClassForToken(IBinder token) { 6378 synchronized(this) { 6379 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6380 if (r == null) { 6381 return null; 6382 } 6383 return r.intent.getComponent(); 6384 } 6385 } 6386 6387 @Override 6388 public String getPackageForToken(IBinder token) { 6389 synchronized(this) { 6390 ActivityRecord r = ActivityRecord.isInStackLocked(token); 6391 if (r == null) { 6392 return null; 6393 } 6394 return r.packageName; 6395 } 6396 } 6397 6398 @Override 6399 public IIntentSender getIntentSender(int type, 6400 String packageName, IBinder token, String resultWho, 6401 int requestCode, Intent[] intents, String[] resolvedTypes, 6402 int flags, Bundle options, int userId) { 6403 enforceNotIsolatedCaller("getIntentSender"); 6404 // Refuse possible leaked file descriptors 6405 if (intents != null) { 6406 if (intents.length < 1) { 6407 throw new IllegalArgumentException("Intents array length must be >= 1"); 6408 } 6409 for (int i=0; i<intents.length; i++) { 6410 Intent intent = intents[i]; 6411 if (intent != null) { 6412 if (intent.hasFileDescriptors()) { 6413 throw new IllegalArgumentException("File descriptors passed in Intent"); 6414 } 6415 if (type == ActivityManager.INTENT_SENDER_BROADCAST && 6416 (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 6417 throw new IllegalArgumentException( 6418 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 6419 } 6420 intents[i] = new Intent(intent); 6421 } 6422 } 6423 if (resolvedTypes != null && resolvedTypes.length != intents.length) { 6424 throw new IllegalArgumentException( 6425 "Intent array length does not match resolvedTypes length"); 6426 } 6427 } 6428 if (options != null) { 6429 if (options.hasFileDescriptors()) { 6430 throw new IllegalArgumentException("File descriptors passed in options"); 6431 } 6432 } 6433 6434 synchronized(this) { 6435 int callingUid = Binder.getCallingUid(); 6436 int origUserId = userId; 6437 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 6438 type == ActivityManager.INTENT_SENDER_BROADCAST, 6439 ALLOW_NON_FULL, "getIntentSender", null); 6440 if (origUserId == UserHandle.USER_CURRENT) { 6441 // We don't want to evaluate this until the pending intent is 6442 // actually executed. However, we do want to always do the 6443 // security checking for it above. 6444 userId = UserHandle.USER_CURRENT; 6445 } 6446 try { 6447 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 6448 int uid = AppGlobals.getPackageManager() 6449 .getPackageUid(packageName, UserHandle.getUserId(callingUid)); 6450 if (!UserHandle.isSameApp(callingUid, uid)) { 6451 String msg = "Permission Denial: getIntentSender() from pid=" 6452 + Binder.getCallingPid() 6453 + ", uid=" + Binder.getCallingUid() 6454 + ", (need uid=" + uid + ")" 6455 + " is not allowed to send as package " + packageName; 6456 Slog.w(TAG, msg); 6457 throw new SecurityException(msg); 6458 } 6459 } 6460 6461 return getIntentSenderLocked(type, packageName, callingUid, userId, 6462 token, resultWho, requestCode, intents, resolvedTypes, flags, options); 6463 6464 } catch (RemoteException e) { 6465 throw new SecurityException(e); 6466 } 6467 } 6468 } 6469 6470 IIntentSender getIntentSenderLocked(int type, String packageName, 6471 int callingUid, int userId, IBinder token, String resultWho, 6472 int requestCode, Intent[] intents, String[] resolvedTypes, int flags, 6473 Bundle options) { 6474 if (DEBUG_MU) 6475 Slog.v(TAG_MU, "getIntentSenderLocked(): uid=" + callingUid); 6476 ActivityRecord activity = null; 6477 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 6478 activity = ActivityRecord.isInStackLocked(token); 6479 if (activity == null) { 6480 return null; 6481 } 6482 if (activity.finishing) { 6483 return null; 6484 } 6485 } 6486 6487 final boolean noCreate = (flags&PendingIntent.FLAG_NO_CREATE) != 0; 6488 final boolean cancelCurrent = (flags&PendingIntent.FLAG_CANCEL_CURRENT) != 0; 6489 final boolean updateCurrent = (flags&PendingIntent.FLAG_UPDATE_CURRENT) != 0; 6490 flags &= ~(PendingIntent.FLAG_NO_CREATE|PendingIntent.FLAG_CANCEL_CURRENT 6491 |PendingIntent.FLAG_UPDATE_CURRENT); 6492 6493 PendingIntentRecord.Key key = new PendingIntentRecord.Key( 6494 type, packageName, activity, resultWho, 6495 requestCode, intents, resolvedTypes, flags, options, userId); 6496 WeakReference<PendingIntentRecord> ref; 6497 ref = mIntentSenderRecords.get(key); 6498 PendingIntentRecord rec = ref != null ? ref.get() : null; 6499 if (rec != null) { 6500 if (!cancelCurrent) { 6501 if (updateCurrent) { 6502 if (rec.key.requestIntent != null) { 6503 rec.key.requestIntent.replaceExtras(intents != null ? 6504 intents[intents.length - 1] : null); 6505 } 6506 if (intents != null) { 6507 intents[intents.length-1] = rec.key.requestIntent; 6508 rec.key.allIntents = intents; 6509 rec.key.allResolvedTypes = resolvedTypes; 6510 } else { 6511 rec.key.allIntents = null; 6512 rec.key.allResolvedTypes = null; 6513 } 6514 } 6515 return rec; 6516 } 6517 rec.canceled = true; 6518 mIntentSenderRecords.remove(key); 6519 } 6520 if (noCreate) { 6521 return rec; 6522 } 6523 rec = new PendingIntentRecord(this, key, callingUid); 6524 mIntentSenderRecords.put(key, rec.ref); 6525 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 6526 if (activity.pendingResults == null) { 6527 activity.pendingResults 6528 = new HashSet<WeakReference<PendingIntentRecord>>(); 6529 } 6530 activity.pendingResults.add(rec.ref); 6531 } 6532 return rec; 6533 } 6534 6535 @Override 6536 public void cancelIntentSender(IIntentSender sender) { 6537 if (!(sender instanceof PendingIntentRecord)) { 6538 return; 6539 } 6540 synchronized(this) { 6541 PendingIntentRecord rec = (PendingIntentRecord)sender; 6542 try { 6543 int uid = AppGlobals.getPackageManager() 6544 .getPackageUid(rec.key.packageName, UserHandle.getCallingUserId()); 6545 if (!UserHandle.isSameApp(uid, Binder.getCallingUid())) { 6546 String msg = "Permission Denial: cancelIntentSender() from pid=" 6547 + Binder.getCallingPid() 6548 + ", uid=" + Binder.getCallingUid() 6549 + " is not allowed to cancel packges " 6550 + rec.key.packageName; 6551 Slog.w(TAG, msg); 6552 throw new SecurityException(msg); 6553 } 6554 } catch (RemoteException e) { 6555 throw new SecurityException(e); 6556 } 6557 cancelIntentSenderLocked(rec, true); 6558 } 6559 } 6560 6561 void cancelIntentSenderLocked(PendingIntentRecord rec, boolean cleanActivity) { 6562 rec.canceled = true; 6563 mIntentSenderRecords.remove(rec.key); 6564 if (cleanActivity && rec.key.activity != null) { 6565 rec.key.activity.pendingResults.remove(rec.ref); 6566 } 6567 } 6568 6569 @Override 6570 public String getPackageForIntentSender(IIntentSender pendingResult) { 6571 if (!(pendingResult instanceof PendingIntentRecord)) { 6572 return null; 6573 } 6574 try { 6575 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6576 return res.key.packageName; 6577 } catch (ClassCastException e) { 6578 } 6579 return null; 6580 } 6581 6582 @Override 6583 public int getUidForIntentSender(IIntentSender sender) { 6584 if (sender instanceof PendingIntentRecord) { 6585 try { 6586 PendingIntentRecord res = (PendingIntentRecord)sender; 6587 return res.uid; 6588 } catch (ClassCastException e) { 6589 } 6590 } 6591 return -1; 6592 } 6593 6594 @Override 6595 public boolean isIntentSenderTargetedToPackage(IIntentSender pendingResult) { 6596 if (!(pendingResult instanceof PendingIntentRecord)) { 6597 return false; 6598 } 6599 try { 6600 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6601 if (res.key.allIntents == null) { 6602 return false; 6603 } 6604 for (int i=0; i<res.key.allIntents.length; i++) { 6605 Intent intent = res.key.allIntents[i]; 6606 if (intent.getPackage() != null && intent.getComponent() != null) { 6607 return false; 6608 } 6609 } 6610 return true; 6611 } catch (ClassCastException e) { 6612 } 6613 return false; 6614 } 6615 6616 @Override 6617 public boolean isIntentSenderAnActivity(IIntentSender pendingResult) { 6618 if (!(pendingResult instanceof PendingIntentRecord)) { 6619 return false; 6620 } 6621 try { 6622 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6623 if (res.key.type == ActivityManager.INTENT_SENDER_ACTIVITY) { 6624 return true; 6625 } 6626 return false; 6627 } catch (ClassCastException e) { 6628 } 6629 return false; 6630 } 6631 6632 @Override 6633 public Intent getIntentForIntentSender(IIntentSender pendingResult) { 6634 if (!(pendingResult instanceof PendingIntentRecord)) { 6635 return null; 6636 } 6637 try { 6638 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6639 return res.key.requestIntent != null ? new Intent(res.key.requestIntent) : null; 6640 } catch (ClassCastException e) { 6641 } 6642 return null; 6643 } 6644 6645 @Override 6646 public String getTagForIntentSender(IIntentSender pendingResult, String prefix) { 6647 if (!(pendingResult instanceof PendingIntentRecord)) { 6648 return null; 6649 } 6650 try { 6651 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6652 Intent intent = res.key.requestIntent; 6653 if (intent != null) { 6654 if (res.lastTag != null && res.lastTagPrefix == prefix && (res.lastTagPrefix == null 6655 || res.lastTagPrefix.equals(prefix))) { 6656 return res.lastTag; 6657 } 6658 res.lastTagPrefix = prefix; 6659 StringBuilder sb = new StringBuilder(128); 6660 if (prefix != null) { 6661 sb.append(prefix); 6662 } 6663 if (intent.getAction() != null) { 6664 sb.append(intent.getAction()); 6665 } else if (intent.getComponent() != null) { 6666 intent.getComponent().appendShortString(sb); 6667 } else { 6668 sb.append("?"); 6669 } 6670 return res.lastTag = sb.toString(); 6671 } 6672 } catch (ClassCastException e) { 6673 } 6674 return null; 6675 } 6676 6677 @Override 6678 public void setProcessLimit(int max) { 6679 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 6680 "setProcessLimit()"); 6681 synchronized (this) { 6682 mProcessLimit = max < 0 ? ProcessList.MAX_CACHED_APPS : max; 6683 mProcessLimitOverride = max; 6684 } 6685 trimApplications(); 6686 } 6687 6688 @Override 6689 public int getProcessLimit() { 6690 synchronized (this) { 6691 return mProcessLimitOverride; 6692 } 6693 } 6694 6695 void foregroundTokenDied(ForegroundToken token) { 6696 synchronized (ActivityManagerService.this) { 6697 synchronized (mPidsSelfLocked) { 6698 ForegroundToken cur 6699 = mForegroundProcesses.get(token.pid); 6700 if (cur != token) { 6701 return; 6702 } 6703 mForegroundProcesses.remove(token.pid); 6704 ProcessRecord pr = mPidsSelfLocked.get(token.pid); 6705 if (pr == null) { 6706 return; 6707 } 6708 pr.forcingToForeground = null; 6709 updateProcessForegroundLocked(pr, false, false); 6710 } 6711 updateOomAdjLocked(); 6712 } 6713 } 6714 6715 @Override 6716 public void setProcessForeground(IBinder token, int pid, boolean isForeground) { 6717 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 6718 "setProcessForeground()"); 6719 synchronized(this) { 6720 boolean changed = false; 6721 6722 synchronized (mPidsSelfLocked) { 6723 ProcessRecord pr = mPidsSelfLocked.get(pid); 6724 if (pr == null && isForeground) { 6725 Slog.w(TAG, "setProcessForeground called on unknown pid: " + pid); 6726 return; 6727 } 6728 ForegroundToken oldToken = mForegroundProcesses.get(pid); 6729 if (oldToken != null) { 6730 oldToken.token.unlinkToDeath(oldToken, 0); 6731 mForegroundProcesses.remove(pid); 6732 if (pr != null) { 6733 pr.forcingToForeground = null; 6734 } 6735 changed = true; 6736 } 6737 if (isForeground && token != null) { 6738 ForegroundToken newToken = new ForegroundToken() { 6739 @Override 6740 public void binderDied() { 6741 foregroundTokenDied(this); 6742 } 6743 }; 6744 newToken.pid = pid; 6745 newToken.token = token; 6746 try { 6747 token.linkToDeath(newToken, 0); 6748 mForegroundProcesses.put(pid, newToken); 6749 pr.forcingToForeground = token; 6750 changed = true; 6751 } catch (RemoteException e) { 6752 // If the process died while doing this, we will later 6753 // do the cleanup with the process death link. 6754 } 6755 } 6756 } 6757 6758 if (changed) { 6759 updateOomAdjLocked(); 6760 } 6761 } 6762 } 6763 6764 // ========================================================= 6765 // PERMISSIONS 6766 // ========================================================= 6767 6768 static class PermissionController extends IPermissionController.Stub { 6769 ActivityManagerService mActivityManagerService; 6770 PermissionController(ActivityManagerService activityManagerService) { 6771 mActivityManagerService = activityManagerService; 6772 } 6773 6774 @Override 6775 public boolean checkPermission(String permission, int pid, int uid) { 6776 return mActivityManagerService.checkPermission(permission, pid, 6777 uid) == PackageManager.PERMISSION_GRANTED; 6778 } 6779 } 6780 6781 class IntentFirewallInterface implements IntentFirewall.AMSInterface { 6782 @Override 6783 public int checkComponentPermission(String permission, int pid, int uid, 6784 int owningUid, boolean exported) { 6785 return ActivityManagerService.this.checkComponentPermission(permission, pid, uid, 6786 owningUid, exported); 6787 } 6788 6789 @Override 6790 public Object getAMSLock() { 6791 return ActivityManagerService.this; 6792 } 6793 } 6794 6795 /** 6796 * This can be called with or without the global lock held. 6797 */ 6798 int checkComponentPermission(String permission, int pid, int uid, 6799 int owningUid, boolean exported) { 6800 // We might be performing an operation on behalf of an indirect binder 6801 // invocation, e.g. via {@link #openContentUri}. Check and adjust the 6802 // client identity accordingly before proceeding. 6803 Identity tlsIdentity = sCallerIdentity.get(); 6804 if (tlsIdentity != null) { 6805 Slog.d(TAG, "checkComponentPermission() adjusting {pid,uid} to {" 6806 + tlsIdentity.pid + "," + tlsIdentity.uid + "}"); 6807 uid = tlsIdentity.uid; 6808 pid = tlsIdentity.pid; 6809 } 6810 6811 if (pid == MY_PID) { 6812 return PackageManager.PERMISSION_GRANTED; 6813 } 6814 6815 return ActivityManager.checkComponentPermission(permission, uid, 6816 owningUid, exported); 6817 } 6818 6819 /** 6820 * As the only public entry point for permissions checking, this method 6821 * can enforce the semantic that requesting a check on a null global 6822 * permission is automatically denied. (Internally a null permission 6823 * string is used when calling {@link #checkComponentPermission} in cases 6824 * when only uid-based security is needed.) 6825 * 6826 * This can be called with or without the global lock held. 6827 */ 6828 @Override 6829 public int checkPermission(String permission, int pid, int uid) { 6830 if (permission == null) { 6831 return PackageManager.PERMISSION_DENIED; 6832 } 6833 return checkComponentPermission(permission, pid, UserHandle.getAppId(uid), -1, true); 6834 } 6835 6836 /** 6837 * Binder IPC calls go through the public entry point. 6838 * This can be called with or without the global lock held. 6839 */ 6840 int checkCallingPermission(String permission) { 6841 return checkPermission(permission, 6842 Binder.getCallingPid(), 6843 UserHandle.getAppId(Binder.getCallingUid())); 6844 } 6845 6846 /** 6847 * This can be called with or without the global lock held. 6848 */ 6849 void enforceCallingPermission(String permission, String func) { 6850 if (checkCallingPermission(permission) 6851 == PackageManager.PERMISSION_GRANTED) { 6852 return; 6853 } 6854 6855 String msg = "Permission Denial: " + func + " from pid=" 6856 + Binder.getCallingPid() 6857 + ", uid=" + Binder.getCallingUid() 6858 + " requires " + permission; 6859 Slog.w(TAG, msg); 6860 throw new SecurityException(msg); 6861 } 6862 6863 /** 6864 * Determine if UID is holding permissions required to access {@link Uri} in 6865 * the given {@link ProviderInfo}. Final permission checking is always done 6866 * in {@link ContentProvider}. 6867 */ 6868 private final boolean checkHoldingPermissionsLocked( 6869 IPackageManager pm, ProviderInfo pi, GrantUri grantUri, int uid, final int modeFlags) { 6870 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6871 "checkHoldingPermissionsLocked: uri=" + grantUri + " uid=" + uid); 6872 if (UserHandle.getUserId(uid) != grantUri.sourceUserId) { 6873 if (ActivityManager.checkComponentPermission(INTERACT_ACROSS_USERS, uid, -1, true) 6874 != PERMISSION_GRANTED) { 6875 return false; 6876 } 6877 } 6878 return checkHoldingPermissionsInternalLocked(pm, pi, grantUri, uid, modeFlags, true); 6879 } 6880 6881 private final boolean checkHoldingPermissionsInternalLocked(IPackageManager pm, ProviderInfo pi, 6882 GrantUri grantUri, int uid, final int modeFlags, boolean considerUidPermissions) { 6883 if (pi.applicationInfo.uid == uid) { 6884 return true; 6885 } else if (!pi.exported) { 6886 return false; 6887 } 6888 6889 boolean readMet = (modeFlags & Intent.FLAG_GRANT_READ_URI_PERMISSION) == 0; 6890 boolean writeMet = (modeFlags & Intent.FLAG_GRANT_WRITE_URI_PERMISSION) == 0; 6891 try { 6892 // check if target holds top-level <provider> permissions 6893 if (!readMet && pi.readPermission != null && considerUidPermissions 6894 && (pm.checkUidPermission(pi.readPermission, uid) == PERMISSION_GRANTED)) { 6895 readMet = true; 6896 } 6897 if (!writeMet && pi.writePermission != null && considerUidPermissions 6898 && (pm.checkUidPermission(pi.writePermission, uid) == PERMISSION_GRANTED)) { 6899 writeMet = true; 6900 } 6901 6902 // track if unprotected read/write is allowed; any denied 6903 // <path-permission> below removes this ability 6904 boolean allowDefaultRead = pi.readPermission == null; 6905 boolean allowDefaultWrite = pi.writePermission == null; 6906 6907 // check if target holds any <path-permission> that match uri 6908 final PathPermission[] pps = pi.pathPermissions; 6909 if (pps != null) { 6910 final String path = grantUri.uri.getPath(); 6911 int i = pps.length; 6912 while (i > 0 && (!readMet || !writeMet)) { 6913 i--; 6914 PathPermission pp = pps[i]; 6915 if (pp.match(path)) { 6916 if (!readMet) { 6917 final String pprperm = pp.getReadPermission(); 6918 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking read perm for " 6919 + pprperm + " for " + pp.getPath() 6920 + ": match=" + pp.match(path) 6921 + " check=" + pm.checkUidPermission(pprperm, uid)); 6922 if (pprperm != null) { 6923 if (considerUidPermissions && pm.checkUidPermission(pprperm, uid) 6924 == PERMISSION_GRANTED) { 6925 readMet = true; 6926 } else { 6927 allowDefaultRead = false; 6928 } 6929 } 6930 } 6931 if (!writeMet) { 6932 final String ppwperm = pp.getWritePermission(); 6933 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking write perm " 6934 + ppwperm + " for " + pp.getPath() 6935 + ": match=" + pp.match(path) 6936 + " check=" + pm.checkUidPermission(ppwperm, uid)); 6937 if (ppwperm != null) { 6938 if (considerUidPermissions && pm.checkUidPermission(ppwperm, uid) 6939 == PERMISSION_GRANTED) { 6940 writeMet = true; 6941 } else { 6942 allowDefaultWrite = false; 6943 } 6944 } 6945 } 6946 } 6947 } 6948 } 6949 6950 // grant unprotected <provider> read/write, if not blocked by 6951 // <path-permission> above 6952 if (allowDefaultRead) readMet = true; 6953 if (allowDefaultWrite) writeMet = true; 6954 6955 } catch (RemoteException e) { 6956 return false; 6957 } 6958 6959 return readMet && writeMet; 6960 } 6961 6962 private ProviderInfo getProviderInfoLocked(String authority, int userHandle) { 6963 ProviderInfo pi = null; 6964 ContentProviderRecord cpr = mProviderMap.getProviderByName(authority, userHandle); 6965 if (cpr != null) { 6966 pi = cpr.info; 6967 } else { 6968 try { 6969 pi = AppGlobals.getPackageManager().resolveContentProvider( 6970 authority, PackageManager.GET_URI_PERMISSION_PATTERNS, userHandle); 6971 } catch (RemoteException ex) { 6972 } 6973 } 6974 return pi; 6975 } 6976 6977 private UriPermission findUriPermissionLocked(int targetUid, GrantUri grantUri) { 6978 final ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6979 if (targetUris != null) { 6980 return targetUris.get(grantUri); 6981 } 6982 return null; 6983 } 6984 6985 private UriPermission findOrCreateUriPermissionLocked(String sourcePkg, 6986 String targetPkg, int targetUid, GrantUri grantUri) { 6987 ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6988 if (targetUris == null) { 6989 targetUris = Maps.newArrayMap(); 6990 mGrantedUriPermissions.put(targetUid, targetUris); 6991 } 6992 6993 UriPermission perm = targetUris.get(grantUri); 6994 if (perm == null) { 6995 perm = new UriPermission(sourcePkg, targetPkg, targetUid, grantUri); 6996 targetUris.put(grantUri, perm); 6997 } 6998 6999 return perm; 7000 } 7001 7002 private final boolean checkUriPermissionLocked(GrantUri grantUri, int uid, 7003 final int modeFlags) { 7004 final boolean persistable = (modeFlags & Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION) != 0; 7005 final int minStrength = persistable ? UriPermission.STRENGTH_PERSISTABLE 7006 : UriPermission.STRENGTH_OWNED; 7007 7008 // Root gets to do everything. 7009 if (uid == 0) { 7010 return true; 7011 } 7012 7013 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 7014 if (perms == null) return false; 7015 7016 // First look for exact match 7017 final UriPermission exactPerm = perms.get(grantUri); 7018 if (exactPerm != null && exactPerm.getStrength(modeFlags) >= minStrength) { 7019 return true; 7020 } 7021 7022 // No exact match, look for prefixes 7023 final int N = perms.size(); 7024 for (int i = 0; i < N; i++) { 7025 final UriPermission perm = perms.valueAt(i); 7026 if (perm.uri.prefix && grantUri.uri.isPathPrefixMatch(perm.uri.uri) 7027 && perm.getStrength(modeFlags) >= minStrength) { 7028 return true; 7029 } 7030 } 7031 7032 return false; 7033 } 7034 7035 /** 7036 * @param uri This uri must NOT contain an embedded userId. 7037 * @param userId The userId in which the uri is to be resolved. 7038 */ 7039 @Override 7040 public int checkUriPermission(Uri uri, int pid, int uid, 7041 final int modeFlags, int userId) { 7042 enforceNotIsolatedCaller("checkUriPermission"); 7043 7044 // Another redirected-binder-call permissions check as in 7045 // {@link checkComponentPermission}. 7046 Identity tlsIdentity = sCallerIdentity.get(); 7047 if (tlsIdentity != null) { 7048 uid = tlsIdentity.uid; 7049 pid = tlsIdentity.pid; 7050 } 7051 7052 // Our own process gets to do everything. 7053 if (pid == MY_PID) { 7054 return PackageManager.PERMISSION_GRANTED; 7055 } 7056 synchronized (this) { 7057 return checkUriPermissionLocked(new GrantUri(userId, uri, false), uid, modeFlags) 7058 ? PackageManager.PERMISSION_GRANTED 7059 : PackageManager.PERMISSION_DENIED; 7060 } 7061 } 7062 7063 /** 7064 * Check if the targetPkg can be granted permission to access uri by 7065 * the callingUid using the given modeFlags. Throws a security exception 7066 * if callingUid is not allowed to do this. Returns the uid of the target 7067 * if the URI permission grant should be performed; returns -1 if it is not 7068 * needed (for example targetPkg already has permission to access the URI). 7069 * If you already know the uid of the target, you can supply it in 7070 * lastTargetUid else set that to -1. 7071 */ 7072 int checkGrantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 7073 final int modeFlags, int lastTargetUid) { 7074 if (!Intent.isAccessUriMode(modeFlags)) { 7075 return -1; 7076 } 7077 7078 if (targetPkg != null) { 7079 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7080 "Checking grant " + targetPkg + " permission to " + grantUri); 7081 } 7082 7083 final IPackageManager pm = AppGlobals.getPackageManager(); 7084 7085 // If this is not a content: uri, we can't do anything with it. 7086 if (!ContentResolver.SCHEME_CONTENT.equals(grantUri.uri.getScheme())) { 7087 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7088 "Can't grant URI permission for non-content URI: " + grantUri); 7089 return -1; 7090 } 7091 7092 final String authority = grantUri.uri.getAuthority(); 7093 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 7094 if (pi == null) { 7095 Slog.w(TAG, "No content provider found for permission check: " + 7096 grantUri.uri.toSafeString()); 7097 return -1; 7098 } 7099 7100 int targetUid = lastTargetUid; 7101 if (targetUid < 0 && targetPkg != null) { 7102 try { 7103 targetUid = pm.getPackageUid(targetPkg, UserHandle.getUserId(callingUid)); 7104 if (targetUid < 0) { 7105 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7106 "Can't grant URI permission no uid for: " + targetPkg); 7107 return -1; 7108 } 7109 } catch (RemoteException ex) { 7110 return -1; 7111 } 7112 } 7113 7114 if (targetUid >= 0) { 7115 // First... does the target actually need this permission? 7116 if (checkHoldingPermissionsLocked(pm, pi, grantUri, targetUid, modeFlags)) { 7117 // No need to grant the target this permission. 7118 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7119 "Target " + targetPkg + " already has full permission to " + grantUri); 7120 return -1; 7121 } 7122 } else { 7123 // First... there is no target package, so can anyone access it? 7124 boolean allowed = pi.exported; 7125 if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) { 7126 if (pi.readPermission != null) { 7127 allowed = false; 7128 } 7129 } 7130 if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) { 7131 if (pi.writePermission != null) { 7132 allowed = false; 7133 } 7134 } 7135 if (allowed) { 7136 return -1; 7137 } 7138 } 7139 7140 /* There is a special cross user grant if: 7141 * - The target is on another user. 7142 * - Apps on the current user can access the uri without any uid permissions. 7143 * In this case, we grant a uri permission, even if the ContentProvider does not normally 7144 * grant uri permissions. 7145 */ 7146 boolean specialCrossUserGrant = UserHandle.getUserId(targetUid) != grantUri.sourceUserId 7147 && checkHoldingPermissionsInternalLocked(pm, pi, grantUri, callingUid, 7148 modeFlags, false /*without considering the uid permissions*/); 7149 7150 // Second... is the provider allowing granting of URI permissions? 7151 if (!specialCrossUserGrant) { 7152 if (!pi.grantUriPermissions) { 7153 throw new SecurityException("Provider " + pi.packageName 7154 + "/" + pi.name 7155 + " does not allow granting of Uri permissions (uri " 7156 + grantUri + ")"); 7157 } 7158 if (pi.uriPermissionPatterns != null) { 7159 final int N = pi.uriPermissionPatterns.length; 7160 boolean allowed = false; 7161 for (int i=0; i<N; i++) { 7162 if (pi.uriPermissionPatterns[i] != null 7163 && pi.uriPermissionPatterns[i].match(grantUri.uri.getPath())) { 7164 allowed = true; 7165 break; 7166 } 7167 } 7168 if (!allowed) { 7169 throw new SecurityException("Provider " + pi.packageName 7170 + "/" + pi.name 7171 + " does not allow granting of permission to path of Uri " 7172 + grantUri); 7173 } 7174 } 7175 } 7176 7177 // Third... does the caller itself have permission to access 7178 // this uri? 7179 if (UserHandle.getAppId(callingUid) != Process.SYSTEM_UID) { 7180 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 7181 // Require they hold a strong enough Uri permission 7182 if (!checkUriPermissionLocked(grantUri, callingUid, modeFlags)) { 7183 throw new SecurityException("Uid " + callingUid 7184 + " does not have permission to uri " + grantUri); 7185 } 7186 } 7187 } 7188 return targetUid; 7189 } 7190 7191 /** 7192 * @param uri This uri must NOT contain an embedded userId. 7193 * @param userId The userId in which the uri is to be resolved. 7194 */ 7195 @Override 7196 public int checkGrantUriPermission(int callingUid, String targetPkg, Uri uri, 7197 final int modeFlags, int userId) { 7198 enforceNotIsolatedCaller("checkGrantUriPermission"); 7199 synchronized(this) { 7200 return checkGrantUriPermissionLocked(callingUid, targetPkg, 7201 new GrantUri(userId, uri, false), modeFlags, -1); 7202 } 7203 } 7204 7205 void grantUriPermissionUncheckedLocked(int targetUid, String targetPkg, GrantUri grantUri, 7206 final int modeFlags, UriPermissionOwner owner) { 7207 if (!Intent.isAccessUriMode(modeFlags)) { 7208 return; 7209 } 7210 7211 // So here we are: the caller has the assumed permission 7212 // to the uri, and the target doesn't. Let's now give this to 7213 // the target. 7214 7215 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7216 "Granting " + targetPkg + "/" + targetUid + " permission to " + grantUri); 7217 7218 final String authority = grantUri.uri.getAuthority(); 7219 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 7220 if (pi == null) { 7221 Slog.w(TAG, "No content provider found for grant: " + grantUri.toSafeString()); 7222 return; 7223 } 7224 7225 if ((modeFlags & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0) { 7226 grantUri.prefix = true; 7227 } 7228 final UriPermission perm = findOrCreateUriPermissionLocked( 7229 pi.packageName, targetPkg, targetUid, grantUri); 7230 perm.grantModes(modeFlags, owner); 7231 } 7232 7233 void grantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 7234 final int modeFlags, UriPermissionOwner owner, int targetUserId) { 7235 if (targetPkg == null) { 7236 throw new NullPointerException("targetPkg"); 7237 } 7238 int targetUid; 7239 final IPackageManager pm = AppGlobals.getPackageManager(); 7240 try { 7241 targetUid = pm.getPackageUid(targetPkg, targetUserId); 7242 } catch (RemoteException ex) { 7243 return; 7244 } 7245 7246 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, modeFlags, 7247 targetUid); 7248 if (targetUid < 0) { 7249 return; 7250 } 7251 7252 grantUriPermissionUncheckedLocked(targetUid, targetPkg, grantUri, modeFlags, 7253 owner); 7254 } 7255 7256 static class NeededUriGrants extends ArrayList<GrantUri> { 7257 final String targetPkg; 7258 final int targetUid; 7259 final int flags; 7260 7261 NeededUriGrants(String targetPkg, int targetUid, int flags) { 7262 this.targetPkg = targetPkg; 7263 this.targetUid = targetUid; 7264 this.flags = flags; 7265 } 7266 } 7267 7268 /** 7269 * Like checkGrantUriPermissionLocked, but takes an Intent. 7270 */ 7271 NeededUriGrants checkGrantUriPermissionFromIntentLocked(int callingUid, 7272 String targetPkg, Intent intent, int mode, NeededUriGrants needed, int targetUserId) { 7273 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7274 "Checking URI perm to data=" + (intent != null ? intent.getData() : null) 7275 + " clip=" + (intent != null ? intent.getClipData() : null) 7276 + " from " + intent + "; flags=0x" 7277 + Integer.toHexString(intent != null ? intent.getFlags() : 0)); 7278 7279 if (targetPkg == null) { 7280 throw new NullPointerException("targetPkg"); 7281 } 7282 7283 if (intent == null) { 7284 return null; 7285 } 7286 Uri data = intent.getData(); 7287 ClipData clip = intent.getClipData(); 7288 if (data == null && clip == null) { 7289 return null; 7290 } 7291 // Default userId for uris in the intent (if they don't specify it themselves) 7292 int contentUserHint = intent.getContentUserHint(); 7293 if (contentUserHint == UserHandle.USER_CURRENT) { 7294 contentUserHint = UserHandle.getUserId(callingUid); 7295 } 7296 final IPackageManager pm = AppGlobals.getPackageManager(); 7297 int targetUid; 7298 if (needed != null) { 7299 targetUid = needed.targetUid; 7300 } else { 7301 try { 7302 targetUid = pm.getPackageUid(targetPkg, targetUserId); 7303 } catch (RemoteException ex) { 7304 return null; 7305 } 7306 if (targetUid < 0) { 7307 if (DEBUG_URI_PERMISSION) { 7308 Slog.v(TAG, "Can't grant URI permission no uid for: " + targetPkg 7309 + " on user " + targetUserId); 7310 } 7311 return null; 7312 } 7313 } 7314 if (data != null) { 7315 GrantUri grantUri = GrantUri.resolve(contentUserHint, data); 7316 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 7317 targetUid); 7318 if (targetUid > 0) { 7319 if (needed == null) { 7320 needed = new NeededUriGrants(targetPkg, targetUid, mode); 7321 } 7322 needed.add(grantUri); 7323 } 7324 } 7325 if (clip != null) { 7326 for (int i=0; i<clip.getItemCount(); i++) { 7327 Uri uri = clip.getItemAt(i).getUri(); 7328 if (uri != null) { 7329 GrantUri grantUri = GrantUri.resolve(contentUserHint, uri); 7330 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 7331 targetUid); 7332 if (targetUid > 0) { 7333 if (needed == null) { 7334 needed = new NeededUriGrants(targetPkg, targetUid, mode); 7335 } 7336 needed.add(grantUri); 7337 } 7338 } else { 7339 Intent clipIntent = clip.getItemAt(i).getIntent(); 7340 if (clipIntent != null) { 7341 NeededUriGrants newNeeded = checkGrantUriPermissionFromIntentLocked( 7342 callingUid, targetPkg, clipIntent, mode, needed, targetUserId); 7343 if (newNeeded != null) { 7344 needed = newNeeded; 7345 } 7346 } 7347 } 7348 } 7349 } 7350 7351 return needed; 7352 } 7353 7354 /** 7355 * Like grantUriPermissionUncheckedLocked, but takes an Intent. 7356 */ 7357 void grantUriPermissionUncheckedFromIntentLocked(NeededUriGrants needed, 7358 UriPermissionOwner owner) { 7359 if (needed != null) { 7360 for (int i=0; i<needed.size(); i++) { 7361 GrantUri grantUri = needed.get(i); 7362 grantUriPermissionUncheckedLocked(needed.targetUid, needed.targetPkg, 7363 grantUri, needed.flags, owner); 7364 } 7365 } 7366 } 7367 7368 void grantUriPermissionFromIntentLocked(int callingUid, 7369 String targetPkg, Intent intent, UriPermissionOwner owner, int targetUserId) { 7370 NeededUriGrants needed = checkGrantUriPermissionFromIntentLocked(callingUid, targetPkg, 7371 intent, intent != null ? intent.getFlags() : 0, null, targetUserId); 7372 if (needed == null) { 7373 return; 7374 } 7375 7376 grantUriPermissionUncheckedFromIntentLocked(needed, owner); 7377 } 7378 7379 /** 7380 * @param uri This uri must NOT contain an embedded userId. 7381 * @param userId The userId in which the uri is to be resolved. 7382 */ 7383 @Override 7384 public void grantUriPermission(IApplicationThread caller, String targetPkg, Uri uri, 7385 final int modeFlags, int userId) { 7386 enforceNotIsolatedCaller("grantUriPermission"); 7387 GrantUri grantUri = new GrantUri(userId, uri, false); 7388 synchronized(this) { 7389 final ProcessRecord r = getRecordForAppLocked(caller); 7390 if (r == null) { 7391 throw new SecurityException("Unable to find app for caller " 7392 + caller 7393 + " when granting permission to uri " + grantUri); 7394 } 7395 if (targetPkg == null) { 7396 throw new IllegalArgumentException("null target"); 7397 } 7398 if (grantUri == null) { 7399 throw new IllegalArgumentException("null uri"); 7400 } 7401 7402 Preconditions.checkFlagsArgument(modeFlags, Intent.FLAG_GRANT_READ_URI_PERMISSION 7403 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION 7404 | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION 7405 | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION); 7406 7407 grantUriPermissionLocked(r.uid, targetPkg, grantUri, modeFlags, null, 7408 UserHandle.getUserId(r.uid)); 7409 } 7410 } 7411 7412 void removeUriPermissionIfNeededLocked(UriPermission perm) { 7413 if (perm.modeFlags == 0) { 7414 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 7415 perm.targetUid); 7416 if (perms != null) { 7417 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 7418 "Removing " + perm.targetUid + " permission to " + perm.uri); 7419 7420 perms.remove(perm.uri); 7421 if (perms.isEmpty()) { 7422 mGrantedUriPermissions.remove(perm.targetUid); 7423 } 7424 } 7425 } 7426 } 7427 7428 private void revokeUriPermissionLocked(int callingUid, GrantUri grantUri, final int modeFlags) { 7429 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Revoking all granted permissions to " + grantUri); 7430 7431 final IPackageManager pm = AppGlobals.getPackageManager(); 7432 final String authority = grantUri.uri.getAuthority(); 7433 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 7434 if (pi == null) { 7435 Slog.w(TAG, "No content provider found for permission revoke: " 7436 + grantUri.toSafeString()); 7437 return; 7438 } 7439 7440 // Does the caller have this permission on the URI? 7441 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 7442 // Right now, if you are not the original owner of the permission, 7443 // you are not allowed to revoke it. 7444 //if (!checkUriPermissionLocked(uri, callingUid, modeFlags)) { 7445 throw new SecurityException("Uid " + callingUid 7446 + " does not have permission to uri " + grantUri); 7447 //} 7448 } 7449 7450 boolean persistChanged = false; 7451 7452 // Go through all of the permissions and remove any that match. 7453 int N = mGrantedUriPermissions.size(); 7454 for (int i = 0; i < N; i++) { 7455 final int targetUid = mGrantedUriPermissions.keyAt(i); 7456 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 7457 7458 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 7459 final UriPermission perm = it.next(); 7460 if (perm.uri.sourceUserId == grantUri.sourceUserId 7461 && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) { 7462 if (DEBUG_URI_PERMISSION) 7463 Slog.v(TAG, 7464 "Revoking " + perm.targetUid + " permission to " + perm.uri); 7465 persistChanged |= perm.revokeModes( 7466 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 7467 if (perm.modeFlags == 0) { 7468 it.remove(); 7469 } 7470 } 7471 } 7472 7473 if (perms.isEmpty()) { 7474 mGrantedUriPermissions.remove(targetUid); 7475 N--; 7476 i--; 7477 } 7478 } 7479 7480 if (persistChanged) { 7481 schedulePersistUriGrants(); 7482 } 7483 } 7484 7485 /** 7486 * @param uri This uri must NOT contain an embedded userId. 7487 * @param userId The userId in which the uri is to be resolved. 7488 */ 7489 @Override 7490 public void revokeUriPermission(IApplicationThread caller, Uri uri, final int modeFlags, 7491 int userId) { 7492 enforceNotIsolatedCaller("revokeUriPermission"); 7493 synchronized(this) { 7494 final ProcessRecord r = getRecordForAppLocked(caller); 7495 if (r == null) { 7496 throw new SecurityException("Unable to find app for caller " 7497 + caller 7498 + " when revoking permission to uri " + uri); 7499 } 7500 if (uri == null) { 7501 Slog.w(TAG, "revokeUriPermission: null uri"); 7502 return; 7503 } 7504 7505 if (!Intent.isAccessUriMode(modeFlags)) { 7506 return; 7507 } 7508 7509 final IPackageManager pm = AppGlobals.getPackageManager(); 7510 final String authority = uri.getAuthority(); 7511 final ProviderInfo pi = getProviderInfoLocked(authority, userId); 7512 if (pi == null) { 7513 Slog.w(TAG, "No content provider found for permission revoke: " 7514 + uri.toSafeString()); 7515 return; 7516 } 7517 7518 revokeUriPermissionLocked(r.uid, new GrantUri(userId, uri, false), modeFlags); 7519 } 7520 } 7521 7522 /** 7523 * Remove any {@link UriPermission} granted <em>from</em> or <em>to</em> the 7524 * given package. 7525 * 7526 * @param packageName Package name to match, or {@code null} to apply to all 7527 * packages. 7528 * @param userHandle User to match, or {@link UserHandle#USER_ALL} to apply 7529 * to all users. 7530 * @param persistable If persistable grants should be removed. 7531 */ 7532 private void removeUriPermissionsForPackageLocked( 7533 String packageName, int userHandle, boolean persistable) { 7534 if (userHandle == UserHandle.USER_ALL && packageName == null) { 7535 throw new IllegalArgumentException("Must narrow by either package or user"); 7536 } 7537 7538 boolean persistChanged = false; 7539 7540 int N = mGrantedUriPermissions.size(); 7541 for (int i = 0; i < N; i++) { 7542 final int targetUid = mGrantedUriPermissions.keyAt(i); 7543 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 7544 7545 // Only inspect grants matching user 7546 if (userHandle == UserHandle.USER_ALL 7547 || userHandle == UserHandle.getUserId(targetUid)) { 7548 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 7549 final UriPermission perm = it.next(); 7550 7551 // Only inspect grants matching package 7552 if (packageName == null || perm.sourcePkg.equals(packageName) 7553 || perm.targetPkg.equals(packageName)) { 7554 persistChanged |= perm.revokeModes( 7555 persistable ? ~0 : ~Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 7556 7557 // Only remove when no modes remain; any persisted grants 7558 // will keep this alive. 7559 if (perm.modeFlags == 0) { 7560 it.remove(); 7561 } 7562 } 7563 } 7564 7565 if (perms.isEmpty()) { 7566 mGrantedUriPermissions.remove(targetUid); 7567 N--; 7568 i--; 7569 } 7570 } 7571 } 7572 7573 if (persistChanged) { 7574 schedulePersistUriGrants(); 7575 } 7576 } 7577 7578 @Override 7579 public IBinder newUriPermissionOwner(String name) { 7580 enforceNotIsolatedCaller("newUriPermissionOwner"); 7581 synchronized(this) { 7582 UriPermissionOwner owner = new UriPermissionOwner(this, name); 7583 return owner.getExternalTokenLocked(); 7584 } 7585 } 7586 7587 /** 7588 * @param uri This uri must NOT contain an embedded userId. 7589 * @param sourceUserId The userId in which the uri is to be resolved. 7590 * @param targetUserId The userId of the app that receives the grant. 7591 */ 7592 @Override 7593 public void grantUriPermissionFromOwner(IBinder token, int fromUid, String targetPkg, Uri uri, 7594 final int modeFlags, int sourceUserId, int targetUserId) { 7595 targetUserId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 7596 targetUserId, false, ALLOW_FULL_ONLY, "grantUriPermissionFromOwner", null); 7597 synchronized(this) { 7598 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 7599 if (owner == null) { 7600 throw new IllegalArgumentException("Unknown owner: " + token); 7601 } 7602 if (fromUid != Binder.getCallingUid()) { 7603 if (Binder.getCallingUid() != Process.myUid()) { 7604 // Only system code can grant URI permissions on behalf 7605 // of other users. 7606 throw new SecurityException("nice try"); 7607 } 7608 } 7609 if (targetPkg == null) { 7610 throw new IllegalArgumentException("null target"); 7611 } 7612 if (uri == null) { 7613 throw new IllegalArgumentException("null uri"); 7614 } 7615 7616 grantUriPermissionLocked(fromUid, targetPkg, new GrantUri(sourceUserId, uri, false), 7617 modeFlags, owner, targetUserId); 7618 } 7619 } 7620 7621 /** 7622 * @param uri This uri must NOT contain an embedded userId. 7623 * @param userId The userId in which the uri is to be resolved. 7624 */ 7625 @Override 7626 public void revokeUriPermissionFromOwner(IBinder token, Uri uri, int mode, int userId) { 7627 synchronized(this) { 7628 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 7629 if (owner == null) { 7630 throw new IllegalArgumentException("Unknown owner: " + token); 7631 } 7632 7633 if (uri == null) { 7634 owner.removeUriPermissionsLocked(mode); 7635 } else { 7636 owner.removeUriPermissionLocked(new GrantUri(userId, uri, false), mode); 7637 } 7638 } 7639 } 7640 7641 private void schedulePersistUriGrants() { 7642 if (!mHandler.hasMessages(PERSIST_URI_GRANTS_MSG)) { 7643 mHandler.sendMessageDelayed(mHandler.obtainMessage(PERSIST_URI_GRANTS_MSG), 7644 10 * DateUtils.SECOND_IN_MILLIS); 7645 } 7646 } 7647 7648 private void writeGrantedUriPermissions() { 7649 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "writeGrantedUriPermissions()"); 7650 7651 // Snapshot permissions so we can persist without lock 7652 ArrayList<UriPermission.Snapshot> persist = Lists.newArrayList(); 7653 synchronized (this) { 7654 final int size = mGrantedUriPermissions.size(); 7655 for (int i = 0; i < size; i++) { 7656 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 7657 for (UriPermission perm : perms.values()) { 7658 if (perm.persistedModeFlags != 0) { 7659 persist.add(perm.snapshot()); 7660 } 7661 } 7662 } 7663 } 7664 7665 FileOutputStream fos = null; 7666 try { 7667 fos = mGrantFile.startWrite(); 7668 7669 XmlSerializer out = new FastXmlSerializer(); 7670 out.setOutput(fos, "utf-8"); 7671 out.startDocument(null, true); 7672 out.startTag(null, TAG_URI_GRANTS); 7673 for (UriPermission.Snapshot perm : persist) { 7674 out.startTag(null, TAG_URI_GRANT); 7675 writeIntAttribute(out, ATTR_SOURCE_USER_ID, perm.uri.sourceUserId); 7676 writeIntAttribute(out, ATTR_TARGET_USER_ID, perm.targetUserId); 7677 out.attribute(null, ATTR_SOURCE_PKG, perm.sourcePkg); 7678 out.attribute(null, ATTR_TARGET_PKG, perm.targetPkg); 7679 out.attribute(null, ATTR_URI, String.valueOf(perm.uri.uri)); 7680 writeBooleanAttribute(out, ATTR_PREFIX, perm.uri.prefix); 7681 writeIntAttribute(out, ATTR_MODE_FLAGS, perm.persistedModeFlags); 7682 writeLongAttribute(out, ATTR_CREATED_TIME, perm.persistedCreateTime); 7683 out.endTag(null, TAG_URI_GRANT); 7684 } 7685 out.endTag(null, TAG_URI_GRANTS); 7686 out.endDocument(); 7687 7688 mGrantFile.finishWrite(fos); 7689 } catch (IOException e) { 7690 if (fos != null) { 7691 mGrantFile.failWrite(fos); 7692 } 7693 } 7694 } 7695 7696 private void readGrantedUriPermissionsLocked() { 7697 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "readGrantedUriPermissions()"); 7698 7699 final long now = System.currentTimeMillis(); 7700 7701 FileInputStream fis = null; 7702 try { 7703 fis = mGrantFile.openRead(); 7704 final XmlPullParser in = Xml.newPullParser(); 7705 in.setInput(fis, null); 7706 7707 int type; 7708 while ((type = in.next()) != END_DOCUMENT) { 7709 final String tag = in.getName(); 7710 if (type == START_TAG) { 7711 if (TAG_URI_GRANT.equals(tag)) { 7712 final int sourceUserId; 7713 final int targetUserId; 7714 final int userHandle = readIntAttribute(in, 7715 ATTR_USER_HANDLE, UserHandle.USER_NULL); 7716 if (userHandle != UserHandle.USER_NULL) { 7717 // For backwards compatibility. 7718 sourceUserId = userHandle; 7719 targetUserId = userHandle; 7720 } else { 7721 sourceUserId = readIntAttribute(in, ATTR_SOURCE_USER_ID); 7722 targetUserId = readIntAttribute(in, ATTR_TARGET_USER_ID); 7723 } 7724 final String sourcePkg = in.getAttributeValue(null, ATTR_SOURCE_PKG); 7725 final String targetPkg = in.getAttributeValue(null, ATTR_TARGET_PKG); 7726 final Uri uri = Uri.parse(in.getAttributeValue(null, ATTR_URI)); 7727 final boolean prefix = readBooleanAttribute(in, ATTR_PREFIX); 7728 final int modeFlags = readIntAttribute(in, ATTR_MODE_FLAGS); 7729 final long createdTime = readLongAttribute(in, ATTR_CREATED_TIME, now); 7730 7731 // Sanity check that provider still belongs to source package 7732 final ProviderInfo pi = getProviderInfoLocked( 7733 uri.getAuthority(), sourceUserId); 7734 if (pi != null && sourcePkg.equals(pi.packageName)) { 7735 int targetUid = -1; 7736 try { 7737 targetUid = AppGlobals.getPackageManager() 7738 .getPackageUid(targetPkg, targetUserId); 7739 } catch (RemoteException e) { 7740 } 7741 if (targetUid != -1) { 7742 final UriPermission perm = findOrCreateUriPermissionLocked( 7743 sourcePkg, targetPkg, targetUid, 7744 new GrantUri(sourceUserId, uri, prefix)); 7745 perm.initPersistedModes(modeFlags, createdTime); 7746 } 7747 } else { 7748 Slog.w(TAG, "Persisted grant for " + uri + " had source " + sourcePkg 7749 + " but instead found " + pi); 7750 } 7751 } 7752 } 7753 } 7754 } catch (FileNotFoundException e) { 7755 // Missing grants is okay 7756 } catch (IOException e) { 7757 Log.wtf(TAG, "Failed reading Uri grants", e); 7758 } catch (XmlPullParserException e) { 7759 Log.wtf(TAG, "Failed reading Uri grants", e); 7760 } finally { 7761 IoUtils.closeQuietly(fis); 7762 } 7763 } 7764 7765 /** 7766 * @param uri This uri must NOT contain an embedded userId. 7767 * @param userId The userId in which the uri is to be resolved. 7768 */ 7769 @Override 7770 public void takePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 7771 enforceNotIsolatedCaller("takePersistableUriPermission"); 7772 7773 Preconditions.checkFlagsArgument(modeFlags, 7774 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 7775 7776 synchronized (this) { 7777 final int callingUid = Binder.getCallingUid(); 7778 boolean persistChanged = false; 7779 GrantUri grantUri = new GrantUri(userId, uri, false); 7780 7781 UriPermission exactPerm = findUriPermissionLocked(callingUid, 7782 new GrantUri(userId, uri, false)); 7783 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 7784 new GrantUri(userId, uri, true)); 7785 7786 final boolean exactValid = (exactPerm != null) 7787 && ((modeFlags & exactPerm.persistableModeFlags) == modeFlags); 7788 final boolean prefixValid = (prefixPerm != null) 7789 && ((modeFlags & prefixPerm.persistableModeFlags) == modeFlags); 7790 7791 if (!(exactValid || prefixValid)) { 7792 throw new SecurityException("No persistable permission grants found for UID " 7793 + callingUid + " and Uri " + grantUri.toSafeString()); 7794 } 7795 7796 if (exactValid) { 7797 persistChanged |= exactPerm.takePersistableModes(modeFlags); 7798 } 7799 if (prefixValid) { 7800 persistChanged |= prefixPerm.takePersistableModes(modeFlags); 7801 } 7802 7803 persistChanged |= maybePrunePersistedUriGrantsLocked(callingUid); 7804 7805 if (persistChanged) { 7806 schedulePersistUriGrants(); 7807 } 7808 } 7809 } 7810 7811 /** 7812 * @param uri This uri must NOT contain an embedded userId. 7813 * @param userId The userId in which the uri is to be resolved. 7814 */ 7815 @Override 7816 public void releasePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 7817 enforceNotIsolatedCaller("releasePersistableUriPermission"); 7818 7819 Preconditions.checkFlagsArgument(modeFlags, 7820 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 7821 7822 synchronized (this) { 7823 final int callingUid = Binder.getCallingUid(); 7824 boolean persistChanged = false; 7825 7826 UriPermission exactPerm = findUriPermissionLocked(callingUid, 7827 new GrantUri(userId, uri, false)); 7828 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 7829 new GrantUri(userId, uri, true)); 7830 if (exactPerm == null && prefixPerm == null) { 7831 throw new SecurityException("No permission grants found for UID " + callingUid 7832 + " and Uri " + uri.toSafeString()); 7833 } 7834 7835 if (exactPerm != null) { 7836 persistChanged |= exactPerm.releasePersistableModes(modeFlags); 7837 removeUriPermissionIfNeededLocked(exactPerm); 7838 } 7839 if (prefixPerm != null) { 7840 persistChanged |= prefixPerm.releasePersistableModes(modeFlags); 7841 removeUriPermissionIfNeededLocked(prefixPerm); 7842 } 7843 7844 if (persistChanged) { 7845 schedulePersistUriGrants(); 7846 } 7847 } 7848 } 7849 7850 /** 7851 * Prune any older {@link UriPermission} for the given UID until outstanding 7852 * persisted grants are below {@link #MAX_PERSISTED_URI_GRANTS}. 7853 * 7854 * @return if any mutations occured that require persisting. 7855 */ 7856 private boolean maybePrunePersistedUriGrantsLocked(int uid) { 7857 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 7858 if (perms == null) return false; 7859 if (perms.size() < MAX_PERSISTED_URI_GRANTS) return false; 7860 7861 final ArrayList<UriPermission> persisted = Lists.newArrayList(); 7862 for (UriPermission perm : perms.values()) { 7863 if (perm.persistedModeFlags != 0) { 7864 persisted.add(perm); 7865 } 7866 } 7867 7868 final int trimCount = persisted.size() - MAX_PERSISTED_URI_GRANTS; 7869 if (trimCount <= 0) return false; 7870 7871 Collections.sort(persisted, new UriPermission.PersistedTimeComparator()); 7872 for (int i = 0; i < trimCount; i++) { 7873 final UriPermission perm = persisted.get(i); 7874 7875 if (DEBUG_URI_PERMISSION) { 7876 Slog.v(TAG, "Trimming grant created at " + perm.persistedCreateTime); 7877 } 7878 7879 perm.releasePersistableModes(~0); 7880 removeUriPermissionIfNeededLocked(perm); 7881 } 7882 7883 return true; 7884 } 7885 7886 @Override 7887 public ParceledListSlice<android.content.UriPermission> getPersistedUriPermissions( 7888 String packageName, boolean incoming) { 7889 enforceNotIsolatedCaller("getPersistedUriPermissions"); 7890 Preconditions.checkNotNull(packageName, "packageName"); 7891 7892 final int callingUid = Binder.getCallingUid(); 7893 final IPackageManager pm = AppGlobals.getPackageManager(); 7894 try { 7895 final int packageUid = pm.getPackageUid(packageName, UserHandle.getUserId(callingUid)); 7896 if (packageUid != callingUid) { 7897 throw new SecurityException( 7898 "Package " + packageName + " does not belong to calling UID " + callingUid); 7899 } 7900 } catch (RemoteException e) { 7901 throw new SecurityException("Failed to verify package name ownership"); 7902 } 7903 7904 final ArrayList<android.content.UriPermission> result = Lists.newArrayList(); 7905 synchronized (this) { 7906 if (incoming) { 7907 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 7908 callingUid); 7909 if (perms == null) { 7910 Slog.w(TAG, "No permission grants found for " + packageName); 7911 } else { 7912 for (UriPermission perm : perms.values()) { 7913 if (packageName.equals(perm.targetPkg) && perm.persistedModeFlags != 0) { 7914 result.add(perm.buildPersistedPublicApiObject()); 7915 } 7916 } 7917 } 7918 } else { 7919 final int size = mGrantedUriPermissions.size(); 7920 for (int i = 0; i < size; i++) { 7921 final ArrayMap<GrantUri, UriPermission> perms = 7922 mGrantedUriPermissions.valueAt(i); 7923 for (UriPermission perm : perms.values()) { 7924 if (packageName.equals(perm.sourcePkg) && perm.persistedModeFlags != 0) { 7925 result.add(perm.buildPersistedPublicApiObject()); 7926 } 7927 } 7928 } 7929 } 7930 } 7931 return new ParceledListSlice<android.content.UriPermission>(result); 7932 } 7933 7934 @Override 7935 public void showWaitingForDebugger(IApplicationThread who, boolean waiting) { 7936 synchronized (this) { 7937 ProcessRecord app = 7938 who != null ? getRecordForAppLocked(who) : null; 7939 if (app == null) return; 7940 7941 Message msg = Message.obtain(); 7942 msg.what = WAIT_FOR_DEBUGGER_MSG; 7943 msg.obj = app; 7944 msg.arg1 = waiting ? 1 : 0; 7945 mHandler.sendMessage(msg); 7946 } 7947 } 7948 7949 @Override 7950 public void getMemoryInfo(ActivityManager.MemoryInfo outInfo) { 7951 final long homeAppMem = mProcessList.getMemLevel(ProcessList.HOME_APP_ADJ); 7952 final long cachedAppMem = mProcessList.getMemLevel(ProcessList.CACHED_APP_MIN_ADJ); 7953 outInfo.availMem = Process.getFreeMemory(); 7954 outInfo.totalMem = Process.getTotalMemory(); 7955 outInfo.threshold = homeAppMem; 7956 outInfo.lowMemory = outInfo.availMem < (homeAppMem + ((cachedAppMem-homeAppMem)/2)); 7957 outInfo.hiddenAppThreshold = cachedAppMem; 7958 outInfo.secondaryServerThreshold = mProcessList.getMemLevel( 7959 ProcessList.SERVICE_ADJ); 7960 outInfo.visibleAppThreshold = mProcessList.getMemLevel( 7961 ProcessList.VISIBLE_APP_ADJ); 7962 outInfo.foregroundAppThreshold = mProcessList.getMemLevel( 7963 ProcessList.FOREGROUND_APP_ADJ); 7964 } 7965 7966 // ========================================================= 7967 // TASK MANAGEMENT 7968 // ========================================================= 7969 7970 @Override 7971 public List<IAppTask> getAppTasks(String callingPackage) { 7972 int callingUid = Binder.getCallingUid(); 7973 long ident = Binder.clearCallingIdentity(); 7974 7975 synchronized(this) { 7976 ArrayList<IAppTask> list = new ArrayList<IAppTask>(); 7977 try { 7978 if (localLOGV) Slog.v(TAG, "getAppTasks"); 7979 7980 final int N = mRecentTasks.size(); 7981 for (int i = 0; i < N; i++) { 7982 TaskRecord tr = mRecentTasks.get(i); 7983 // Skip tasks that do not match the caller. We don't need to verify 7984 // callingPackage, because we are also limiting to callingUid and know 7985 // that will limit to the correct security sandbox. 7986 if (tr.effectiveUid != callingUid) { 7987 continue; 7988 } 7989 Intent intent = tr.getBaseIntent(); 7990 if (intent == null || 7991 !callingPackage.equals(intent.getComponent().getPackageName())) { 7992 continue; 7993 } 7994 ActivityManager.RecentTaskInfo taskInfo = 7995 createRecentTaskInfoFromTaskRecord(tr); 7996 AppTaskImpl taskImpl = new AppTaskImpl(taskInfo.persistentId, callingUid); 7997 list.add(taskImpl); 7998 } 7999 } finally { 8000 Binder.restoreCallingIdentity(ident); 8001 } 8002 return list; 8003 } 8004 } 8005 8006 @Override 8007 public List<RunningTaskInfo> getTasks(int maxNum, int flags) { 8008 final int callingUid = Binder.getCallingUid(); 8009 ArrayList<RunningTaskInfo> list = new ArrayList<RunningTaskInfo>(); 8010 8011 synchronized(this) { 8012 if (localLOGV) Slog.v( 8013 TAG, "getTasks: max=" + maxNum + ", flags=" + flags); 8014 8015 final boolean allowed = checkCallingPermission( 8016 android.Manifest.permission.GET_TASKS) 8017 == PackageManager.PERMISSION_GRANTED; 8018 if (!allowed) { 8019 Slog.w(TAG, "getTasks: caller " + callingUid 8020 + " does not hold GET_TASKS; limiting output"); 8021 } 8022 8023 // TODO: Improve with MRU list from all ActivityStacks. 8024 mStackSupervisor.getTasksLocked(maxNum, list, callingUid, allowed); 8025 } 8026 8027 return list; 8028 } 8029 8030 TaskRecord getMostRecentTask() { 8031 return mRecentTasks.get(0); 8032 } 8033 8034 /** 8035 * Creates a new RecentTaskInfo from a TaskRecord. 8036 */ 8037 private ActivityManager.RecentTaskInfo createRecentTaskInfoFromTaskRecord(TaskRecord tr) { 8038 // Update the task description to reflect any changes in the task stack 8039 tr.updateTaskDescription(); 8040 8041 // Compose the recent task info 8042 ActivityManager.RecentTaskInfo rti = new ActivityManager.RecentTaskInfo(); 8043 rti.id = tr.getTopActivity() == null ? -1 : tr.taskId; 8044 rti.persistentId = tr.taskId; 8045 rti.baseIntent = new Intent(tr.getBaseIntent()); 8046 rti.origActivity = tr.origActivity; 8047 rti.description = tr.lastDescription; 8048 rti.stackId = tr.stack != null ? tr.stack.mStackId : -1; 8049 rti.userId = tr.userId; 8050 rti.taskDescription = new ActivityManager.TaskDescription(tr.lastTaskDescription); 8051 rti.firstActiveTime = tr.firstActiveTime; 8052 rti.lastActiveTime = tr.lastActiveTime; 8053 rti.affiliatedTaskId = tr.mAffiliatedTaskId; 8054 rti.affiliatedTaskColor = tr.mAffiliatedTaskColor; 8055 return rti; 8056 } 8057 8058 @Override 8059 public List<ActivityManager.RecentTaskInfo> getRecentTasks(int maxNum, int flags, int userId) { 8060 final int callingUid = Binder.getCallingUid(); 8061 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 8062 false, ALLOW_FULL_ONLY, "getRecentTasks", null); 8063 8064 final boolean includeProfiles = (flags & ActivityManager.RECENT_INCLUDE_PROFILES) != 0; 8065 final boolean withExcluded = (flags&ActivityManager.RECENT_WITH_EXCLUDED) != 0; 8066 synchronized (this) { 8067 final boolean allowed = checkCallingPermission(android.Manifest.permission.GET_TASKS) 8068 == PackageManager.PERMISSION_GRANTED; 8069 if (!allowed) { 8070 Slog.w(TAG, "getRecentTasks: caller " + callingUid 8071 + " does not hold GET_TASKS; limiting output"); 8072 } 8073 final boolean detailed = checkCallingPermission( 8074 android.Manifest.permission.GET_DETAILED_TASKS) 8075 == PackageManager.PERMISSION_GRANTED; 8076 8077 final int N = mRecentTasks.size(); 8078 ArrayList<ActivityManager.RecentTaskInfo> res 8079 = new ArrayList<ActivityManager.RecentTaskInfo>( 8080 maxNum < N ? maxNum : N); 8081 8082 final Set<Integer> includedUsers; 8083 if (includeProfiles) { 8084 includedUsers = getProfileIdsLocked(userId); 8085 } else { 8086 includedUsers = new HashSet<Integer>(); 8087 } 8088 includedUsers.add(Integer.valueOf(userId)); 8089 8090 for (int i=0; i<N && maxNum > 0; i++) { 8091 TaskRecord tr = mRecentTasks.get(i); 8092 // Only add calling user or related users recent tasks 8093 if (!includedUsers.contains(Integer.valueOf(tr.userId))) { 8094 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, not user: " + tr); 8095 continue; 8096 } 8097 8098 // Return the entry if desired by the caller. We always return 8099 // the first entry, because callers always expect this to be the 8100 // foreground app. We may filter others if the caller has 8101 // not supplied RECENT_WITH_EXCLUDED and there is some reason 8102 // we should exclude the entry. 8103 8104 if (i == 0 8105 || withExcluded 8106 || (tr.intent == null) 8107 || ((tr.intent.getFlags() & Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS) 8108 == 0)) { 8109 if (!allowed) { 8110 // If the caller doesn't have the GET_TASKS permission, then only 8111 // allow them to see a small subset of tasks -- their own and home. 8112 if (!tr.isHomeTask() && tr.effectiveUid != callingUid) { 8113 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, not allowed: " + tr); 8114 continue; 8115 } 8116 } 8117 if ((flags & ActivityManager.RECENT_IGNORE_HOME_STACK_TASKS) != 0) { 8118 if (tr.stack != null && tr.stack.isHomeStack()) { 8119 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, home stack task: " + tr); 8120 continue; 8121 } 8122 } 8123 if (tr.autoRemoveRecents && tr.getTopActivity() == null) { 8124 // Don't include auto remove tasks that are finished or finishing. 8125 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, auto-remove without activity: " 8126 + tr); 8127 continue; 8128 } 8129 if ((flags&ActivityManager.RECENT_IGNORE_UNAVAILABLE) != 0 8130 && !tr.isAvailable) { 8131 if (DEBUG_RECENTS) Slog.d(TAG, "Skipping, unavail real act: " + tr); 8132 continue; 8133 } 8134 8135 ActivityManager.RecentTaskInfo rti = createRecentTaskInfoFromTaskRecord(tr); 8136 if (!detailed) { 8137 rti.baseIntent.replaceExtras((Bundle)null); 8138 } 8139 8140 res.add(rti); 8141 maxNum--; 8142 } 8143 } 8144 return res; 8145 } 8146 } 8147 8148 private TaskRecord recentTaskForIdLocked(int id) { 8149 final int N = mRecentTasks.size(); 8150 for (int i=0; i<N; i++) { 8151 TaskRecord tr = mRecentTasks.get(i); 8152 if (tr.taskId == id) { 8153 return tr; 8154 } 8155 } 8156 return null; 8157 } 8158 8159 @Override 8160 public ActivityManager.TaskThumbnail getTaskThumbnail(int id) { 8161 synchronized (this) { 8162 enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER, 8163 "getTaskThumbnail()"); 8164 TaskRecord tr = recentTaskForIdLocked(id); 8165 if (tr != null) { 8166 return tr.getTaskThumbnailLocked(); 8167 } 8168 } 8169 return null; 8170 } 8171 8172 @Override 8173 public int addAppTask(IBinder activityToken, Intent intent, 8174 ActivityManager.TaskDescription description, Bitmap thumbnail) throws RemoteException { 8175 final int callingUid = Binder.getCallingUid(); 8176 final long callingIdent = Binder.clearCallingIdentity(); 8177 8178 try { 8179 synchronized (this) { 8180 ActivityRecord r = ActivityRecord.isInStackLocked(activityToken); 8181 if (r == null) { 8182 throw new IllegalArgumentException("Activity does not exist; token=" 8183 + activityToken); 8184 } 8185 ComponentName comp = intent.getComponent(); 8186 if (comp == null) { 8187 throw new IllegalArgumentException("Intent " + intent 8188 + " must specify explicit component"); 8189 } 8190 if (thumbnail.getWidth() != mThumbnailWidth 8191 || thumbnail.getHeight() != mThumbnailHeight) { 8192 throw new IllegalArgumentException("Bad thumbnail size: got " 8193 + thumbnail.getWidth() + "x" + thumbnail.getHeight() + ", require " 8194 + mThumbnailWidth + "x" + mThumbnailHeight); 8195 } 8196 if (intent.getSelector() != null) { 8197 intent.setSelector(null); 8198 } 8199 if (intent.getSourceBounds() != null) { 8200 intent.setSourceBounds(null); 8201 } 8202 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_DOCUMENT) != 0) { 8203 if ((intent.getFlags()&Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS) == 0) { 8204 // The caller has added this as an auto-remove task... that makes no 8205 // sense, so turn off auto-remove. 8206 intent.addFlags(Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS); 8207 } 8208 } else if ((intent.getFlags()&Intent.FLAG_ACTIVITY_NEW_TASK) != 0) { 8209 // Must be a new task. 8210 intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 8211 } 8212 if (!comp.equals(mLastAddedTaskComponent) || callingUid != mLastAddedTaskUid) { 8213 mLastAddedTaskActivity = null; 8214 } 8215 ActivityInfo ainfo = mLastAddedTaskActivity; 8216 if (ainfo == null) { 8217 ainfo = mLastAddedTaskActivity = AppGlobals.getPackageManager().getActivityInfo( 8218 comp, 0, UserHandle.getUserId(callingUid)); 8219 if (ainfo.applicationInfo.uid != callingUid) { 8220 throw new SecurityException( 8221 "Can't add task for another application: target uid=" 8222 + ainfo.applicationInfo.uid + ", calling uid=" + callingUid); 8223 } 8224 } 8225 8226 TaskRecord task = new TaskRecord(this, mStackSupervisor.getNextTaskId(), ainfo, 8227 intent, description); 8228 8229 int trimIdx = trimRecentsForTask(task, false); 8230 if (trimIdx >= 0) { 8231 // If this would have caused a trim, then we'll abort because that 8232 // means it would be added at the end of the list but then just removed. 8233 return -1; 8234 } 8235 8236 final int N = mRecentTasks.size(); 8237 if (N >= (ActivityManager.getMaxRecentTasksStatic()-1)) { 8238 final TaskRecord tr = mRecentTasks.remove(N - 1); 8239 tr.removedFromRecents(mTaskPersister); 8240 } 8241 8242 task.inRecents = true; 8243 mRecentTasks.add(task); 8244 r.task.stack.addTask(task, false, false); 8245 8246 task.setLastThumbnail(thumbnail); 8247 task.freeLastThumbnail(); 8248 8249 return task.taskId; 8250 } 8251 } finally { 8252 Binder.restoreCallingIdentity(callingIdent); 8253 } 8254 } 8255 8256 @Override 8257 public Point getAppTaskThumbnailSize() { 8258 synchronized (this) { 8259 return new Point(mThumbnailWidth, mThumbnailHeight); 8260 } 8261 } 8262 8263 @Override 8264 public void setTaskDescription(IBinder token, ActivityManager.TaskDescription td) { 8265 synchronized (this) { 8266 ActivityRecord r = ActivityRecord.isInStackLocked(token); 8267 if (r != null) { 8268 r.taskDescription = td; 8269 r.task.updateTaskDescription(); 8270 } 8271 } 8272 } 8273 8274 private void cleanUpRemovedTaskLocked(TaskRecord tr, int flags) { 8275 mRecentTasks.remove(tr); 8276 tr.removedFromRecents(mTaskPersister); 8277 final boolean killProcesses = (flags&ActivityManager.REMOVE_TASK_KILL_PROCESS) != 0; 8278 Intent baseIntent = new Intent( 8279 tr.intent != null ? tr.intent : tr.affinityIntent); 8280 ComponentName component = baseIntent.getComponent(); 8281 if (component == null) { 8282 Slog.w(TAG, "Now component for base intent of task: " + tr); 8283 return; 8284 } 8285 8286 // Find any running services associated with this app. 8287 mServices.cleanUpRemovedTaskLocked(tr, component, baseIntent); 8288 8289 if (killProcesses) { 8290 // Find any running processes associated with this app. 8291 final String pkg = component.getPackageName(); 8292 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 8293 ArrayMap<String, SparseArray<ProcessRecord>> pmap = mProcessNames.getMap(); 8294 for (int i=0; i<pmap.size(); i++) { 8295 SparseArray<ProcessRecord> uids = pmap.valueAt(i); 8296 for (int j=0; j<uids.size(); j++) { 8297 ProcessRecord proc = uids.valueAt(j); 8298 if (proc.userId != tr.userId) { 8299 continue; 8300 } 8301 if (!proc.pkgList.containsKey(pkg)) { 8302 continue; 8303 } 8304 procs.add(proc); 8305 } 8306 } 8307 8308 // Kill the running processes. 8309 for (int i=0; i<procs.size(); i++) { 8310 ProcessRecord pr = procs.get(i); 8311 if (pr == mHomeProcess) { 8312 // Don't kill the home process along with tasks from the same package. 8313 continue; 8314 } 8315 if (pr.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 8316 pr.kill("remove task", true); 8317 } else { 8318 pr.waitingToKill = "remove task"; 8319 } 8320 } 8321 } 8322 } 8323 8324 /** 8325 * Removes the task with the specified task id. 8326 * 8327 * @param taskId Identifier of the task to be removed. 8328 * @param flags Additional operational flags. May be 0 or 8329 * {@link ActivityManager#REMOVE_TASK_KILL_PROCESS}. 8330 * @return Returns true if the given task was found and removed. 8331 */ 8332 private boolean removeTaskByIdLocked(int taskId, int flags) { 8333 TaskRecord tr = recentTaskForIdLocked(taskId); 8334 if (tr != null) { 8335 tr.removeTaskActivitiesLocked(); 8336 cleanUpRemovedTaskLocked(tr, flags); 8337 if (tr.isPersistable) { 8338 notifyTaskPersisterLocked(null, true); 8339 } 8340 return true; 8341 } 8342 return false; 8343 } 8344 8345 @Override 8346 public boolean removeTask(int taskId, int flags) { 8347 synchronized (this) { 8348 enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, 8349 "removeTask()"); 8350 long ident = Binder.clearCallingIdentity(); 8351 try { 8352 return removeTaskByIdLocked(taskId, flags); 8353 } finally { 8354 Binder.restoreCallingIdentity(ident); 8355 } 8356 } 8357 } 8358 8359 /** 8360 * TODO: Add mController hook 8361 */ 8362 @Override 8363 public void moveTaskToFront(int taskId, int flags, Bundle options) { 8364 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 8365 "moveTaskToFront()"); 8366 8367 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToFront: moving taskId=" + taskId); 8368 synchronized(this) { 8369 moveTaskToFrontLocked(taskId, flags, options); 8370 } 8371 } 8372 8373 void moveTaskToFrontLocked(int taskId, int flags, Bundle options) { 8374 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 8375 Binder.getCallingUid(), "Task to front")) { 8376 ActivityOptions.abort(options); 8377 return; 8378 } 8379 final long origId = Binder.clearCallingIdentity(); 8380 try { 8381 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 8382 if (task == null) { 8383 return; 8384 } 8385 if (mStackSupervisor.isLockTaskModeViolation(task)) { 8386 mStackSupervisor.showLockTaskToast(); 8387 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode"); 8388 return; 8389 } 8390 final ActivityRecord prev = mStackSupervisor.topRunningActivityLocked(); 8391 if (prev != null && prev.isRecentsActivity()) { 8392 task.setTaskToReturnTo(ActivityRecord.RECENTS_ACTIVITY_TYPE); 8393 } 8394 mStackSupervisor.findTaskToMoveToFrontLocked(task, flags, options); 8395 } finally { 8396 Binder.restoreCallingIdentity(origId); 8397 } 8398 ActivityOptions.abort(options); 8399 } 8400 8401 @Override 8402 public void moveTaskToBack(int taskId) { 8403 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 8404 "moveTaskToBack()"); 8405 8406 synchronized(this) { 8407 TaskRecord tr = recentTaskForIdLocked(taskId); 8408 if (tr != null) { 8409 if (tr == mStackSupervisor.mLockTaskModeTask) { 8410 mStackSupervisor.showLockTaskToast(); 8411 return; 8412 } 8413 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToBack: moving task=" + tr); 8414 ActivityStack stack = tr.stack; 8415 if (stack.mResumedActivity != null && stack.mResumedActivity.task == tr) { 8416 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 8417 Binder.getCallingUid(), "Task to back")) { 8418 return; 8419 } 8420 } 8421 final long origId = Binder.clearCallingIdentity(); 8422 try { 8423 stack.moveTaskToBackLocked(taskId, null); 8424 } finally { 8425 Binder.restoreCallingIdentity(origId); 8426 } 8427 } 8428 } 8429 } 8430 8431 /** 8432 * Moves an activity, and all of the other activities within the same task, to the bottom 8433 * of the history stack. The activity's order within the task is unchanged. 8434 * 8435 * @param token A reference to the activity we wish to move 8436 * @param nonRoot If false then this only works if the activity is the root 8437 * of a task; if true it will work for any activity in a task. 8438 * @return Returns true if the move completed, false if not. 8439 */ 8440 @Override 8441 public boolean moveActivityTaskToBack(IBinder token, boolean nonRoot) { 8442 enforceNotIsolatedCaller("moveActivityTaskToBack"); 8443 synchronized(this) { 8444 final long origId = Binder.clearCallingIdentity(); 8445 try { 8446 int taskId = ActivityRecord.getTaskForActivityLocked(token, !nonRoot); 8447 if (taskId >= 0) { 8448 if ((mStackSupervisor.mLockTaskModeTask != null) 8449 && (mStackSupervisor.mLockTaskModeTask.taskId == taskId)) { 8450 mStackSupervisor.showLockTaskToast(); 8451 return false; 8452 } 8453 return ActivityRecord.getStackLocked(token).moveTaskToBackLocked(taskId, null); 8454 } 8455 } finally { 8456 Binder.restoreCallingIdentity(origId); 8457 } 8458 } 8459 return false; 8460 } 8461 8462 @Override 8463 public void moveTaskBackwards(int task) { 8464 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 8465 "moveTaskBackwards()"); 8466 8467 synchronized(this) { 8468 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 8469 Binder.getCallingUid(), "Task backwards")) { 8470 return; 8471 } 8472 final long origId = Binder.clearCallingIdentity(); 8473 moveTaskBackwardsLocked(task); 8474 Binder.restoreCallingIdentity(origId); 8475 } 8476 } 8477 8478 private final void moveTaskBackwardsLocked(int task) { 8479 Slog.e(TAG, "moveTaskBackwards not yet implemented!"); 8480 } 8481 8482 @Override 8483 public IBinder getHomeActivityToken() throws RemoteException { 8484 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8485 "getHomeActivityToken()"); 8486 synchronized (this) { 8487 return mStackSupervisor.getHomeActivityToken(); 8488 } 8489 } 8490 8491 @Override 8492 public IActivityContainer createActivityContainer(IBinder parentActivityToken, 8493 IActivityContainerCallback callback) throws RemoteException { 8494 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8495 "createActivityContainer()"); 8496 synchronized (this) { 8497 if (parentActivityToken == null) { 8498 throw new IllegalArgumentException("parent token must not be null"); 8499 } 8500 ActivityRecord r = ActivityRecord.forToken(parentActivityToken); 8501 if (r == null) { 8502 return null; 8503 } 8504 if (callback == null) { 8505 throw new IllegalArgumentException("callback must not be null"); 8506 } 8507 return mStackSupervisor.createActivityContainer(r, callback); 8508 } 8509 } 8510 8511 @Override 8512 public void deleteActivityContainer(IActivityContainer container) throws RemoteException { 8513 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8514 "deleteActivityContainer()"); 8515 synchronized (this) { 8516 mStackSupervisor.deleteActivityContainer(container); 8517 } 8518 } 8519 8520 @Override 8521 public IActivityContainer getEnclosingActivityContainer(IBinder activityToken) 8522 throws RemoteException { 8523 synchronized (this) { 8524 ActivityStack stack = ActivityRecord.getStackLocked(activityToken); 8525 if (stack != null) { 8526 return stack.mActivityContainer; 8527 } 8528 return null; 8529 } 8530 } 8531 8532 @Override 8533 public void moveTaskToStack(int taskId, int stackId, boolean toTop) { 8534 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8535 "moveTaskToStack()"); 8536 if (stackId == HOME_STACK_ID) { 8537 Slog.e(TAG, "moveTaskToStack: Attempt to move task " + taskId + " to home stack", 8538 new RuntimeException("here").fillInStackTrace()); 8539 } 8540 synchronized (this) { 8541 long ident = Binder.clearCallingIdentity(); 8542 try { 8543 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToStack: moving task=" + taskId + " to stackId=" 8544 + stackId + " toTop=" + toTop); 8545 mStackSupervisor.moveTaskToStack(taskId, stackId, toTop); 8546 } finally { 8547 Binder.restoreCallingIdentity(ident); 8548 } 8549 } 8550 } 8551 8552 @Override 8553 public void resizeStack(int stackBoxId, Rect bounds) { 8554 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8555 "resizeStackBox()"); 8556 long ident = Binder.clearCallingIdentity(); 8557 try { 8558 mWindowManager.resizeStack(stackBoxId, bounds); 8559 } finally { 8560 Binder.restoreCallingIdentity(ident); 8561 } 8562 } 8563 8564 @Override 8565 public List<StackInfo> getAllStackInfos() { 8566 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8567 "getAllStackInfos()"); 8568 long ident = Binder.clearCallingIdentity(); 8569 try { 8570 synchronized (this) { 8571 return mStackSupervisor.getAllStackInfosLocked(); 8572 } 8573 } finally { 8574 Binder.restoreCallingIdentity(ident); 8575 } 8576 } 8577 8578 @Override 8579 public StackInfo getStackInfo(int stackId) { 8580 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8581 "getStackInfo()"); 8582 long ident = Binder.clearCallingIdentity(); 8583 try { 8584 synchronized (this) { 8585 return mStackSupervisor.getStackInfoLocked(stackId); 8586 } 8587 } finally { 8588 Binder.restoreCallingIdentity(ident); 8589 } 8590 } 8591 8592 @Override 8593 public boolean isInHomeStack(int taskId) { 8594 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8595 "getStackInfo()"); 8596 long ident = Binder.clearCallingIdentity(); 8597 try { 8598 synchronized (this) { 8599 TaskRecord tr = recentTaskForIdLocked(taskId); 8600 return tr != null && tr.stack != null && tr.stack.isHomeStack(); 8601 } 8602 } finally { 8603 Binder.restoreCallingIdentity(ident); 8604 } 8605 } 8606 8607 @Override 8608 public int getTaskForActivity(IBinder token, boolean onlyRoot) { 8609 synchronized(this) { 8610 return ActivityRecord.getTaskForActivityLocked(token, onlyRoot); 8611 } 8612 } 8613 8614 private boolean isLockTaskAuthorized(String pkg) { 8615 final DevicePolicyManager dpm = (DevicePolicyManager) 8616 mContext.getSystemService(Context.DEVICE_POLICY_SERVICE); 8617 try { 8618 int uid = mContext.getPackageManager().getPackageUid(pkg, 8619 Binder.getCallingUserHandle().getIdentifier()); 8620 return (uid == Binder.getCallingUid()) && dpm != null && dpm.isLockTaskPermitted(pkg); 8621 } catch (NameNotFoundException e) { 8622 return false; 8623 } 8624 } 8625 8626 void startLockTaskMode(TaskRecord task) { 8627 final String pkg; 8628 synchronized (this) { 8629 pkg = task.intent.getComponent().getPackageName(); 8630 } 8631 boolean isSystemInitiated = Binder.getCallingUid() == Process.SYSTEM_UID; 8632 if (!isSystemInitiated && !isLockTaskAuthorized(pkg)) { 8633 final TaskRecord taskRecord = task; 8634 mHandler.post(new Runnable() { 8635 @Override 8636 public void run() { 8637 mLockToAppRequest.showLockTaskPrompt(taskRecord); 8638 } 8639 }); 8640 return; 8641 } 8642 long ident = Binder.clearCallingIdentity(); 8643 try { 8644 synchronized (this) { 8645 // Since we lost lock on task, make sure it is still there. 8646 task = mStackSupervisor.anyTaskForIdLocked(task.taskId); 8647 if (task != null) { 8648 if (!isSystemInitiated 8649 && ((mFocusedActivity == null) || (task != mFocusedActivity.task))) { 8650 throw new IllegalArgumentException("Invalid task, not in foreground"); 8651 } 8652 mStackSupervisor.setLockTaskModeLocked(task, !isSystemInitiated); 8653 } 8654 } 8655 } finally { 8656 Binder.restoreCallingIdentity(ident); 8657 } 8658 } 8659 8660 @Override 8661 public void startLockTaskMode(int taskId) { 8662 final TaskRecord task; 8663 long ident = Binder.clearCallingIdentity(); 8664 try { 8665 synchronized (this) { 8666 task = mStackSupervisor.anyTaskForIdLocked(taskId); 8667 } 8668 } finally { 8669 Binder.restoreCallingIdentity(ident); 8670 } 8671 if (task != null) { 8672 startLockTaskMode(task); 8673 } 8674 } 8675 8676 @Override 8677 public void startLockTaskMode(IBinder token) { 8678 final TaskRecord task; 8679 long ident = Binder.clearCallingIdentity(); 8680 try { 8681 synchronized (this) { 8682 final ActivityRecord r = ActivityRecord.forToken(token); 8683 if (r == null) { 8684 return; 8685 } 8686 task = r.task; 8687 } 8688 } finally { 8689 Binder.restoreCallingIdentity(ident); 8690 } 8691 if (task != null) { 8692 startLockTaskMode(task); 8693 } 8694 } 8695 8696 @Override 8697 public void startLockTaskModeOnCurrent() throws RemoteException { 8698 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8699 "startLockTaskModeOnCurrent"); 8700 ActivityRecord r = null; 8701 synchronized (this) { 8702 r = mStackSupervisor.topRunningActivityLocked(); 8703 } 8704 startLockTaskMode(r.task); 8705 } 8706 8707 @Override 8708 public void stopLockTaskMode() { 8709 // Verify that the user matches the package of the intent for the TaskRecord 8710 // we are locked to or systtem. This will ensure the same caller for startLockTaskMode 8711 // and stopLockTaskMode. 8712 final int callingUid = Binder.getCallingUid(); 8713 if (callingUid != Process.SYSTEM_UID) { 8714 try { 8715 String pkg = 8716 mStackSupervisor.mLockTaskModeTask.intent.getComponent().getPackageName(); 8717 int uid = mContext.getPackageManager().getPackageUid(pkg, 8718 Binder.getCallingUserHandle().getIdentifier()); 8719 if (uid != callingUid) { 8720 throw new SecurityException("Invalid uid, expected " + uid); 8721 } 8722 } catch (NameNotFoundException e) { 8723 Log.d(TAG, "stopLockTaskMode " + e); 8724 return; 8725 } 8726 } 8727 long ident = Binder.clearCallingIdentity(); 8728 try { 8729 Log.d(TAG, "stopLockTaskMode"); 8730 // Stop lock task 8731 synchronized (this) { 8732 mStackSupervisor.setLockTaskModeLocked(null, false); 8733 } 8734 } finally { 8735 Binder.restoreCallingIdentity(ident); 8736 } 8737 } 8738 8739 @Override 8740 public void stopLockTaskModeOnCurrent() throws RemoteException { 8741 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 8742 "stopLockTaskModeOnCurrent"); 8743 long ident = Binder.clearCallingIdentity(); 8744 try { 8745 stopLockTaskMode(); 8746 } finally { 8747 Binder.restoreCallingIdentity(ident); 8748 } 8749 } 8750 8751 @Override 8752 public boolean isInLockTaskMode() { 8753 synchronized (this) { 8754 return mStackSupervisor.isInLockTaskMode(); 8755 } 8756 } 8757 8758 // ========================================================= 8759 // CONTENT PROVIDERS 8760 // ========================================================= 8761 8762 private final List<ProviderInfo> generateApplicationProvidersLocked(ProcessRecord app) { 8763 List<ProviderInfo> providers = null; 8764 try { 8765 providers = AppGlobals.getPackageManager(). 8766 queryContentProviders(app.processName, app.uid, 8767 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS); 8768 } catch (RemoteException ex) { 8769 } 8770 if (DEBUG_MU) 8771 Slog.v(TAG_MU, "generateApplicationProvidersLocked, app.info.uid = " + app.uid); 8772 int userId = app.userId; 8773 if (providers != null) { 8774 int N = providers.size(); 8775 app.pubProviders.ensureCapacity(N + app.pubProviders.size()); 8776 for (int i=0; i<N; i++) { 8777 ProviderInfo cpi = 8778 (ProviderInfo)providers.get(i); 8779 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo, 8780 cpi.name, cpi.flags); 8781 if (singleton && UserHandle.getUserId(app.uid) != 0) { 8782 // This is a singleton provider, but a user besides the 8783 // default user is asking to initialize a process it runs 8784 // in... well, no, it doesn't actually run in this process, 8785 // it runs in the process of the default user. Get rid of it. 8786 providers.remove(i); 8787 N--; 8788 i--; 8789 continue; 8790 } 8791 8792 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 8793 ContentProviderRecord cpr = mProviderMap.getProviderByClass(comp, userId); 8794 if (cpr == null) { 8795 cpr = new ContentProviderRecord(this, cpi, app.info, comp, singleton); 8796 mProviderMap.putProviderByClass(comp, cpr); 8797 } 8798 if (DEBUG_MU) 8799 Slog.v(TAG_MU, "generateApplicationProvidersLocked, cpi.uid = " + cpr.uid); 8800 app.pubProviders.put(cpi.name, cpr); 8801 if (!cpi.multiprocess || !"android".equals(cpi.packageName)) { 8802 // Don't add this if it is a platform component that is marked 8803 // to run in multiple processes, because this is actually 8804 // part of the framework so doesn't make sense to track as a 8805 // separate apk in the process. 8806 app.addPackage(cpi.applicationInfo.packageName, cpi.applicationInfo.versionCode, 8807 mProcessStats); 8808 } 8809 ensurePackageDexOpt(cpi.applicationInfo.packageName); 8810 } 8811 } 8812 return providers; 8813 } 8814 8815 /** 8816 * Check if {@link ProcessRecord} has a possible chance at accessing the 8817 * given {@link ProviderInfo}. Final permission checking is always done 8818 * in {@link ContentProvider}. 8819 */ 8820 private final String checkContentProviderPermissionLocked( 8821 ProviderInfo cpi, ProcessRecord r, int userId, boolean checkUser) { 8822 final int callingPid = (r != null) ? r.pid : Binder.getCallingPid(); 8823 final int callingUid = (r != null) ? r.uid : Binder.getCallingUid(); 8824 boolean checkedGrants = false; 8825 if (checkUser) { 8826 // Looking for cross-user grants before enforcing the typical cross-users permissions 8827 int tmpTargetUserId = unsafeConvertIncomingUser(userId); 8828 if (tmpTargetUserId != UserHandle.getUserId(callingUid)) { 8829 if (checkAuthorityGrants(callingUid, cpi, tmpTargetUserId, checkUser)) { 8830 return null; 8831 } 8832 checkedGrants = true; 8833 } 8834 userId = handleIncomingUser(callingPid, callingUid, userId, 8835 false, ALLOW_NON_FULL, 8836 "checkContentProviderPermissionLocked " + cpi.authority, null); 8837 if (userId != tmpTargetUserId) { 8838 // When we actually went to determine the final targer user ID, this ended 8839 // up different than our initial check for the authority. This is because 8840 // they had asked for USER_CURRENT_OR_SELF and we ended up switching to 8841 // SELF. So we need to re-check the grants again. 8842 checkedGrants = false; 8843 } 8844 } 8845 if (checkComponentPermission(cpi.readPermission, callingPid, callingUid, 8846 cpi.applicationInfo.uid, cpi.exported) 8847 == PackageManager.PERMISSION_GRANTED) { 8848 return null; 8849 } 8850 if (checkComponentPermission(cpi.writePermission, callingPid, callingUid, 8851 cpi.applicationInfo.uid, cpi.exported) 8852 == PackageManager.PERMISSION_GRANTED) { 8853 return null; 8854 } 8855 8856 PathPermission[] pps = cpi.pathPermissions; 8857 if (pps != null) { 8858 int i = pps.length; 8859 while (i > 0) { 8860 i--; 8861 PathPermission pp = pps[i]; 8862 String pprperm = pp.getReadPermission(); 8863 if (pprperm != null && checkComponentPermission(pprperm, callingPid, callingUid, 8864 cpi.applicationInfo.uid, cpi.exported) 8865 == PackageManager.PERMISSION_GRANTED) { 8866 return null; 8867 } 8868 String ppwperm = pp.getWritePermission(); 8869 if (ppwperm != null && checkComponentPermission(ppwperm, callingPid, callingUid, 8870 cpi.applicationInfo.uid, cpi.exported) 8871 == PackageManager.PERMISSION_GRANTED) { 8872 return null; 8873 } 8874 } 8875 } 8876 if (!checkedGrants && checkAuthorityGrants(callingUid, cpi, userId, checkUser)) { 8877 return null; 8878 } 8879 8880 String msg; 8881 if (!cpi.exported) { 8882 msg = "Permission Denial: opening provider " + cpi.name 8883 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 8884 + ", uid=" + callingUid + ") that is not exported from uid " 8885 + cpi.applicationInfo.uid; 8886 } else { 8887 msg = "Permission Denial: opening provider " + cpi.name 8888 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 8889 + ", uid=" + callingUid + ") requires " 8890 + cpi.readPermission + " or " + cpi.writePermission; 8891 } 8892 Slog.w(TAG, msg); 8893 return msg; 8894 } 8895 8896 /** 8897 * Returns if the ContentProvider has granted a uri to callingUid 8898 */ 8899 boolean checkAuthorityGrants(int callingUid, ProviderInfo cpi, int userId, boolean checkUser) { 8900 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 8901 if (perms != null) { 8902 for (int i=perms.size()-1; i>=0; i--) { 8903 GrantUri grantUri = perms.keyAt(i); 8904 if (grantUri.sourceUserId == userId || !checkUser) { 8905 if (matchesProvider(grantUri.uri, cpi)) { 8906 return true; 8907 } 8908 } 8909 } 8910 } 8911 return false; 8912 } 8913 8914 /** 8915 * Returns true if the uri authority is one of the authorities specified in the provider. 8916 */ 8917 boolean matchesProvider(Uri uri, ProviderInfo cpi) { 8918 String uriAuth = uri.getAuthority(); 8919 String cpiAuth = cpi.authority; 8920 if (cpiAuth.indexOf(';') == -1) { 8921 return cpiAuth.equals(uriAuth); 8922 } 8923 String[] cpiAuths = cpiAuth.split(";"); 8924 int length = cpiAuths.length; 8925 for (int i = 0; i < length; i++) { 8926 if (cpiAuths[i].equals(uriAuth)) return true; 8927 } 8928 return false; 8929 } 8930 8931 ContentProviderConnection incProviderCountLocked(ProcessRecord r, 8932 final ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 8933 if (r != null) { 8934 for (int i=0; i<r.conProviders.size(); i++) { 8935 ContentProviderConnection conn = r.conProviders.get(i); 8936 if (conn.provider == cpr) { 8937 if (DEBUG_PROVIDER) Slog.v(TAG, 8938 "Adding provider requested by " 8939 + r.processName + " from process " 8940 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 8941 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 8942 if (stable) { 8943 conn.stableCount++; 8944 conn.numStableIncs++; 8945 } else { 8946 conn.unstableCount++; 8947 conn.numUnstableIncs++; 8948 } 8949 return conn; 8950 } 8951 } 8952 ContentProviderConnection conn = new ContentProviderConnection(cpr, r); 8953 if (stable) { 8954 conn.stableCount = 1; 8955 conn.numStableIncs = 1; 8956 } else { 8957 conn.unstableCount = 1; 8958 conn.numUnstableIncs = 1; 8959 } 8960 cpr.connections.add(conn); 8961 r.conProviders.add(conn); 8962 return conn; 8963 } 8964 cpr.addExternalProcessHandleLocked(externalProcessToken); 8965 return null; 8966 } 8967 8968 boolean decProviderCountLocked(ContentProviderConnection conn, 8969 ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 8970 if (conn != null) { 8971 cpr = conn.provider; 8972 if (DEBUG_PROVIDER) Slog.v(TAG, 8973 "Removing provider requested by " 8974 + conn.client.processName + " from process " 8975 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 8976 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 8977 if (stable) { 8978 conn.stableCount--; 8979 } else { 8980 conn.unstableCount--; 8981 } 8982 if (conn.stableCount == 0 && conn.unstableCount == 0) { 8983 cpr.connections.remove(conn); 8984 conn.client.conProviders.remove(conn); 8985 return true; 8986 } 8987 return false; 8988 } 8989 cpr.removeExternalProcessHandleLocked(externalProcessToken); 8990 return false; 8991 } 8992 8993 private void checkTime(long startTime, String where) { 8994 long now = SystemClock.elapsedRealtime(); 8995 if ((now-startTime) > 1000) { 8996 // If we are taking more than a second, log about it. 8997 Slog.w(TAG, "Slow operation: " + (now-startTime) + "ms so far, now at " + where); 8998 } 8999 } 9000 9001 private final ContentProviderHolder getContentProviderImpl(IApplicationThread caller, 9002 String name, IBinder token, boolean stable, int userId) { 9003 ContentProviderRecord cpr; 9004 ContentProviderConnection conn = null; 9005 ProviderInfo cpi = null; 9006 9007 synchronized(this) { 9008 long startTime = SystemClock.elapsedRealtime(); 9009 9010 ProcessRecord r = null; 9011 if (caller != null) { 9012 r = getRecordForAppLocked(caller); 9013 if (r == null) { 9014 throw new SecurityException( 9015 "Unable to find app for caller " + caller 9016 + " (pid=" + Binder.getCallingPid() 9017 + ") when getting content provider " + name); 9018 } 9019 } 9020 9021 boolean checkCrossUser = true; 9022 9023 checkTime(startTime, "getContentProviderImpl: getProviderByName"); 9024 9025 // First check if this content provider has been published... 9026 cpr = mProviderMap.getProviderByName(name, userId); 9027 // If that didn't work, check if it exists for user 0 and then 9028 // verify that it's a singleton provider before using it. 9029 if (cpr == null && userId != UserHandle.USER_OWNER) { 9030 cpr = mProviderMap.getProviderByName(name, UserHandle.USER_OWNER); 9031 if (cpr != null) { 9032 cpi = cpr.info; 9033 if (isSingleton(cpi.processName, cpi.applicationInfo, 9034 cpi.name, cpi.flags) 9035 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid)) { 9036 userId = UserHandle.USER_OWNER; 9037 checkCrossUser = false; 9038 } else { 9039 cpr = null; 9040 cpi = null; 9041 } 9042 } 9043 } 9044 9045 boolean providerRunning = cpr != null; 9046 if (providerRunning) { 9047 cpi = cpr.info; 9048 String msg; 9049 checkTime(startTime, "getContentProviderImpl: before checkContentProviderPermission"); 9050 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, checkCrossUser)) 9051 != null) { 9052 throw new SecurityException(msg); 9053 } 9054 checkTime(startTime, "getContentProviderImpl: after checkContentProviderPermission"); 9055 9056 if (r != null && cpr.canRunHere(r)) { 9057 // This provider has been published or is in the process 9058 // of being published... but it is also allowed to run 9059 // in the caller's process, so don't make a connection 9060 // and just let the caller instantiate its own instance. 9061 ContentProviderHolder holder = cpr.newHolder(null); 9062 // don't give caller the provider object, it needs 9063 // to make its own. 9064 holder.provider = null; 9065 return holder; 9066 } 9067 9068 final long origId = Binder.clearCallingIdentity(); 9069 9070 checkTime(startTime, "getContentProviderImpl: incProviderCountLocked"); 9071 9072 // In this case the provider instance already exists, so we can 9073 // return it right away. 9074 conn = incProviderCountLocked(r, cpr, token, stable); 9075 if (conn != null && (conn.stableCount+conn.unstableCount) == 1) { 9076 if (cpr.proc != null && r.setAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 9077 // If this is a perceptible app accessing the provider, 9078 // make sure to count it as being accessed and thus 9079 // back up on the LRU list. This is good because 9080 // content providers are often expensive to start. 9081 checkTime(startTime, "getContentProviderImpl: before updateLruProcess"); 9082 updateLruProcessLocked(cpr.proc, false, null); 9083 checkTime(startTime, "getContentProviderImpl: after updateLruProcess"); 9084 } 9085 } 9086 9087 if (cpr.proc != null) { 9088 if (false) { 9089 if (cpr.name.flattenToShortString().equals( 9090 "com.android.providers.calendar/.CalendarProvider2")) { 9091 Slog.v(TAG, "****************** KILLING " 9092 + cpr.name.flattenToShortString()); 9093 Process.killProcess(cpr.proc.pid); 9094 } 9095 } 9096 checkTime(startTime, "getContentProviderImpl: before updateOomAdj"); 9097 boolean success = updateOomAdjLocked(cpr.proc); 9098 checkTime(startTime, "getContentProviderImpl: after updateOomAdj"); 9099 if (DEBUG_PROVIDER) Slog.i(TAG, "Adjust success: " + success); 9100 // NOTE: there is still a race here where a signal could be 9101 // pending on the process even though we managed to update its 9102 // adj level. Not sure what to do about this, but at least 9103 // the race is now smaller. 9104 if (!success) { 9105 // Uh oh... it looks like the provider's process 9106 // has been killed on us. We need to wait for a new 9107 // process to be started, and make sure its death 9108 // doesn't kill our process. 9109 Slog.i(TAG, 9110 "Existing provider " + cpr.name.flattenToShortString() 9111 + " is crashing; detaching " + r); 9112 boolean lastRef = decProviderCountLocked(conn, cpr, token, stable); 9113 checkTime(startTime, "getContentProviderImpl: before appDied"); 9114 appDiedLocked(cpr.proc); 9115 checkTime(startTime, "getContentProviderImpl: after appDied"); 9116 if (!lastRef) { 9117 // This wasn't the last ref our process had on 9118 // the provider... we have now been killed, bail. 9119 return null; 9120 } 9121 providerRunning = false; 9122 conn = null; 9123 } 9124 } 9125 9126 Binder.restoreCallingIdentity(origId); 9127 } 9128 9129 boolean singleton; 9130 if (!providerRunning) { 9131 try { 9132 checkTime(startTime, "getContentProviderImpl: before resolveContentProvider"); 9133 cpi = AppGlobals.getPackageManager(). 9134 resolveContentProvider(name, 9135 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS, userId); 9136 checkTime(startTime, "getContentProviderImpl: after resolveContentProvider"); 9137 } catch (RemoteException ex) { 9138 } 9139 if (cpi == null) { 9140 return null; 9141 } 9142 // If the provider is a singleton AND 9143 // (it's a call within the same user || the provider is a 9144 // privileged app) 9145 // Then allow connecting to the singleton provider 9146 singleton = isSingleton(cpi.processName, cpi.applicationInfo, 9147 cpi.name, cpi.flags) 9148 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid); 9149 if (singleton) { 9150 userId = UserHandle.USER_OWNER; 9151 } 9152 cpi.applicationInfo = getAppInfoForUser(cpi.applicationInfo, userId); 9153 checkTime(startTime, "getContentProviderImpl: got app info for user"); 9154 9155 String msg; 9156 checkTime(startTime, "getContentProviderImpl: before checkContentProviderPermission"); 9157 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, !singleton)) 9158 != null) { 9159 throw new SecurityException(msg); 9160 } 9161 checkTime(startTime, "getContentProviderImpl: after checkContentProviderPermission"); 9162 9163 if (!mProcessesReady && !mDidUpdate && !mWaitingUpdate 9164 && !cpi.processName.equals("system")) { 9165 // If this content provider does not run in the system 9166 // process, and the system is not yet ready to run other 9167 // processes, then fail fast instead of hanging. 9168 throw new IllegalArgumentException( 9169 "Attempt to launch content provider before system ready"); 9170 } 9171 9172 // Make sure that the user who owns this provider is started. If not, 9173 // we don't want to allow it to run. 9174 if (mStartedUsers.get(userId) == null) { 9175 Slog.w(TAG, "Unable to launch app " 9176 + cpi.applicationInfo.packageName + "/" 9177 + cpi.applicationInfo.uid + " for provider " 9178 + name + ": user " + userId + " is stopped"); 9179 return null; 9180 } 9181 9182 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 9183 checkTime(startTime, "getContentProviderImpl: before getProviderByClass"); 9184 cpr = mProviderMap.getProviderByClass(comp, userId); 9185 checkTime(startTime, "getContentProviderImpl: after getProviderByClass"); 9186 final boolean firstClass = cpr == null; 9187 if (firstClass) { 9188 try { 9189 checkTime(startTime, "getContentProviderImpl: before getApplicationInfo"); 9190 ApplicationInfo ai = 9191 AppGlobals.getPackageManager(). 9192 getApplicationInfo( 9193 cpi.applicationInfo.packageName, 9194 STOCK_PM_FLAGS, userId); 9195 checkTime(startTime, "getContentProviderImpl: after getApplicationInfo"); 9196 if (ai == null) { 9197 Slog.w(TAG, "No package info for content provider " 9198 + cpi.name); 9199 return null; 9200 } 9201 ai = getAppInfoForUser(ai, userId); 9202 cpr = new ContentProviderRecord(this, cpi, ai, comp, singleton); 9203 } catch (RemoteException ex) { 9204 // pm is in same process, this will never happen. 9205 } 9206 } 9207 9208 checkTime(startTime, "getContentProviderImpl: now have ContentProviderRecord"); 9209 9210 if (r != null && cpr.canRunHere(r)) { 9211 // If this is a multiprocess provider, then just return its 9212 // info and allow the caller to instantiate it. Only do 9213 // this if the provider is the same user as the caller's 9214 // process, or can run as root (so can be in any process). 9215 return cpr.newHolder(null); 9216 } 9217 9218 if (DEBUG_PROVIDER) { 9219 RuntimeException e = new RuntimeException("here"); 9220 Slog.w(TAG, "LAUNCHING REMOTE PROVIDER (myuid " + (r != null ? r.uid : null) 9221 + " pruid " + cpr.appInfo.uid + "): " + cpr.info.name, e); 9222 } 9223 9224 // This is single process, and our app is now connecting to it. 9225 // See if we are already in the process of launching this 9226 // provider. 9227 final int N = mLaunchingProviders.size(); 9228 int i; 9229 for (i=0; i<N; i++) { 9230 if (mLaunchingProviders.get(i) == cpr) { 9231 break; 9232 } 9233 } 9234 9235 // If the provider is not already being launched, then get it 9236 // started. 9237 if (i >= N) { 9238 final long origId = Binder.clearCallingIdentity(); 9239 9240 try { 9241 // Content provider is now in use, its package can't be stopped. 9242 try { 9243 checkTime(startTime, "getContentProviderImpl: before set stopped state"); 9244 AppGlobals.getPackageManager().setPackageStoppedState( 9245 cpr.appInfo.packageName, false, userId); 9246 checkTime(startTime, "getContentProviderImpl: after set stopped state"); 9247 } catch (RemoteException e) { 9248 } catch (IllegalArgumentException e) { 9249 Slog.w(TAG, "Failed trying to unstop package " 9250 + cpr.appInfo.packageName + ": " + e); 9251 } 9252 9253 // Use existing process if already started 9254 checkTime(startTime, "getContentProviderImpl: looking for process record"); 9255 ProcessRecord proc = getProcessRecordLocked( 9256 cpi.processName, cpr.appInfo.uid, false); 9257 if (proc != null && proc.thread != null) { 9258 if (DEBUG_PROVIDER) { 9259 Slog.d(TAG, "Installing in existing process " + proc); 9260 } 9261 checkTime(startTime, "getContentProviderImpl: scheduling install"); 9262 proc.pubProviders.put(cpi.name, cpr); 9263 try { 9264 proc.thread.scheduleInstallProvider(cpi); 9265 } catch (RemoteException e) { 9266 } 9267 } else { 9268 checkTime(startTime, "getContentProviderImpl: before start process"); 9269 proc = startProcessLocked(cpi.processName, 9270 cpr.appInfo, false, 0, "content provider", 9271 new ComponentName(cpi.applicationInfo.packageName, 9272 cpi.name), false, false, false); 9273 checkTime(startTime, "getContentProviderImpl: after start process"); 9274 if (proc == null) { 9275 Slog.w(TAG, "Unable to launch app " 9276 + cpi.applicationInfo.packageName + "/" 9277 + cpi.applicationInfo.uid + " for provider " 9278 + name + ": process is bad"); 9279 return null; 9280 } 9281 } 9282 cpr.launchingApp = proc; 9283 mLaunchingProviders.add(cpr); 9284 } finally { 9285 Binder.restoreCallingIdentity(origId); 9286 } 9287 } 9288 9289 checkTime(startTime, "getContentProviderImpl: updating data structures"); 9290 9291 // Make sure the provider is published (the same provider class 9292 // may be published under multiple names). 9293 if (firstClass) { 9294 mProviderMap.putProviderByClass(comp, cpr); 9295 } 9296 9297 mProviderMap.putProviderByName(name, cpr); 9298 conn = incProviderCountLocked(r, cpr, token, stable); 9299 if (conn != null) { 9300 conn.waiting = true; 9301 } 9302 } 9303 checkTime(startTime, "getContentProviderImpl: done!"); 9304 } 9305 9306 // Wait for the provider to be published... 9307 synchronized (cpr) { 9308 while (cpr.provider == null) { 9309 if (cpr.launchingApp == null) { 9310 Slog.w(TAG, "Unable to launch app " 9311 + cpi.applicationInfo.packageName + "/" 9312 + cpi.applicationInfo.uid + " for provider " 9313 + name + ": launching app became null"); 9314 EventLog.writeEvent(EventLogTags.AM_PROVIDER_LOST_PROCESS, 9315 UserHandle.getUserId(cpi.applicationInfo.uid), 9316 cpi.applicationInfo.packageName, 9317 cpi.applicationInfo.uid, name); 9318 return null; 9319 } 9320 try { 9321 if (DEBUG_MU) { 9322 Slog.v(TAG_MU, "Waiting to start provider " + cpr + " launchingApp=" 9323 + cpr.launchingApp); 9324 } 9325 if (conn != null) { 9326 conn.waiting = true; 9327 } 9328 cpr.wait(); 9329 } catch (InterruptedException ex) { 9330 } finally { 9331 if (conn != null) { 9332 conn.waiting = false; 9333 } 9334 } 9335 } 9336 } 9337 return cpr != null ? cpr.newHolder(conn) : null; 9338 } 9339 9340 @Override 9341 public final ContentProviderHolder getContentProvider( 9342 IApplicationThread caller, String name, int userId, boolean stable) { 9343 enforceNotIsolatedCaller("getContentProvider"); 9344 if (caller == null) { 9345 String msg = "null IApplicationThread when getting content provider " 9346 + name; 9347 Slog.w(TAG, msg); 9348 throw new SecurityException(msg); 9349 } 9350 // The incoming user check is now handled in checkContentProviderPermissionLocked() to deal 9351 // with cross-user grant. 9352 return getContentProviderImpl(caller, name, null, stable, userId); 9353 } 9354 9355 public ContentProviderHolder getContentProviderExternal( 9356 String name, int userId, IBinder token) { 9357 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 9358 "Do not have permission in call getContentProviderExternal()"); 9359 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 9360 false, ALLOW_FULL_ONLY, "getContentProvider", null); 9361 return getContentProviderExternalUnchecked(name, token, userId); 9362 } 9363 9364 private ContentProviderHolder getContentProviderExternalUnchecked(String name, 9365 IBinder token, int userId) { 9366 return getContentProviderImpl(null, name, token, true, userId); 9367 } 9368 9369 /** 9370 * Drop a content provider from a ProcessRecord's bookkeeping 9371 */ 9372 public void removeContentProvider(IBinder connection, boolean stable) { 9373 enforceNotIsolatedCaller("removeContentProvider"); 9374 long ident = Binder.clearCallingIdentity(); 9375 try { 9376 synchronized (this) { 9377 ContentProviderConnection conn; 9378 try { 9379 conn = (ContentProviderConnection)connection; 9380 } catch (ClassCastException e) { 9381 String msg ="removeContentProvider: " + connection 9382 + " not a ContentProviderConnection"; 9383 Slog.w(TAG, msg); 9384 throw new IllegalArgumentException(msg); 9385 } 9386 if (conn == null) { 9387 throw new NullPointerException("connection is null"); 9388 } 9389 if (decProviderCountLocked(conn, null, null, stable)) { 9390 updateOomAdjLocked(); 9391 } 9392 } 9393 } finally { 9394 Binder.restoreCallingIdentity(ident); 9395 } 9396 } 9397 9398 public void removeContentProviderExternal(String name, IBinder token) { 9399 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 9400 "Do not have permission in call removeContentProviderExternal()"); 9401 removeContentProviderExternalUnchecked(name, token, UserHandle.getCallingUserId()); 9402 } 9403 9404 private void removeContentProviderExternalUnchecked(String name, IBinder token, int userId) { 9405 synchronized (this) { 9406 ContentProviderRecord cpr = mProviderMap.getProviderByName(name, userId); 9407 if(cpr == null) { 9408 //remove from mProvidersByClass 9409 if(localLOGV) Slog.v(TAG, name+" content provider not found in providers list"); 9410 return; 9411 } 9412 9413 //update content provider record entry info 9414 ComponentName comp = new ComponentName(cpr.info.packageName, cpr.info.name); 9415 ContentProviderRecord localCpr = mProviderMap.getProviderByClass(comp, userId); 9416 if (localCpr.hasExternalProcessHandles()) { 9417 if (localCpr.removeExternalProcessHandleLocked(token)) { 9418 updateOomAdjLocked(); 9419 } else { 9420 Slog.e(TAG, "Attmpt to remove content provider " + localCpr 9421 + " with no external reference for token: " 9422 + token + "."); 9423 } 9424 } else { 9425 Slog.e(TAG, "Attmpt to remove content provider: " + localCpr 9426 + " with no external references."); 9427 } 9428 } 9429 } 9430 9431 public final void publishContentProviders(IApplicationThread caller, 9432 List<ContentProviderHolder> providers) { 9433 if (providers == null) { 9434 return; 9435 } 9436 9437 enforceNotIsolatedCaller("publishContentProviders"); 9438 synchronized (this) { 9439 final ProcessRecord r = getRecordForAppLocked(caller); 9440 if (DEBUG_MU) 9441 Slog.v(TAG_MU, "ProcessRecord uid = " + r.uid); 9442 if (r == null) { 9443 throw new SecurityException( 9444 "Unable to find app for caller " + caller 9445 + " (pid=" + Binder.getCallingPid() 9446 + ") when publishing content providers"); 9447 } 9448 9449 final long origId = Binder.clearCallingIdentity(); 9450 9451 final int N = providers.size(); 9452 for (int i=0; i<N; i++) { 9453 ContentProviderHolder src = providers.get(i); 9454 if (src == null || src.info == null || src.provider == null) { 9455 continue; 9456 } 9457 ContentProviderRecord dst = r.pubProviders.get(src.info.name); 9458 if (DEBUG_MU) 9459 Slog.v(TAG_MU, "ContentProviderRecord uid = " + dst.uid); 9460 if (dst != null) { 9461 ComponentName comp = new ComponentName(dst.info.packageName, dst.info.name); 9462 mProviderMap.putProviderByClass(comp, dst); 9463 String names[] = dst.info.authority.split(";"); 9464 for (int j = 0; j < names.length; j++) { 9465 mProviderMap.putProviderByName(names[j], dst); 9466 } 9467 9468 int NL = mLaunchingProviders.size(); 9469 int j; 9470 for (j=0; j<NL; j++) { 9471 if (mLaunchingProviders.get(j) == dst) { 9472 mLaunchingProviders.remove(j); 9473 j--; 9474 NL--; 9475 } 9476 } 9477 synchronized (dst) { 9478 dst.provider = src.provider; 9479 dst.proc = r; 9480 dst.notifyAll(); 9481 } 9482 updateOomAdjLocked(r); 9483 } 9484 } 9485 9486 Binder.restoreCallingIdentity(origId); 9487 } 9488 } 9489 9490 public boolean refContentProvider(IBinder connection, int stable, int unstable) { 9491 ContentProviderConnection conn; 9492 try { 9493 conn = (ContentProviderConnection)connection; 9494 } catch (ClassCastException e) { 9495 String msg ="refContentProvider: " + connection 9496 + " not a ContentProviderConnection"; 9497 Slog.w(TAG, msg); 9498 throw new IllegalArgumentException(msg); 9499 } 9500 if (conn == null) { 9501 throw new NullPointerException("connection is null"); 9502 } 9503 9504 synchronized (this) { 9505 if (stable > 0) { 9506 conn.numStableIncs += stable; 9507 } 9508 stable = conn.stableCount + stable; 9509 if (stable < 0) { 9510 throw new IllegalStateException("stableCount < 0: " + stable); 9511 } 9512 9513 if (unstable > 0) { 9514 conn.numUnstableIncs += unstable; 9515 } 9516 unstable = conn.unstableCount + unstable; 9517 if (unstable < 0) { 9518 throw new IllegalStateException("unstableCount < 0: " + unstable); 9519 } 9520 9521 if ((stable+unstable) <= 0) { 9522 throw new IllegalStateException("ref counts can't go to zero here: stable=" 9523 + stable + " unstable=" + unstable); 9524 } 9525 conn.stableCount = stable; 9526 conn.unstableCount = unstable; 9527 return !conn.dead; 9528 } 9529 } 9530 9531 public void unstableProviderDied(IBinder connection) { 9532 ContentProviderConnection conn; 9533 try { 9534 conn = (ContentProviderConnection)connection; 9535 } catch (ClassCastException e) { 9536 String msg ="refContentProvider: " + connection 9537 + " not a ContentProviderConnection"; 9538 Slog.w(TAG, msg); 9539 throw new IllegalArgumentException(msg); 9540 } 9541 if (conn == null) { 9542 throw new NullPointerException("connection is null"); 9543 } 9544 9545 // Safely retrieve the content provider associated with the connection. 9546 IContentProvider provider; 9547 synchronized (this) { 9548 provider = conn.provider.provider; 9549 } 9550 9551 if (provider == null) { 9552 // Um, yeah, we're way ahead of you. 9553 return; 9554 } 9555 9556 // Make sure the caller is being honest with us. 9557 if (provider.asBinder().pingBinder()) { 9558 // Er, no, still looks good to us. 9559 synchronized (this) { 9560 Slog.w(TAG, "unstableProviderDied: caller " + Binder.getCallingUid() 9561 + " says " + conn + " died, but we don't agree"); 9562 return; 9563 } 9564 } 9565 9566 // Well look at that! It's dead! 9567 synchronized (this) { 9568 if (conn.provider.provider != provider) { 9569 // But something changed... good enough. 9570 return; 9571 } 9572 9573 ProcessRecord proc = conn.provider.proc; 9574 if (proc == null || proc.thread == null) { 9575 // Seems like the process is already cleaned up. 9576 return; 9577 } 9578 9579 // As far as we're concerned, this is just like receiving a 9580 // death notification... just a bit prematurely. 9581 Slog.i(TAG, "Process " + proc.processName + " (pid " + proc.pid 9582 + ") early provider death"); 9583 final long ident = Binder.clearCallingIdentity(); 9584 try { 9585 appDiedLocked(proc); 9586 } finally { 9587 Binder.restoreCallingIdentity(ident); 9588 } 9589 } 9590 } 9591 9592 @Override 9593 public void appNotRespondingViaProvider(IBinder connection) { 9594 enforceCallingPermission( 9595 android.Manifest.permission.REMOVE_TASKS, "appNotRespondingViaProvider()"); 9596 9597 final ContentProviderConnection conn = (ContentProviderConnection) connection; 9598 if (conn == null) { 9599 Slog.w(TAG, "ContentProviderConnection is null"); 9600 return; 9601 } 9602 9603 final ProcessRecord host = conn.provider.proc; 9604 if (host == null) { 9605 Slog.w(TAG, "Failed to find hosting ProcessRecord"); 9606 return; 9607 } 9608 9609 final long token = Binder.clearCallingIdentity(); 9610 try { 9611 appNotResponding(host, null, null, false, "ContentProvider not responding"); 9612 } finally { 9613 Binder.restoreCallingIdentity(token); 9614 } 9615 } 9616 9617 public final void installSystemProviders() { 9618 List<ProviderInfo> providers; 9619 synchronized (this) { 9620 ProcessRecord app = mProcessNames.get("system", Process.SYSTEM_UID); 9621 providers = generateApplicationProvidersLocked(app); 9622 if (providers != null) { 9623 for (int i=providers.size()-1; i>=0; i--) { 9624 ProviderInfo pi = (ProviderInfo)providers.get(i); 9625 if ((pi.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) == 0) { 9626 Slog.w(TAG, "Not installing system proc provider " + pi.name 9627 + ": not system .apk"); 9628 providers.remove(i); 9629 } 9630 } 9631 } 9632 } 9633 if (providers != null) { 9634 mSystemThread.installSystemProviders(providers); 9635 } 9636 9637 mCoreSettingsObserver = new CoreSettingsObserver(this); 9638 9639 //mUsageStatsService.monitorPackages(); 9640 } 9641 9642 /** 9643 * Allows apps to retrieve the MIME type of a URI. 9644 * If an app is in the same user as the ContentProvider, or if it is allowed to interact across 9645 * users, then it does not need permission to access the ContentProvider. 9646 * Either, it needs cross-user uri grants. 9647 * 9648 * CTS tests for this functionality can be run with "runtest cts-appsecurity". 9649 * 9650 * Test cases are at cts/tests/appsecurity-tests/test-apps/UsePermissionDiffCert/ 9651 * src/com/android/cts/usespermissiondiffcertapp/AccessPermissionWithDiffSigTest.java 9652 */ 9653 public String getProviderMimeType(Uri uri, int userId) { 9654 enforceNotIsolatedCaller("getProviderMimeType"); 9655 final String name = uri.getAuthority(); 9656 int callingUid = Binder.getCallingUid(); 9657 int callingPid = Binder.getCallingPid(); 9658 long ident = 0; 9659 boolean clearedIdentity = false; 9660 userId = unsafeConvertIncomingUser(userId); 9661 if (UserHandle.getUserId(callingUid) != userId) { 9662 if (checkComponentPermission(INTERACT_ACROSS_USERS, callingPid, 9663 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED 9664 || checkComponentPermission(INTERACT_ACROSS_USERS_FULL, callingPid, 9665 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED) { 9666 clearedIdentity = true; 9667 ident = Binder.clearCallingIdentity(); 9668 } 9669 } 9670 ContentProviderHolder holder = null; 9671 try { 9672 holder = getContentProviderExternalUnchecked(name, null, userId); 9673 if (holder != null) { 9674 return holder.provider.getType(uri); 9675 } 9676 } catch (RemoteException e) { 9677 Log.w(TAG, "Content provider dead retrieving " + uri, e); 9678 return null; 9679 } finally { 9680 // We need to clear the identity to call removeContentProviderExternalUnchecked 9681 if (!clearedIdentity) { 9682 ident = Binder.clearCallingIdentity(); 9683 } 9684 try { 9685 if (holder != null) { 9686 removeContentProviderExternalUnchecked(name, null, userId); 9687 } 9688 } finally { 9689 Binder.restoreCallingIdentity(ident); 9690 } 9691 } 9692 9693 return null; 9694 } 9695 9696 // ========================================================= 9697 // GLOBAL MANAGEMENT 9698 // ========================================================= 9699 9700 final ProcessRecord newProcessRecordLocked(ApplicationInfo info, String customProcess, 9701 boolean isolated, int isolatedUid) { 9702 String proc = customProcess != null ? customProcess : info.processName; 9703 BatteryStatsImpl.Uid.Proc ps = null; 9704 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 9705 int uid = info.uid; 9706 if (isolated) { 9707 if (isolatedUid == 0) { 9708 int userId = UserHandle.getUserId(uid); 9709 int stepsLeft = Process.LAST_ISOLATED_UID - Process.FIRST_ISOLATED_UID + 1; 9710 while (true) { 9711 if (mNextIsolatedProcessUid < Process.FIRST_ISOLATED_UID 9712 || mNextIsolatedProcessUid > Process.LAST_ISOLATED_UID) { 9713 mNextIsolatedProcessUid = Process.FIRST_ISOLATED_UID; 9714 } 9715 uid = UserHandle.getUid(userId, mNextIsolatedProcessUid); 9716 mNextIsolatedProcessUid++; 9717 if (mIsolatedProcesses.indexOfKey(uid) < 0) { 9718 // No process for this uid, use it. 9719 break; 9720 } 9721 stepsLeft--; 9722 if (stepsLeft <= 0) { 9723 return null; 9724 } 9725 } 9726 } else { 9727 // Special case for startIsolatedProcess (internal only), where 9728 // the uid of the isolated process is specified by the caller. 9729 uid = isolatedUid; 9730 } 9731 } 9732 return new ProcessRecord(stats, info, proc, uid); 9733 } 9734 9735 final ProcessRecord addAppLocked(ApplicationInfo info, boolean isolated, 9736 String abiOverride) { 9737 ProcessRecord app; 9738 if (!isolated) { 9739 app = getProcessRecordLocked(info.processName, info.uid, true); 9740 } else { 9741 app = null; 9742 } 9743 9744 if (app == null) { 9745 app = newProcessRecordLocked(info, null, isolated, 0); 9746 mProcessNames.put(info.processName, app.uid, app); 9747 if (isolated) { 9748 mIsolatedProcesses.put(app.uid, app); 9749 } 9750 updateLruProcessLocked(app, false, null); 9751 updateOomAdjLocked(); 9752 } 9753 9754 // This package really, really can not be stopped. 9755 try { 9756 AppGlobals.getPackageManager().setPackageStoppedState( 9757 info.packageName, false, UserHandle.getUserId(app.uid)); 9758 } catch (RemoteException e) { 9759 } catch (IllegalArgumentException e) { 9760 Slog.w(TAG, "Failed trying to unstop package " 9761 + info.packageName + ": " + e); 9762 } 9763 9764 if ((info.flags&(ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) 9765 == (ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) { 9766 app.persistent = true; 9767 app.maxAdj = ProcessList.PERSISTENT_PROC_ADJ; 9768 } 9769 if (app.thread == null && mPersistentStartingProcesses.indexOf(app) < 0) { 9770 mPersistentStartingProcesses.add(app); 9771 startProcessLocked(app, "added application", app.processName, abiOverride, 9772 null /* entryPoint */, null /* entryPointArgs */); 9773 } 9774 9775 return app; 9776 } 9777 9778 public void unhandledBack() { 9779 enforceCallingPermission(android.Manifest.permission.FORCE_BACK, 9780 "unhandledBack()"); 9781 9782 synchronized(this) { 9783 final long origId = Binder.clearCallingIdentity(); 9784 try { 9785 getFocusedStack().unhandledBackLocked(); 9786 } finally { 9787 Binder.restoreCallingIdentity(origId); 9788 } 9789 } 9790 } 9791 9792 public ParcelFileDescriptor openContentUri(Uri uri) throws RemoteException { 9793 enforceNotIsolatedCaller("openContentUri"); 9794 final int userId = UserHandle.getCallingUserId(); 9795 String name = uri.getAuthority(); 9796 ContentProviderHolder cph = getContentProviderExternalUnchecked(name, null, userId); 9797 ParcelFileDescriptor pfd = null; 9798 if (cph != null) { 9799 // We record the binder invoker's uid in thread-local storage before 9800 // going to the content provider to open the file. Later, in the code 9801 // that handles all permissions checks, we look for this uid and use 9802 // that rather than the Activity Manager's own uid. The effect is that 9803 // we do the check against the caller's permissions even though it looks 9804 // to the content provider like the Activity Manager itself is making 9805 // the request. 9806 sCallerIdentity.set(new Identity( 9807 Binder.getCallingPid(), Binder.getCallingUid())); 9808 try { 9809 pfd = cph.provider.openFile(null, uri, "r", null); 9810 } catch (FileNotFoundException e) { 9811 // do nothing; pfd will be returned null 9812 } finally { 9813 // Ensure that whatever happens, we clean up the identity state 9814 sCallerIdentity.remove(); 9815 } 9816 9817 // We've got the fd now, so we're done with the provider. 9818 removeContentProviderExternalUnchecked(name, null, userId); 9819 } else { 9820 Slog.d(TAG, "Failed to get provider for authority '" + name + "'"); 9821 } 9822 return pfd; 9823 } 9824 9825 // Actually is sleeping or shutting down or whatever else in the future 9826 // is an inactive state. 9827 public boolean isSleepingOrShuttingDown() { 9828 return mSleeping || mShuttingDown; 9829 } 9830 9831 public boolean isSleeping() { 9832 return mSleeping; 9833 } 9834 9835 void goingToSleep() { 9836 synchronized(this) { 9837 mWentToSleep = true; 9838 updateEventDispatchingLocked(); 9839 goToSleepIfNeededLocked(); 9840 } 9841 } 9842 9843 void finishRunningVoiceLocked() { 9844 if (mRunningVoice) { 9845 mRunningVoice = false; 9846 goToSleepIfNeededLocked(); 9847 } 9848 } 9849 9850 void goToSleepIfNeededLocked() { 9851 if (mWentToSleep && !mRunningVoice) { 9852 if (!mSleeping) { 9853 mSleeping = true; 9854 mStackSupervisor.goingToSleepLocked(); 9855 9856 // Initialize the wake times of all processes. 9857 checkExcessivePowerUsageLocked(false); 9858 mHandler.removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 9859 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 9860 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 9861 } 9862 } 9863 } 9864 9865 void notifyTaskPersisterLocked(TaskRecord task, boolean flush) { 9866 if (task != null && task.stack != null && task.stack.isHomeStack()) { 9867 // Never persist the home stack. 9868 return; 9869 } 9870 mTaskPersister.wakeup(task, flush); 9871 } 9872 9873 @Override 9874 public boolean shutdown(int timeout) { 9875 if (checkCallingPermission(android.Manifest.permission.SHUTDOWN) 9876 != PackageManager.PERMISSION_GRANTED) { 9877 throw new SecurityException("Requires permission " 9878 + android.Manifest.permission.SHUTDOWN); 9879 } 9880 9881 boolean timedout = false; 9882 9883 synchronized(this) { 9884 mShuttingDown = true; 9885 updateEventDispatchingLocked(); 9886 timedout = mStackSupervisor.shutdownLocked(timeout); 9887 } 9888 9889 mAppOpsService.shutdown(); 9890 if (mUsageStatsService != null) { 9891 mUsageStatsService.prepareShutdown(); 9892 } 9893 mBatteryStatsService.shutdown(); 9894 synchronized (this) { 9895 mProcessStats.shutdownLocked(); 9896 } 9897 notifyTaskPersisterLocked(null, true); 9898 9899 return timedout; 9900 } 9901 9902 public final void activitySlept(IBinder token) { 9903 if (localLOGV) Slog.v(TAG, "Activity slept: token=" + token); 9904 9905 final long origId = Binder.clearCallingIdentity(); 9906 9907 synchronized (this) { 9908 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9909 if (r != null) { 9910 mStackSupervisor.activitySleptLocked(r); 9911 } 9912 } 9913 9914 Binder.restoreCallingIdentity(origId); 9915 } 9916 9917 void logLockScreen(String msg) { 9918 if (DEBUG_LOCKSCREEN) Slog.d(TAG, Debug.getCallers(2) + ":" + msg + 9919 " mLockScreenShown=" + mLockScreenShown + " mWentToSleep=" + 9920 mWentToSleep + " mSleeping=" + mSleeping); 9921 } 9922 9923 private void comeOutOfSleepIfNeededLocked() { 9924 if ((!mWentToSleep && !mLockScreenShown) || mRunningVoice) { 9925 if (mSleeping) { 9926 mSleeping = false; 9927 mStackSupervisor.comeOutOfSleepIfNeededLocked(); 9928 } 9929 } 9930 } 9931 9932 void wakingUp() { 9933 synchronized(this) { 9934 mWentToSleep = false; 9935 updateEventDispatchingLocked(); 9936 comeOutOfSleepIfNeededLocked(); 9937 } 9938 } 9939 9940 void startRunningVoiceLocked() { 9941 if (!mRunningVoice) { 9942 mRunningVoice = true; 9943 comeOutOfSleepIfNeededLocked(); 9944 } 9945 } 9946 9947 private void updateEventDispatchingLocked() { 9948 mWindowManager.setEventDispatching(mBooted && !mShuttingDown); 9949 } 9950 9951 public void setLockScreenShown(boolean shown) { 9952 if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER) 9953 != PackageManager.PERMISSION_GRANTED) { 9954 throw new SecurityException("Requires permission " 9955 + android.Manifest.permission.DEVICE_POWER); 9956 } 9957 9958 synchronized(this) { 9959 long ident = Binder.clearCallingIdentity(); 9960 try { 9961 if (DEBUG_LOCKSCREEN) logLockScreen(" shown=" + shown); 9962 mLockScreenShown = shown; 9963 comeOutOfSleepIfNeededLocked(); 9964 } finally { 9965 Binder.restoreCallingIdentity(ident); 9966 } 9967 } 9968 } 9969 9970 @Override 9971 public void stopAppSwitches() { 9972 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 9973 != PackageManager.PERMISSION_GRANTED) { 9974 throw new SecurityException("Requires permission " 9975 + android.Manifest.permission.STOP_APP_SWITCHES); 9976 } 9977 9978 synchronized(this) { 9979 mAppSwitchesAllowedTime = SystemClock.uptimeMillis() 9980 + APP_SWITCH_DELAY_TIME; 9981 mDidAppSwitch = false; 9982 mHandler.removeMessages(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 9983 Message msg = mHandler.obtainMessage(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 9984 mHandler.sendMessageDelayed(msg, APP_SWITCH_DELAY_TIME); 9985 } 9986 } 9987 9988 public void resumeAppSwitches() { 9989 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 9990 != PackageManager.PERMISSION_GRANTED) { 9991 throw new SecurityException("Requires permission " 9992 + android.Manifest.permission.STOP_APP_SWITCHES); 9993 } 9994 9995 synchronized(this) { 9996 // Note that we don't execute any pending app switches... we will 9997 // let those wait until either the timeout, or the next start 9998 // activity request. 9999 mAppSwitchesAllowedTime = 0; 10000 } 10001 } 10002 10003 boolean checkAppSwitchAllowedLocked(int callingPid, int callingUid, 10004 String name) { 10005 if (mAppSwitchesAllowedTime < SystemClock.uptimeMillis()) { 10006 return true; 10007 } 10008 10009 final int perm = checkComponentPermission( 10010 android.Manifest.permission.STOP_APP_SWITCHES, callingPid, 10011 callingUid, -1, true); 10012 if (perm == PackageManager.PERMISSION_GRANTED) { 10013 return true; 10014 } 10015 10016 Slog.w(TAG, name + " request from " + callingUid + " stopped"); 10017 return false; 10018 } 10019 10020 public void setDebugApp(String packageName, boolean waitForDebugger, 10021 boolean persistent) { 10022 enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP, 10023 "setDebugApp()"); 10024 10025 long ident = Binder.clearCallingIdentity(); 10026 try { 10027 // Note that this is not really thread safe if there are multiple 10028 // callers into it at the same time, but that's not a situation we 10029 // care about. 10030 if (persistent) { 10031 final ContentResolver resolver = mContext.getContentResolver(); 10032 Settings.Global.putString( 10033 resolver, Settings.Global.DEBUG_APP, 10034 packageName); 10035 Settings.Global.putInt( 10036 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 10037 waitForDebugger ? 1 : 0); 10038 } 10039 10040 synchronized (this) { 10041 if (!persistent) { 10042 mOrigDebugApp = mDebugApp; 10043 mOrigWaitForDebugger = mWaitForDebugger; 10044 } 10045 mDebugApp = packageName; 10046 mWaitForDebugger = waitForDebugger; 10047 mDebugTransient = !persistent; 10048 if (packageName != null) { 10049 forceStopPackageLocked(packageName, -1, false, false, true, true, 10050 false, UserHandle.USER_ALL, "set debug app"); 10051 } 10052 } 10053 } finally { 10054 Binder.restoreCallingIdentity(ident); 10055 } 10056 } 10057 10058 void setOpenGlTraceApp(ApplicationInfo app, String processName) { 10059 synchronized (this) { 10060 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 10061 if (!isDebuggable) { 10062 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 10063 throw new SecurityException("Process not debuggable: " + app.packageName); 10064 } 10065 } 10066 10067 mOpenGlTraceApp = processName; 10068 } 10069 } 10070 10071 void setProfileApp(ApplicationInfo app, String processName, ProfilerInfo profilerInfo) { 10072 synchronized (this) { 10073 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 10074 if (!isDebuggable) { 10075 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 10076 throw new SecurityException("Process not debuggable: " + app.packageName); 10077 } 10078 } 10079 mProfileApp = processName; 10080 mProfileFile = profilerInfo.profileFile; 10081 if (mProfileFd != null) { 10082 try { 10083 mProfileFd.close(); 10084 } catch (IOException e) { 10085 } 10086 mProfileFd = null; 10087 } 10088 mProfileFd = profilerInfo.profileFd; 10089 mSamplingInterval = profilerInfo.samplingInterval; 10090 mAutoStopProfiler = profilerInfo.autoStopProfiler; 10091 mProfileType = 0; 10092 } 10093 } 10094 10095 @Override 10096 public void setAlwaysFinish(boolean enabled) { 10097 enforceCallingPermission(android.Manifest.permission.SET_ALWAYS_FINISH, 10098 "setAlwaysFinish()"); 10099 10100 Settings.Global.putInt( 10101 mContext.getContentResolver(), 10102 Settings.Global.ALWAYS_FINISH_ACTIVITIES, enabled ? 1 : 0); 10103 10104 synchronized (this) { 10105 mAlwaysFinishActivities = enabled; 10106 } 10107 } 10108 10109 @Override 10110 public void setActivityController(IActivityController controller) { 10111 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 10112 "setActivityController()"); 10113 synchronized (this) { 10114 mController = controller; 10115 Watchdog.getInstance().setActivityController(controller); 10116 } 10117 } 10118 10119 @Override 10120 public void setUserIsMonkey(boolean userIsMonkey) { 10121 synchronized (this) { 10122 synchronized (mPidsSelfLocked) { 10123 final int callingPid = Binder.getCallingPid(); 10124 ProcessRecord precessRecord = mPidsSelfLocked.get(callingPid); 10125 if (precessRecord == null) { 10126 throw new SecurityException("Unknown process: " + callingPid); 10127 } 10128 if (precessRecord.instrumentationUiAutomationConnection == null) { 10129 throw new SecurityException("Only an instrumentation process " 10130 + "with a UiAutomation can call setUserIsMonkey"); 10131 } 10132 } 10133 mUserIsMonkey = userIsMonkey; 10134 } 10135 } 10136 10137 @Override 10138 public boolean isUserAMonkey() { 10139 synchronized (this) { 10140 // If there is a controller also implies the user is a monkey. 10141 return (mUserIsMonkey || mController != null); 10142 } 10143 } 10144 10145 public void requestBugReport() { 10146 enforceCallingPermission(android.Manifest.permission.DUMP, "requestBugReport"); 10147 SystemProperties.set("ctl.start", "bugreport"); 10148 } 10149 10150 public static long getInputDispatchingTimeoutLocked(ActivityRecord r) { 10151 return r != null ? getInputDispatchingTimeoutLocked(r.app) : KEY_DISPATCHING_TIMEOUT; 10152 } 10153 10154 public static long getInputDispatchingTimeoutLocked(ProcessRecord r) { 10155 if (r != null && (r.instrumentationClass != null || r.usingWrapper)) { 10156 return INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT; 10157 } 10158 return KEY_DISPATCHING_TIMEOUT; 10159 } 10160 10161 @Override 10162 public long inputDispatchingTimedOut(int pid, final boolean aboveSystem, String reason) { 10163 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 10164 != PackageManager.PERMISSION_GRANTED) { 10165 throw new SecurityException("Requires permission " 10166 + android.Manifest.permission.FILTER_EVENTS); 10167 } 10168 ProcessRecord proc; 10169 long timeout; 10170 synchronized (this) { 10171 synchronized (mPidsSelfLocked) { 10172 proc = mPidsSelfLocked.get(pid); 10173 } 10174 timeout = getInputDispatchingTimeoutLocked(proc); 10175 } 10176 10177 if (!inputDispatchingTimedOut(proc, null, null, aboveSystem, reason)) { 10178 return -1; 10179 } 10180 10181 return timeout; 10182 } 10183 10184 /** 10185 * Handle input dispatching timeouts. 10186 * Returns whether input dispatching should be aborted or not. 10187 */ 10188 public boolean inputDispatchingTimedOut(final ProcessRecord proc, 10189 final ActivityRecord activity, final ActivityRecord parent, 10190 final boolean aboveSystem, String reason) { 10191 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 10192 != PackageManager.PERMISSION_GRANTED) { 10193 throw new SecurityException("Requires permission " 10194 + android.Manifest.permission.FILTER_EVENTS); 10195 } 10196 10197 final String annotation; 10198 if (reason == null) { 10199 annotation = "Input dispatching timed out"; 10200 } else { 10201 annotation = "Input dispatching timed out (" + reason + ")"; 10202 } 10203 10204 if (proc != null) { 10205 synchronized (this) { 10206 if (proc.debugging) { 10207 return false; 10208 } 10209 10210 if (mDidDexOpt) { 10211 // Give more time since we were dexopting. 10212 mDidDexOpt = false; 10213 return false; 10214 } 10215 10216 if (proc.instrumentationClass != null) { 10217 Bundle info = new Bundle(); 10218 info.putString("shortMsg", "keyDispatchingTimedOut"); 10219 info.putString("longMsg", annotation); 10220 finishInstrumentationLocked(proc, Activity.RESULT_CANCELED, info); 10221 return true; 10222 } 10223 } 10224 mHandler.post(new Runnable() { 10225 @Override 10226 public void run() { 10227 appNotResponding(proc, activity, parent, aboveSystem, annotation); 10228 } 10229 }); 10230 } 10231 10232 return true; 10233 } 10234 10235 public Bundle getAssistContextExtras(int requestType) { 10236 enforceCallingPermission(android.Manifest.permission.GET_TOP_ACTIVITY_INFO, 10237 "getAssistContextExtras()"); 10238 PendingAssistExtras pae; 10239 Bundle extras = new Bundle(); 10240 synchronized (this) { 10241 ActivityRecord activity = getFocusedStack().mResumedActivity; 10242 if (activity == null) { 10243 Slog.w(TAG, "getAssistContextExtras failed: no resumed activity"); 10244 return null; 10245 } 10246 extras.putString(Intent.EXTRA_ASSIST_PACKAGE, activity.packageName); 10247 if (activity.app == null || activity.app.thread == null) { 10248 Slog.w(TAG, "getAssistContextExtras failed: no process for " + activity); 10249 return extras; 10250 } 10251 if (activity.app.pid == Binder.getCallingPid()) { 10252 Slog.w(TAG, "getAssistContextExtras failed: request process same as " + activity); 10253 return extras; 10254 } 10255 pae = new PendingAssistExtras(activity); 10256 try { 10257 activity.app.thread.requestAssistContextExtras(activity.appToken, pae, 10258 requestType); 10259 mPendingAssistExtras.add(pae); 10260 mHandler.postDelayed(pae, PENDING_ASSIST_EXTRAS_TIMEOUT); 10261 } catch (RemoteException e) { 10262 Slog.w(TAG, "getAssistContextExtras failed: crash calling " + activity); 10263 return extras; 10264 } 10265 } 10266 synchronized (pae) { 10267 while (!pae.haveResult) { 10268 try { 10269 pae.wait(); 10270 } catch (InterruptedException e) { 10271 } 10272 } 10273 if (pae.result != null) { 10274 extras.putBundle(Intent.EXTRA_ASSIST_CONTEXT, pae.result); 10275 } 10276 } 10277 synchronized (this) { 10278 mPendingAssistExtras.remove(pae); 10279 mHandler.removeCallbacks(pae); 10280 } 10281 return extras; 10282 } 10283 10284 public void reportAssistContextExtras(IBinder token, Bundle extras) { 10285 PendingAssistExtras pae = (PendingAssistExtras)token; 10286 synchronized (pae) { 10287 pae.result = extras; 10288 pae.haveResult = true; 10289 pae.notifyAll(); 10290 } 10291 } 10292 10293 public void registerProcessObserver(IProcessObserver observer) { 10294 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 10295 "registerProcessObserver()"); 10296 synchronized (this) { 10297 mProcessObservers.register(observer); 10298 } 10299 } 10300 10301 @Override 10302 public void unregisterProcessObserver(IProcessObserver observer) { 10303 synchronized (this) { 10304 mProcessObservers.unregister(observer); 10305 } 10306 } 10307 10308 @Override 10309 public boolean convertFromTranslucent(IBinder token) { 10310 final long origId = Binder.clearCallingIdentity(); 10311 try { 10312 synchronized (this) { 10313 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10314 if (r == null) { 10315 return false; 10316 } 10317 final boolean translucentChanged = r.changeWindowTranslucency(true); 10318 if (translucentChanged) { 10319 r.task.stack.releaseBackgroundResources(); 10320 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 10321 } 10322 mWindowManager.setAppFullscreen(token, true); 10323 return translucentChanged; 10324 } 10325 } finally { 10326 Binder.restoreCallingIdentity(origId); 10327 } 10328 } 10329 10330 @Override 10331 public boolean convertToTranslucent(IBinder token, ActivityOptions options) { 10332 final long origId = Binder.clearCallingIdentity(); 10333 try { 10334 synchronized (this) { 10335 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10336 if (r == null) { 10337 return false; 10338 } 10339 int index = r.task.mActivities.lastIndexOf(r); 10340 if (index > 0) { 10341 ActivityRecord under = r.task.mActivities.get(index - 1); 10342 under.returningOptions = options; 10343 } 10344 final boolean translucentChanged = r.changeWindowTranslucency(false); 10345 if (translucentChanged) { 10346 r.task.stack.convertToTranslucent(r); 10347 } 10348 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 10349 mWindowManager.setAppFullscreen(token, false); 10350 return translucentChanged; 10351 } 10352 } finally { 10353 Binder.restoreCallingIdentity(origId); 10354 } 10355 } 10356 10357 @Override 10358 public boolean requestVisibleBehind(IBinder token, boolean visible) { 10359 final long origId = Binder.clearCallingIdentity(); 10360 try { 10361 synchronized (this) { 10362 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10363 if (r != null) { 10364 return mStackSupervisor.requestVisibleBehindLocked(r, visible); 10365 } 10366 } 10367 return false; 10368 } finally { 10369 Binder.restoreCallingIdentity(origId); 10370 } 10371 } 10372 10373 @Override 10374 public boolean isBackgroundVisibleBehind(IBinder token) { 10375 final long origId = Binder.clearCallingIdentity(); 10376 try { 10377 synchronized (this) { 10378 final ActivityStack stack = ActivityRecord.getStackLocked(token); 10379 final boolean visible = stack == null ? false : stack.hasVisibleBehindActivity(); 10380 if (ActivityStackSupervisor.DEBUG_VISIBLE_BEHIND) Slog.d(TAG, 10381 "isBackgroundVisibleBehind: stack=" + stack + " visible=" + visible); 10382 return visible; 10383 } 10384 } finally { 10385 Binder.restoreCallingIdentity(origId); 10386 } 10387 } 10388 10389 @Override 10390 public ActivityOptions getActivityOptions(IBinder token) { 10391 final long origId = Binder.clearCallingIdentity(); 10392 try { 10393 synchronized (this) { 10394 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10395 if (r != null) { 10396 final ActivityOptions activityOptions = r.pendingOptions; 10397 r.pendingOptions = null; 10398 return activityOptions; 10399 } 10400 return null; 10401 } 10402 } finally { 10403 Binder.restoreCallingIdentity(origId); 10404 } 10405 } 10406 10407 @Override 10408 public void setImmersive(IBinder token, boolean immersive) { 10409 synchronized(this) { 10410 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 10411 if (r == null) { 10412 throw new IllegalArgumentException(); 10413 } 10414 r.immersive = immersive; 10415 10416 // update associated state if we're frontmost 10417 if (r == mFocusedActivity) { 10418 if (DEBUG_IMMERSIVE) { 10419 Slog.d(TAG, "Frontmost changed immersion: "+ r); 10420 } 10421 applyUpdateLockStateLocked(r); 10422 } 10423 } 10424 } 10425 10426 @Override 10427 public boolean isImmersive(IBinder token) { 10428 synchronized (this) { 10429 ActivityRecord r = ActivityRecord.isInStackLocked(token); 10430 if (r == null) { 10431 throw new IllegalArgumentException(); 10432 } 10433 return r.immersive; 10434 } 10435 } 10436 10437 public boolean isTopActivityImmersive() { 10438 enforceNotIsolatedCaller("startActivity"); 10439 synchronized (this) { 10440 ActivityRecord r = getFocusedStack().topRunningActivityLocked(null); 10441 return (r != null) ? r.immersive : false; 10442 } 10443 } 10444 10445 @Override 10446 public boolean isTopOfTask(IBinder token) { 10447 synchronized (this) { 10448 ActivityRecord r = ActivityRecord.isInStackLocked(token); 10449 if (r == null) { 10450 throw new IllegalArgumentException(); 10451 } 10452 return r.task.getTopActivity() == r; 10453 } 10454 } 10455 10456 public final void enterSafeMode() { 10457 synchronized(this) { 10458 // It only makes sense to do this before the system is ready 10459 // and started launching other packages. 10460 if (!mSystemReady) { 10461 try { 10462 AppGlobals.getPackageManager().enterSafeMode(); 10463 } catch (RemoteException e) { 10464 } 10465 } 10466 10467 mSafeMode = true; 10468 } 10469 } 10470 10471 public final void showSafeModeOverlay() { 10472 View v = LayoutInflater.from(mContext).inflate( 10473 com.android.internal.R.layout.safe_mode, null); 10474 WindowManager.LayoutParams lp = new WindowManager.LayoutParams(); 10475 lp.type = WindowManager.LayoutParams.TYPE_SECURE_SYSTEM_OVERLAY; 10476 lp.width = WindowManager.LayoutParams.WRAP_CONTENT; 10477 lp.height = WindowManager.LayoutParams.WRAP_CONTENT; 10478 lp.gravity = Gravity.BOTTOM | Gravity.START; 10479 lp.format = v.getBackground().getOpacity(); 10480 lp.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE 10481 | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE; 10482 lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; 10483 ((WindowManager)mContext.getSystemService( 10484 Context.WINDOW_SERVICE)).addView(v, lp); 10485 } 10486 10487 public void noteWakeupAlarm(IIntentSender sender, int sourceUid, String sourcePkg) { 10488 if (!(sender instanceof PendingIntentRecord)) { 10489 return; 10490 } 10491 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 10492 synchronized (stats) { 10493 if (mBatteryStatsService.isOnBattery()) { 10494 mBatteryStatsService.enforceCallingPermission(); 10495 PendingIntentRecord rec = (PendingIntentRecord)sender; 10496 int MY_UID = Binder.getCallingUid(); 10497 int uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid; 10498 BatteryStatsImpl.Uid.Pkg pkg = 10499 stats.getPackageStatsLocked(sourceUid >= 0 ? sourceUid : uid, 10500 sourcePkg != null ? sourcePkg : rec.key.packageName); 10501 pkg.incWakeupsLocked(); 10502 } 10503 } 10504 } 10505 10506 public boolean killPids(int[] pids, String pReason, boolean secure) { 10507 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10508 throw new SecurityException("killPids only available to the system"); 10509 } 10510 String reason = (pReason == null) ? "Unknown" : pReason; 10511 // XXX Note: don't acquire main activity lock here, because the window 10512 // manager calls in with its locks held. 10513 10514 boolean killed = false; 10515 synchronized (mPidsSelfLocked) { 10516 int[] types = new int[pids.length]; 10517 int worstType = 0; 10518 for (int i=0; i<pids.length; i++) { 10519 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 10520 if (proc != null) { 10521 int type = proc.setAdj; 10522 types[i] = type; 10523 if (type > worstType) { 10524 worstType = type; 10525 } 10526 } 10527 } 10528 10529 // If the worst oom_adj is somewhere in the cached proc LRU range, 10530 // then constrain it so we will kill all cached procs. 10531 if (worstType < ProcessList.CACHED_APP_MAX_ADJ 10532 && worstType > ProcessList.CACHED_APP_MIN_ADJ) { 10533 worstType = ProcessList.CACHED_APP_MIN_ADJ; 10534 } 10535 10536 // If this is not a secure call, don't let it kill processes that 10537 // are important. 10538 if (!secure && worstType < ProcessList.SERVICE_ADJ) { 10539 worstType = ProcessList.SERVICE_ADJ; 10540 } 10541 10542 Slog.w(TAG, "Killing processes " + reason + " at adjustment " + worstType); 10543 for (int i=0; i<pids.length; i++) { 10544 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 10545 if (proc == null) { 10546 continue; 10547 } 10548 int adj = proc.setAdj; 10549 if (adj >= worstType && !proc.killedByAm) { 10550 proc.kill(reason, true); 10551 killed = true; 10552 } 10553 } 10554 } 10555 return killed; 10556 } 10557 10558 @Override 10559 public void killUid(int uid, String reason) { 10560 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10561 throw new SecurityException("killUid only available to the system"); 10562 } 10563 synchronized (this) { 10564 killPackageProcessesLocked(null, UserHandle.getAppId(uid), UserHandle.getUserId(uid), 10565 ProcessList.FOREGROUND_APP_ADJ-1, false, true, true, false, 10566 reason != null ? reason : "kill uid"); 10567 } 10568 } 10569 10570 @Override 10571 public boolean killProcessesBelowForeground(String reason) { 10572 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10573 throw new SecurityException("killProcessesBelowForeground() only available to system"); 10574 } 10575 10576 return killProcessesBelowAdj(ProcessList.FOREGROUND_APP_ADJ, reason); 10577 } 10578 10579 private boolean killProcessesBelowAdj(int belowAdj, String reason) { 10580 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 10581 throw new SecurityException("killProcessesBelowAdj() only available to system"); 10582 } 10583 10584 boolean killed = false; 10585 synchronized (mPidsSelfLocked) { 10586 final int size = mPidsSelfLocked.size(); 10587 for (int i = 0; i < size; i++) { 10588 final int pid = mPidsSelfLocked.keyAt(i); 10589 final ProcessRecord proc = mPidsSelfLocked.valueAt(i); 10590 if (proc == null) continue; 10591 10592 final int adj = proc.setAdj; 10593 if (adj > belowAdj && !proc.killedByAm) { 10594 proc.kill(reason, true); 10595 killed = true; 10596 } 10597 } 10598 } 10599 return killed; 10600 } 10601 10602 @Override 10603 public void hang(final IBinder who, boolean allowRestart) { 10604 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 10605 != PackageManager.PERMISSION_GRANTED) { 10606 throw new SecurityException("Requires permission " 10607 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 10608 } 10609 10610 final IBinder.DeathRecipient death = new DeathRecipient() { 10611 @Override 10612 public void binderDied() { 10613 synchronized (this) { 10614 notifyAll(); 10615 } 10616 } 10617 }; 10618 10619 try { 10620 who.linkToDeath(death, 0); 10621 } catch (RemoteException e) { 10622 Slog.w(TAG, "hang: given caller IBinder is already dead."); 10623 return; 10624 } 10625 10626 synchronized (this) { 10627 Watchdog.getInstance().setAllowRestart(allowRestart); 10628 Slog.i(TAG, "Hanging system process at request of pid " + Binder.getCallingPid()); 10629 synchronized (death) { 10630 while (who.isBinderAlive()) { 10631 try { 10632 death.wait(); 10633 } catch (InterruptedException e) { 10634 } 10635 } 10636 } 10637 Watchdog.getInstance().setAllowRestart(true); 10638 } 10639 } 10640 10641 @Override 10642 public void restart() { 10643 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 10644 != PackageManager.PERMISSION_GRANTED) { 10645 throw new SecurityException("Requires permission " 10646 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 10647 } 10648 10649 Log.i(TAG, "Sending shutdown broadcast..."); 10650 10651 BroadcastReceiver br = new BroadcastReceiver() { 10652 @Override public void onReceive(Context context, Intent intent) { 10653 // Now the broadcast is done, finish up the low-level shutdown. 10654 Log.i(TAG, "Shutting down activity manager..."); 10655 shutdown(10000); 10656 Log.i(TAG, "Shutdown complete, restarting!"); 10657 Process.killProcess(Process.myPid()); 10658 System.exit(10); 10659 } 10660 }; 10661 10662 // First send the high-level shut down broadcast. 10663 Intent intent = new Intent(Intent.ACTION_SHUTDOWN); 10664 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 10665 intent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 10666 /* For now we are not doing a clean shutdown, because things seem to get unhappy. 10667 mContext.sendOrderedBroadcastAsUser(intent, 10668 UserHandle.ALL, null, br, mHandler, 0, null, null); 10669 */ 10670 br.onReceive(mContext, intent); 10671 } 10672 10673 private long getLowRamTimeSinceIdle(long now) { 10674 return mLowRamTimeSinceLastIdle + (mLowRamStartTime > 0 ? (now-mLowRamStartTime) : 0); 10675 } 10676 10677 @Override 10678 public void performIdleMaintenance() { 10679 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 10680 != PackageManager.PERMISSION_GRANTED) { 10681 throw new SecurityException("Requires permission " 10682 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 10683 } 10684 10685 synchronized (this) { 10686 final long now = SystemClock.uptimeMillis(); 10687 final long timeSinceLastIdle = now - mLastIdleTime; 10688 final long lowRamSinceLastIdle = getLowRamTimeSinceIdle(now); 10689 mLastIdleTime = now; 10690 mLowRamTimeSinceLastIdle = 0; 10691 if (mLowRamStartTime != 0) { 10692 mLowRamStartTime = now; 10693 } 10694 10695 StringBuilder sb = new StringBuilder(128); 10696 sb.append("Idle maintenance over "); 10697 TimeUtils.formatDuration(timeSinceLastIdle, sb); 10698 sb.append(" low RAM for "); 10699 TimeUtils.formatDuration(lowRamSinceLastIdle, sb); 10700 Slog.i(TAG, sb.toString()); 10701 10702 // If at least 1/3 of our time since the last idle period has been spent 10703 // with RAM low, then we want to kill processes. 10704 boolean doKilling = lowRamSinceLastIdle > (timeSinceLastIdle/3); 10705 10706 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 10707 ProcessRecord proc = mLruProcesses.get(i); 10708 if (proc.notCachedSinceIdle) { 10709 if (proc.setProcState > ActivityManager.PROCESS_STATE_TOP 10710 && proc.setProcState <= ActivityManager.PROCESS_STATE_SERVICE) { 10711 if (doKilling && proc.initialIdlePss != 0 10712 && proc.lastPss > ((proc.initialIdlePss*3)/2)) { 10713 proc.kill("idle maint (pss " + proc.lastPss 10714 + " from " + proc.initialIdlePss + ")", true); 10715 } 10716 } 10717 } else if (proc.setProcState < ActivityManager.PROCESS_STATE_HOME) { 10718 proc.notCachedSinceIdle = true; 10719 proc.initialIdlePss = 0; 10720 proc.nextPssTime = ProcessList.computeNextPssTime(proc.curProcState, true, 10721 isSleeping(), now); 10722 } 10723 } 10724 10725 mHandler.removeMessages(REQUEST_ALL_PSS_MSG); 10726 mHandler.sendEmptyMessageDelayed(REQUEST_ALL_PSS_MSG, 2*60*1000); 10727 } 10728 } 10729 10730 private void retrieveSettings() { 10731 final ContentResolver resolver = mContext.getContentResolver(); 10732 String debugApp = Settings.Global.getString( 10733 resolver, Settings.Global.DEBUG_APP); 10734 boolean waitForDebugger = Settings.Global.getInt( 10735 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 0) != 0; 10736 boolean alwaysFinishActivities = Settings.Global.getInt( 10737 resolver, Settings.Global.ALWAYS_FINISH_ACTIVITIES, 0) != 0; 10738 boolean forceRtl = Settings.Global.getInt( 10739 resolver, Settings.Global.DEVELOPMENT_FORCE_RTL, 0) != 0; 10740 // Transfer any global setting for forcing RTL layout, into a System Property 10741 SystemProperties.set(Settings.Global.DEVELOPMENT_FORCE_RTL, forceRtl ? "1":"0"); 10742 10743 Configuration configuration = new Configuration(); 10744 Settings.System.getConfiguration(resolver, configuration); 10745 if (forceRtl) { 10746 // This will take care of setting the correct layout direction flags 10747 configuration.setLayoutDirection(configuration.locale); 10748 } 10749 10750 synchronized (this) { 10751 mDebugApp = mOrigDebugApp = debugApp; 10752 mWaitForDebugger = mOrigWaitForDebugger = waitForDebugger; 10753 mAlwaysFinishActivities = alwaysFinishActivities; 10754 // This happens before any activities are started, so we can 10755 // change mConfiguration in-place. 10756 updateConfigurationLocked(configuration, null, false, true); 10757 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Initial config: " + mConfiguration); 10758 } 10759 } 10760 10761 /** Loads resources after the current configuration has been set. */ 10762 private void loadResourcesOnSystemReady() { 10763 final Resources res = mContext.getResources(); 10764 mHasRecents = res.getBoolean(com.android.internal.R.bool.config_hasRecents); 10765 mThumbnailWidth = res.getDimensionPixelSize(com.android.internal.R.dimen.thumbnail_width); 10766 mThumbnailHeight = res.getDimensionPixelSize(com.android.internal.R.dimen.thumbnail_height); 10767 } 10768 10769 public boolean testIsSystemReady() { 10770 // no need to synchronize(this) just to read & return the value 10771 return mSystemReady; 10772 } 10773 10774 private static File getCalledPreBootReceiversFile() { 10775 File dataDir = Environment.getDataDirectory(); 10776 File systemDir = new File(dataDir, "system"); 10777 File fname = new File(systemDir, CALLED_PRE_BOOTS_FILENAME); 10778 return fname; 10779 } 10780 10781 private static ArrayList<ComponentName> readLastDonePreBootReceivers() { 10782 ArrayList<ComponentName> lastDoneReceivers = new ArrayList<ComponentName>(); 10783 File file = getCalledPreBootReceiversFile(); 10784 FileInputStream fis = null; 10785 try { 10786 fis = new FileInputStream(file); 10787 DataInputStream dis = new DataInputStream(new BufferedInputStream(fis, 2048)); 10788 int fvers = dis.readInt(); 10789 if (fvers == LAST_PREBOOT_DELIVERED_FILE_VERSION) { 10790 String vers = dis.readUTF(); 10791 String codename = dis.readUTF(); 10792 String build = dis.readUTF(); 10793 if (android.os.Build.VERSION.RELEASE.equals(vers) 10794 && android.os.Build.VERSION.CODENAME.equals(codename) 10795 && android.os.Build.VERSION.INCREMENTAL.equals(build)) { 10796 int num = dis.readInt(); 10797 while (num > 0) { 10798 num--; 10799 String pkg = dis.readUTF(); 10800 String cls = dis.readUTF(); 10801 lastDoneReceivers.add(new ComponentName(pkg, cls)); 10802 } 10803 } 10804 } 10805 } catch (FileNotFoundException e) { 10806 } catch (IOException e) { 10807 Slog.w(TAG, "Failure reading last done pre-boot receivers", e); 10808 } finally { 10809 if (fis != null) { 10810 try { 10811 fis.close(); 10812 } catch (IOException e) { 10813 } 10814 } 10815 } 10816 return lastDoneReceivers; 10817 } 10818 10819 private static void writeLastDonePreBootReceivers(ArrayList<ComponentName> list) { 10820 File file = getCalledPreBootReceiversFile(); 10821 FileOutputStream fos = null; 10822 DataOutputStream dos = null; 10823 try { 10824 fos = new FileOutputStream(file); 10825 dos = new DataOutputStream(new BufferedOutputStream(fos, 2048)); 10826 dos.writeInt(LAST_PREBOOT_DELIVERED_FILE_VERSION); 10827 dos.writeUTF(android.os.Build.VERSION.RELEASE); 10828 dos.writeUTF(android.os.Build.VERSION.CODENAME); 10829 dos.writeUTF(android.os.Build.VERSION.INCREMENTAL); 10830 dos.writeInt(list.size()); 10831 for (int i=0; i<list.size(); i++) { 10832 dos.writeUTF(list.get(i).getPackageName()); 10833 dos.writeUTF(list.get(i).getClassName()); 10834 } 10835 } catch (IOException e) { 10836 Slog.w(TAG, "Failure writing last done pre-boot receivers", e); 10837 file.delete(); 10838 } finally { 10839 FileUtils.sync(fos); 10840 if (dos != null) { 10841 try { 10842 dos.close(); 10843 } catch (IOException e) { 10844 // TODO Auto-generated catch block 10845 e.printStackTrace(); 10846 } 10847 } 10848 } 10849 } 10850 10851 private boolean deliverPreBootCompleted(final Runnable onFinishCallback, 10852 ArrayList<ComponentName> doneReceivers, int userId) { 10853 boolean waitingUpdate = false; 10854 Intent intent = new Intent(Intent.ACTION_PRE_BOOT_COMPLETED); 10855 List<ResolveInfo> ris = null; 10856 try { 10857 ris = AppGlobals.getPackageManager().queryIntentReceivers( 10858 intent, null, 0, userId); 10859 } catch (RemoteException e) { 10860 } 10861 if (ris != null) { 10862 for (int i=ris.size()-1; i>=0; i--) { 10863 if ((ris.get(i).activityInfo.applicationInfo.flags 10864 &ApplicationInfo.FLAG_SYSTEM) == 0) { 10865 ris.remove(i); 10866 } 10867 } 10868 intent.addFlags(Intent.FLAG_RECEIVER_BOOT_UPGRADE); 10869 10870 // For User 0, load the version number. When delivering to a new user, deliver 10871 // to all receivers. 10872 if (userId == UserHandle.USER_OWNER) { 10873 ArrayList<ComponentName> lastDoneReceivers = readLastDonePreBootReceivers(); 10874 for (int i=0; i<ris.size(); i++) { 10875 ActivityInfo ai = ris.get(i).activityInfo; 10876 ComponentName comp = new ComponentName(ai.packageName, ai.name); 10877 if (lastDoneReceivers.contains(comp)) { 10878 // We already did the pre boot receiver for this app with the current 10879 // platform version, so don't do it again... 10880 ris.remove(i); 10881 i--; 10882 // ...however, do keep it as one that has been done, so we don't 10883 // forget about it when rewriting the file of last done receivers. 10884 doneReceivers.add(comp); 10885 } 10886 } 10887 } 10888 10889 // If primary user, send broadcast to all available users, else just to userId 10890 final int[] users = userId == UserHandle.USER_OWNER ? getUsersLocked() 10891 : new int[] { userId }; 10892 for (int i = 0; i < ris.size(); i++) { 10893 ActivityInfo ai = ris.get(i).activityInfo; 10894 ComponentName comp = new ComponentName(ai.packageName, ai.name); 10895 doneReceivers.add(comp); 10896 intent.setComponent(comp); 10897 for (int j=0; j<users.length; j++) { 10898 IIntentReceiver finisher = null; 10899 // On last receiver and user, set up a completion callback 10900 if (i == ris.size() - 1 && j == users.length - 1 && onFinishCallback != null) { 10901 finisher = new IIntentReceiver.Stub() { 10902 public void performReceive(Intent intent, int resultCode, 10903 String data, Bundle extras, boolean ordered, 10904 boolean sticky, int sendingUser) { 10905 // The raw IIntentReceiver interface is called 10906 // with the AM lock held, so redispatch to 10907 // execute our code without the lock. 10908 mHandler.post(onFinishCallback); 10909 } 10910 }; 10911 } 10912 Slog.i(TAG, "Sending system update to " + intent.getComponent() 10913 + " for user " + users[j]); 10914 broadcastIntentLocked(null, null, intent, null, finisher, 10915 0, null, null, null, AppOpsManager.OP_NONE, 10916 true, false, MY_PID, Process.SYSTEM_UID, 10917 users[j]); 10918 if (finisher != null) { 10919 waitingUpdate = true; 10920 } 10921 } 10922 } 10923 } 10924 10925 return waitingUpdate; 10926 } 10927 10928 public void systemReady(final Runnable goingCallback) { 10929 synchronized(this) { 10930 if (mSystemReady) { 10931 // If we're done calling all the receivers, run the next "boot phase" passed in 10932 // by the SystemServer 10933 if (goingCallback != null) { 10934 goingCallback.run(); 10935 } 10936 return; 10937 } 10938 10939 // Make sure we have the current profile info, since it is needed for 10940 // security checks. 10941 updateCurrentProfileIdsLocked(); 10942 10943 if (mRecentTasks == null) { 10944 mRecentTasks = mTaskPersister.restoreTasksLocked(); 10945 if (!mRecentTasks.isEmpty()) { 10946 mStackSupervisor.createStackForRestoredTaskHistory(mRecentTasks); 10947 } 10948 cleanupRecentTasksLocked(UserHandle.USER_ALL); 10949 mTaskPersister.startPersisting(); 10950 } 10951 10952 // Check to see if there are any update receivers to run. 10953 if (!mDidUpdate) { 10954 if (mWaitingUpdate) { 10955 return; 10956 } 10957 final ArrayList<ComponentName> doneReceivers = new ArrayList<ComponentName>(); 10958 mWaitingUpdate = deliverPreBootCompleted(new Runnable() { 10959 public void run() { 10960 synchronized (ActivityManagerService.this) { 10961 mDidUpdate = true; 10962 } 10963 writeLastDonePreBootReceivers(doneReceivers); 10964 showBootMessage(mContext.getText( 10965 R.string.android_upgrading_complete), 10966 false); 10967 systemReady(goingCallback); 10968 } 10969 }, doneReceivers, UserHandle.USER_OWNER); 10970 10971 if (mWaitingUpdate) { 10972 return; 10973 } 10974 mDidUpdate = true; 10975 } 10976 10977 mAppOpsService.systemReady(); 10978 mSystemReady = true; 10979 } 10980 10981 ArrayList<ProcessRecord> procsToKill = null; 10982 synchronized(mPidsSelfLocked) { 10983 for (int i=mPidsSelfLocked.size()-1; i>=0; i--) { 10984 ProcessRecord proc = mPidsSelfLocked.valueAt(i); 10985 if (!isAllowedWhileBooting(proc.info)){ 10986 if (procsToKill == null) { 10987 procsToKill = new ArrayList<ProcessRecord>(); 10988 } 10989 procsToKill.add(proc); 10990 } 10991 } 10992 } 10993 10994 synchronized(this) { 10995 if (procsToKill != null) { 10996 for (int i=procsToKill.size()-1; i>=0; i--) { 10997 ProcessRecord proc = procsToKill.get(i); 10998 Slog.i(TAG, "Removing system update proc: " + proc); 10999 removeProcessLocked(proc, true, false, "system update done"); 11000 } 11001 } 11002 11003 // Now that we have cleaned up any update processes, we 11004 // are ready to start launching real processes and know that 11005 // we won't trample on them any more. 11006 mProcessesReady = true; 11007 } 11008 11009 Slog.i(TAG, "System now ready"); 11010 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_AMS_READY, 11011 SystemClock.uptimeMillis()); 11012 11013 synchronized(this) { 11014 // Make sure we have no pre-ready processes sitting around. 11015 11016 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) { 11017 ResolveInfo ri = mContext.getPackageManager() 11018 .resolveActivity(new Intent(Intent.ACTION_FACTORY_TEST), 11019 STOCK_PM_FLAGS); 11020 CharSequence errorMsg = null; 11021 if (ri != null) { 11022 ActivityInfo ai = ri.activityInfo; 11023 ApplicationInfo app = ai.applicationInfo; 11024 if ((app.flags&ApplicationInfo.FLAG_SYSTEM) != 0) { 11025 mTopAction = Intent.ACTION_FACTORY_TEST; 11026 mTopData = null; 11027 mTopComponent = new ComponentName(app.packageName, 11028 ai.name); 11029 } else { 11030 errorMsg = mContext.getResources().getText( 11031 com.android.internal.R.string.factorytest_not_system); 11032 } 11033 } else { 11034 errorMsg = mContext.getResources().getText( 11035 com.android.internal.R.string.factorytest_no_action); 11036 } 11037 if (errorMsg != null) { 11038 mTopAction = null; 11039 mTopData = null; 11040 mTopComponent = null; 11041 Message msg = Message.obtain(); 11042 msg.what = SHOW_FACTORY_ERROR_MSG; 11043 msg.getData().putCharSequence("msg", errorMsg); 11044 mHandler.sendMessage(msg); 11045 } 11046 } 11047 } 11048 11049 retrieveSettings(); 11050 loadResourcesOnSystemReady(); 11051 11052 synchronized (this) { 11053 readGrantedUriPermissionsLocked(); 11054 } 11055 11056 if (goingCallback != null) goingCallback.run(); 11057 11058 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 11059 Integer.toString(mCurrentUserId), mCurrentUserId); 11060 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 11061 Integer.toString(mCurrentUserId), mCurrentUserId); 11062 mSystemServiceManager.startUser(mCurrentUserId); 11063 11064 synchronized (this) { 11065 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 11066 try { 11067 List apps = AppGlobals.getPackageManager(). 11068 getPersistentApplications(STOCK_PM_FLAGS); 11069 if (apps != null) { 11070 int N = apps.size(); 11071 int i; 11072 for (i=0; i<N; i++) { 11073 ApplicationInfo info 11074 = (ApplicationInfo)apps.get(i); 11075 if (info != null && 11076 !info.packageName.equals("android")) { 11077 addAppLocked(info, false, null /* ABI override */); 11078 } 11079 } 11080 } 11081 } catch (RemoteException ex) { 11082 // pm is in same process, this will never happen. 11083 } 11084 } 11085 11086 // Start up initial activity. 11087 mBooting = true; 11088 11089 try { 11090 if (AppGlobals.getPackageManager().hasSystemUidErrors()) { 11091 Message msg = Message.obtain(); 11092 msg.what = SHOW_UID_ERROR_MSG; 11093 mHandler.sendMessage(msg); 11094 } 11095 } catch (RemoteException e) { 11096 } 11097 11098 long ident = Binder.clearCallingIdentity(); 11099 try { 11100 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 11101 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 11102 | Intent.FLAG_RECEIVER_FOREGROUND); 11103 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 11104 broadcastIntentLocked(null, null, intent, 11105 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 11106 false, false, MY_PID, Process.SYSTEM_UID, mCurrentUserId); 11107 intent = new Intent(Intent.ACTION_USER_STARTING); 11108 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 11109 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 11110 broadcastIntentLocked(null, null, intent, 11111 null, new IIntentReceiver.Stub() { 11112 @Override 11113 public void performReceive(Intent intent, int resultCode, String data, 11114 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 11115 throws RemoteException { 11116 } 11117 }, 0, null, null, 11118 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 11119 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 11120 } catch (Throwable t) { 11121 Slog.wtf(TAG, "Failed sending first user broadcasts", t); 11122 } finally { 11123 Binder.restoreCallingIdentity(ident); 11124 } 11125 mStackSupervisor.resumeTopActivitiesLocked(); 11126 sendUserSwitchBroadcastsLocked(-1, mCurrentUserId); 11127 } 11128 } 11129 11130 private boolean makeAppCrashingLocked(ProcessRecord app, 11131 String shortMsg, String longMsg, String stackTrace) { 11132 app.crashing = true; 11133 app.crashingReport = generateProcessError(app, 11134 ActivityManager.ProcessErrorStateInfo.CRASHED, null, shortMsg, longMsg, stackTrace); 11135 startAppProblemLocked(app); 11136 app.stopFreezingAllLocked(); 11137 return handleAppCrashLocked(app, shortMsg, longMsg, stackTrace); 11138 } 11139 11140 private void makeAppNotRespondingLocked(ProcessRecord app, 11141 String activity, String shortMsg, String longMsg) { 11142 app.notResponding = true; 11143 app.notRespondingReport = generateProcessError(app, 11144 ActivityManager.ProcessErrorStateInfo.NOT_RESPONDING, 11145 activity, shortMsg, longMsg, null); 11146 startAppProblemLocked(app); 11147 app.stopFreezingAllLocked(); 11148 } 11149 11150 /** 11151 * Generate a process error record, suitable for attachment to a ProcessRecord. 11152 * 11153 * @param app The ProcessRecord in which the error occurred. 11154 * @param condition Crashing, Application Not Responding, etc. Values are defined in 11155 * ActivityManager.AppErrorStateInfo 11156 * @param activity The activity associated with the crash, if known. 11157 * @param shortMsg Short message describing the crash. 11158 * @param longMsg Long message describing the crash. 11159 * @param stackTrace Full crash stack trace, may be null. 11160 * 11161 * @return Returns a fully-formed AppErrorStateInfo record. 11162 */ 11163 private ActivityManager.ProcessErrorStateInfo generateProcessError(ProcessRecord app, 11164 int condition, String activity, String shortMsg, String longMsg, String stackTrace) { 11165 ActivityManager.ProcessErrorStateInfo report = new ActivityManager.ProcessErrorStateInfo(); 11166 11167 report.condition = condition; 11168 report.processName = app.processName; 11169 report.pid = app.pid; 11170 report.uid = app.info.uid; 11171 report.tag = activity; 11172 report.shortMsg = shortMsg; 11173 report.longMsg = longMsg; 11174 report.stackTrace = stackTrace; 11175 11176 return report; 11177 } 11178 11179 void killAppAtUsersRequest(ProcessRecord app, Dialog fromDialog) { 11180 synchronized (this) { 11181 app.crashing = false; 11182 app.crashingReport = null; 11183 app.notResponding = false; 11184 app.notRespondingReport = null; 11185 if (app.anrDialog == fromDialog) { 11186 app.anrDialog = null; 11187 } 11188 if (app.waitDialog == fromDialog) { 11189 app.waitDialog = null; 11190 } 11191 if (app.pid > 0 && app.pid != MY_PID) { 11192 handleAppCrashLocked(app, null, null, null); 11193 app.kill("user request after error", true); 11194 } 11195 } 11196 } 11197 11198 private boolean handleAppCrashLocked(ProcessRecord app, String shortMsg, String longMsg, 11199 String stackTrace) { 11200 long now = SystemClock.uptimeMillis(); 11201 11202 Long crashTime; 11203 if (!app.isolated) { 11204 crashTime = mProcessCrashTimes.get(app.info.processName, app.uid); 11205 } else { 11206 crashTime = null; 11207 } 11208 if (crashTime != null && now < crashTime+ProcessList.MIN_CRASH_INTERVAL) { 11209 // This process loses! 11210 Slog.w(TAG, "Process " + app.info.processName 11211 + " has crashed too many times: killing!"); 11212 EventLog.writeEvent(EventLogTags.AM_PROCESS_CRASHED_TOO_MUCH, 11213 app.userId, app.info.processName, app.uid); 11214 mStackSupervisor.handleAppCrashLocked(app); 11215 if (!app.persistent) { 11216 // We don't want to start this process again until the user 11217 // explicitly does so... but for persistent process, we really 11218 // need to keep it running. If a persistent process is actually 11219 // repeatedly crashing, then badness for everyone. 11220 EventLog.writeEvent(EventLogTags.AM_PROC_BAD, app.userId, app.uid, 11221 app.info.processName); 11222 if (!app.isolated) { 11223 // XXX We don't have a way to mark isolated processes 11224 // as bad, since they don't have a peristent identity. 11225 mBadProcesses.put(app.info.processName, app.uid, 11226 new BadProcessInfo(now, shortMsg, longMsg, stackTrace)); 11227 mProcessCrashTimes.remove(app.info.processName, app.uid); 11228 } 11229 app.bad = true; 11230 app.removed = true; 11231 // Don't let services in this process be restarted and potentially 11232 // annoy the user repeatedly. Unless it is persistent, since those 11233 // processes run critical code. 11234 removeProcessLocked(app, false, false, "crash"); 11235 mStackSupervisor.resumeTopActivitiesLocked(); 11236 return false; 11237 } 11238 mStackSupervisor.resumeTopActivitiesLocked(); 11239 } else { 11240 mStackSupervisor.finishTopRunningActivityLocked(app); 11241 } 11242 11243 // Bump up the crash count of any services currently running in the proc. 11244 for (int i=app.services.size()-1; i>=0; i--) { 11245 // Any services running in the application need to be placed 11246 // back in the pending list. 11247 ServiceRecord sr = app.services.valueAt(i); 11248 sr.crashCount++; 11249 } 11250 11251 // If the crashing process is what we consider to be the "home process" and it has been 11252 // replaced by a third-party app, clear the package preferred activities from packages 11253 // with a home activity running in the process to prevent a repeatedly crashing app 11254 // from blocking the user to manually clear the list. 11255 final ArrayList<ActivityRecord> activities = app.activities; 11256 if (app == mHomeProcess && activities.size() > 0 11257 && (mHomeProcess.info.flags & ApplicationInfo.FLAG_SYSTEM) == 0) { 11258 for (int activityNdx = activities.size() - 1; activityNdx >= 0; --activityNdx) { 11259 final ActivityRecord r = activities.get(activityNdx); 11260 if (r.isHomeActivity()) { 11261 Log.i(TAG, "Clearing package preferred activities from " + r.packageName); 11262 try { 11263 ActivityThread.getPackageManager() 11264 .clearPackagePreferredActivities(r.packageName); 11265 } catch (RemoteException c) { 11266 // pm is in same process, this will never happen. 11267 } 11268 } 11269 } 11270 } 11271 11272 if (!app.isolated) { 11273 // XXX Can't keep track of crash times for isolated processes, 11274 // because they don't have a perisistent identity. 11275 mProcessCrashTimes.put(app.info.processName, app.uid, now); 11276 } 11277 11278 if (app.crashHandler != null) mHandler.post(app.crashHandler); 11279 return true; 11280 } 11281 11282 void startAppProblemLocked(ProcessRecord app) { 11283 // If this app is not running under the current user, then we 11284 // can't give it a report button because that would require 11285 // launching the report UI under a different user. 11286 app.errorReportReceiver = null; 11287 11288 for (int userId : mCurrentProfileIds) { 11289 if (app.userId == userId) { 11290 app.errorReportReceiver = ApplicationErrorReport.getErrorReportReceiver( 11291 mContext, app.info.packageName, app.info.flags); 11292 } 11293 } 11294 skipCurrentReceiverLocked(app); 11295 } 11296 11297 void skipCurrentReceiverLocked(ProcessRecord app) { 11298 for (BroadcastQueue queue : mBroadcastQueues) { 11299 queue.skipCurrentReceiverLocked(app); 11300 } 11301 } 11302 11303 /** 11304 * Used by {@link com.android.internal.os.RuntimeInit} to report when an application crashes. 11305 * The application process will exit immediately after this call returns. 11306 * @param app object of the crashing app, null for the system server 11307 * @param crashInfo describing the exception 11308 */ 11309 public void handleApplicationCrash(IBinder app, ApplicationErrorReport.CrashInfo crashInfo) { 11310 ProcessRecord r = findAppProcess(app, "Crash"); 11311 final String processName = app == null ? "system_server" 11312 : (r == null ? "unknown" : r.processName); 11313 11314 handleApplicationCrashInner("crash", r, processName, crashInfo); 11315 } 11316 11317 /* Native crash reporting uses this inner version because it needs to be somewhat 11318 * decoupled from the AM-managed cleanup lifecycle 11319 */ 11320 void handleApplicationCrashInner(String eventType, ProcessRecord r, String processName, 11321 ApplicationErrorReport.CrashInfo crashInfo) { 11322 EventLog.writeEvent(EventLogTags.AM_CRASH, Binder.getCallingPid(), 11323 UserHandle.getUserId(Binder.getCallingUid()), processName, 11324 r == null ? -1 : r.info.flags, 11325 crashInfo.exceptionClassName, 11326 crashInfo.exceptionMessage, 11327 crashInfo.throwFileName, 11328 crashInfo.throwLineNumber); 11329 11330 addErrorToDropBox(eventType, r, processName, null, null, null, null, null, crashInfo); 11331 11332 crashApplication(r, crashInfo); 11333 } 11334 11335 public void handleApplicationStrictModeViolation( 11336 IBinder app, 11337 int violationMask, 11338 StrictMode.ViolationInfo info) { 11339 ProcessRecord r = findAppProcess(app, "StrictMode"); 11340 if (r == null) { 11341 return; 11342 } 11343 11344 if ((violationMask & StrictMode.PENALTY_DROPBOX) != 0) { 11345 Integer stackFingerprint = info.hashCode(); 11346 boolean logIt = true; 11347 synchronized (mAlreadyLoggedViolatedStacks) { 11348 if (mAlreadyLoggedViolatedStacks.contains(stackFingerprint)) { 11349 logIt = false; 11350 // TODO: sub-sample into EventLog for these, with 11351 // the info.durationMillis? Then we'd get 11352 // the relative pain numbers, without logging all 11353 // the stack traces repeatedly. We'd want to do 11354 // likewise in the client code, which also does 11355 // dup suppression, before the Binder call. 11356 } else { 11357 if (mAlreadyLoggedViolatedStacks.size() >= MAX_DUP_SUPPRESSED_STACKS) { 11358 mAlreadyLoggedViolatedStacks.clear(); 11359 } 11360 mAlreadyLoggedViolatedStacks.add(stackFingerprint); 11361 } 11362 } 11363 if (logIt) { 11364 logStrictModeViolationToDropBox(r, info); 11365 } 11366 } 11367 11368 if ((violationMask & StrictMode.PENALTY_DIALOG) != 0) { 11369 AppErrorResult result = new AppErrorResult(); 11370 synchronized (this) { 11371 final long origId = Binder.clearCallingIdentity(); 11372 11373 Message msg = Message.obtain(); 11374 msg.what = SHOW_STRICT_MODE_VIOLATION_MSG; 11375 HashMap<String, Object> data = new HashMap<String, Object>(); 11376 data.put("result", result); 11377 data.put("app", r); 11378 data.put("violationMask", violationMask); 11379 data.put("info", info); 11380 msg.obj = data; 11381 mHandler.sendMessage(msg); 11382 11383 Binder.restoreCallingIdentity(origId); 11384 } 11385 int res = result.get(); 11386 Slog.w(TAG, "handleApplicationStrictModeViolation; res=" + res); 11387 } 11388 } 11389 11390 // Depending on the policy in effect, there could be a bunch of 11391 // these in quick succession so we try to batch these together to 11392 // minimize disk writes, number of dropbox entries, and maximize 11393 // compression, by having more fewer, larger records. 11394 private void logStrictModeViolationToDropBox( 11395 ProcessRecord process, 11396 StrictMode.ViolationInfo info) { 11397 if (info == null) { 11398 return; 11399 } 11400 final boolean isSystemApp = process == null || 11401 (process.info.flags & (ApplicationInfo.FLAG_SYSTEM | 11402 ApplicationInfo.FLAG_UPDATED_SYSTEM_APP)) != 0; 11403 final String processName = process == null ? "unknown" : process.processName; 11404 final String dropboxTag = isSystemApp ? "system_app_strictmode" : "data_app_strictmode"; 11405 final DropBoxManager dbox = (DropBoxManager) 11406 mContext.getSystemService(Context.DROPBOX_SERVICE); 11407 11408 // Exit early if the dropbox isn't configured to accept this report type. 11409 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 11410 11411 boolean bufferWasEmpty; 11412 boolean needsFlush; 11413 final StringBuilder sb = isSystemApp ? mStrictModeBuffer : new StringBuilder(1024); 11414 synchronized (sb) { 11415 bufferWasEmpty = sb.length() == 0; 11416 appendDropBoxProcessHeaders(process, processName, sb); 11417 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 11418 sb.append("System-App: ").append(isSystemApp).append("\n"); 11419 sb.append("Uptime-Millis: ").append(info.violationUptimeMillis).append("\n"); 11420 if (info.violationNumThisLoop != 0) { 11421 sb.append("Loop-Violation-Number: ").append(info.violationNumThisLoop).append("\n"); 11422 } 11423 if (info.numAnimationsRunning != 0) { 11424 sb.append("Animations-Running: ").append(info.numAnimationsRunning).append("\n"); 11425 } 11426 if (info.broadcastIntentAction != null) { 11427 sb.append("Broadcast-Intent-Action: ").append(info.broadcastIntentAction).append("\n"); 11428 } 11429 if (info.durationMillis != -1) { 11430 sb.append("Duration-Millis: ").append(info.durationMillis).append("\n"); 11431 } 11432 if (info.numInstances != -1) { 11433 sb.append("Instance-Count: ").append(info.numInstances).append("\n"); 11434 } 11435 if (info.tags != null) { 11436 for (String tag : info.tags) { 11437 sb.append("Span-Tag: ").append(tag).append("\n"); 11438 } 11439 } 11440 sb.append("\n"); 11441 if (info.crashInfo != null && info.crashInfo.stackTrace != null) { 11442 sb.append(info.crashInfo.stackTrace); 11443 } 11444 sb.append("\n"); 11445 11446 // Only buffer up to ~64k. Various logging bits truncate 11447 // things at 128k. 11448 needsFlush = (sb.length() > 64 * 1024); 11449 } 11450 11451 // Flush immediately if the buffer's grown too large, or this 11452 // is a non-system app. Non-system apps are isolated with a 11453 // different tag & policy and not batched. 11454 // 11455 // Batching is useful during internal testing with 11456 // StrictMode settings turned up high. Without batching, 11457 // thousands of separate files could be created on boot. 11458 if (!isSystemApp || needsFlush) { 11459 new Thread("Error dump: " + dropboxTag) { 11460 @Override 11461 public void run() { 11462 String report; 11463 synchronized (sb) { 11464 report = sb.toString(); 11465 sb.delete(0, sb.length()); 11466 sb.trimToSize(); 11467 } 11468 if (report.length() != 0) { 11469 dbox.addText(dropboxTag, report); 11470 } 11471 } 11472 }.start(); 11473 return; 11474 } 11475 11476 // System app batching: 11477 if (!bufferWasEmpty) { 11478 // An existing dropbox-writing thread is outstanding, so 11479 // we don't need to start it up. The existing thread will 11480 // catch the buffer appends we just did. 11481 return; 11482 } 11483 11484 // Worker thread to both batch writes and to avoid blocking the caller on I/O. 11485 // (After this point, we shouldn't access AMS internal data structures.) 11486 new Thread("Error dump: " + dropboxTag) { 11487 @Override 11488 public void run() { 11489 // 5 second sleep to let stacks arrive and be batched together 11490 try { 11491 Thread.sleep(5000); // 5 seconds 11492 } catch (InterruptedException e) {} 11493 11494 String errorReport; 11495 synchronized (mStrictModeBuffer) { 11496 errorReport = mStrictModeBuffer.toString(); 11497 if (errorReport.length() == 0) { 11498 return; 11499 } 11500 mStrictModeBuffer.delete(0, mStrictModeBuffer.length()); 11501 mStrictModeBuffer.trimToSize(); 11502 } 11503 dbox.addText(dropboxTag, errorReport); 11504 } 11505 }.start(); 11506 } 11507 11508 /** 11509 * Used by {@link Log} via {@link com.android.internal.os.RuntimeInit} to report serious errors. 11510 * @param app object of the crashing app, null for the system server 11511 * @param tag reported by the caller 11512 * @param system whether this wtf is coming from the system 11513 * @param crashInfo describing the context of the error 11514 * @return true if the process should exit immediately (WTF is fatal) 11515 */ 11516 public boolean handleApplicationWtf(IBinder app, final String tag, boolean system, 11517 final ApplicationErrorReport.CrashInfo crashInfo) { 11518 final ProcessRecord r = findAppProcess(app, "WTF"); 11519 final String processName = app == null ? "system_server" 11520 : (r == null ? "unknown" : r.processName); 11521 11522 EventLog.writeEvent(EventLogTags.AM_WTF, 11523 UserHandle.getUserId(Binder.getCallingUid()), Binder.getCallingPid(), 11524 processName, 11525 r == null ? -1 : r.info.flags, 11526 tag, crashInfo.exceptionMessage); 11527 11528 if (system) { 11529 // If this is coming from the system, we could very well have low-level 11530 // system locks held, so we want to do this all asynchronously. And we 11531 // never want this to become fatal, so there is that too. 11532 mHandler.post(new Runnable() { 11533 @Override public void run() { 11534 addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, 11535 crashInfo); 11536 } 11537 }); 11538 return false; 11539 } 11540 11541 addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, crashInfo); 11542 11543 if (r != null && r.pid != Process.myPid() && 11544 Settings.Global.getInt(mContext.getContentResolver(), 11545 Settings.Global.WTF_IS_FATAL, 0) != 0) { 11546 crashApplication(r, crashInfo); 11547 return true; 11548 } else { 11549 return false; 11550 } 11551 } 11552 11553 /** 11554 * @param app object of some object (as stored in {@link com.android.internal.os.RuntimeInit}) 11555 * @return the corresponding {@link ProcessRecord} object, or null if none could be found 11556 */ 11557 private ProcessRecord findAppProcess(IBinder app, String reason) { 11558 if (app == null) { 11559 return null; 11560 } 11561 11562 synchronized (this) { 11563 final int NP = mProcessNames.getMap().size(); 11564 for (int ip=0; ip<NP; ip++) { 11565 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 11566 final int NA = apps.size(); 11567 for (int ia=0; ia<NA; ia++) { 11568 ProcessRecord p = apps.valueAt(ia); 11569 if (p.thread != null && p.thread.asBinder() == app) { 11570 return p; 11571 } 11572 } 11573 } 11574 11575 Slog.w(TAG, "Can't find mystery application for " + reason 11576 + " from pid=" + Binder.getCallingPid() 11577 + " uid=" + Binder.getCallingUid() + ": " + app); 11578 return null; 11579 } 11580 } 11581 11582 /** 11583 * Utility function for addErrorToDropBox and handleStrictModeViolation's logging 11584 * to append various headers to the dropbox log text. 11585 */ 11586 private void appendDropBoxProcessHeaders(ProcessRecord process, String processName, 11587 StringBuilder sb) { 11588 // Watchdog thread ends up invoking this function (with 11589 // a null ProcessRecord) to add the stack file to dropbox. 11590 // Do not acquire a lock on this (am) in such cases, as it 11591 // could cause a potential deadlock, if and when watchdog 11592 // is invoked due to unavailability of lock on am and it 11593 // would prevent watchdog from killing system_server. 11594 if (process == null) { 11595 sb.append("Process: ").append(processName).append("\n"); 11596 return; 11597 } 11598 // Note: ProcessRecord 'process' is guarded by the service 11599 // instance. (notably process.pkgList, which could otherwise change 11600 // concurrently during execution of this method) 11601 synchronized (this) { 11602 sb.append("Process: ").append(processName).append("\n"); 11603 int flags = process.info.flags; 11604 IPackageManager pm = AppGlobals.getPackageManager(); 11605 sb.append("Flags: 0x").append(Integer.toString(flags, 16)).append("\n"); 11606 for (int ip=0; ip<process.pkgList.size(); ip++) { 11607 String pkg = process.pkgList.keyAt(ip); 11608 sb.append("Package: ").append(pkg); 11609 try { 11610 PackageInfo pi = pm.getPackageInfo(pkg, 0, UserHandle.getCallingUserId()); 11611 if (pi != null) { 11612 sb.append(" v").append(pi.versionCode); 11613 if (pi.versionName != null) { 11614 sb.append(" (").append(pi.versionName).append(")"); 11615 } 11616 } 11617 } catch (RemoteException e) { 11618 Slog.e(TAG, "Error getting package info: " + pkg, e); 11619 } 11620 sb.append("\n"); 11621 } 11622 } 11623 } 11624 11625 private static String processClass(ProcessRecord process) { 11626 if (process == null || process.pid == MY_PID) { 11627 return "system_server"; 11628 } else if ((process.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 11629 return "system_app"; 11630 } else { 11631 return "data_app"; 11632 } 11633 } 11634 11635 /** 11636 * Write a description of an error (crash, WTF, ANR) to the drop box. 11637 * @param eventType to include in the drop box tag ("crash", "wtf", etc.) 11638 * @param process which caused the error, null means the system server 11639 * @param activity which triggered the error, null if unknown 11640 * @param parent activity related to the error, null if unknown 11641 * @param subject line related to the error, null if absent 11642 * @param report in long form describing the error, null if absent 11643 * @param logFile to include in the report, null if none 11644 * @param crashInfo giving an application stack trace, null if absent 11645 */ 11646 public void addErrorToDropBox(String eventType, 11647 ProcessRecord process, String processName, ActivityRecord activity, 11648 ActivityRecord parent, String subject, 11649 final String report, final File logFile, 11650 final ApplicationErrorReport.CrashInfo crashInfo) { 11651 // NOTE -- this must never acquire the ActivityManagerService lock, 11652 // otherwise the watchdog may be prevented from resetting the system. 11653 11654 final String dropboxTag = processClass(process) + "_" + eventType; 11655 final DropBoxManager dbox = (DropBoxManager) 11656 mContext.getSystemService(Context.DROPBOX_SERVICE); 11657 11658 // Exit early if the dropbox isn't configured to accept this report type. 11659 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 11660 11661 final StringBuilder sb = new StringBuilder(1024); 11662 appendDropBoxProcessHeaders(process, processName, sb); 11663 if (activity != null) { 11664 sb.append("Activity: ").append(activity.shortComponentName).append("\n"); 11665 } 11666 if (parent != null && parent.app != null && parent.app.pid != process.pid) { 11667 sb.append("Parent-Process: ").append(parent.app.processName).append("\n"); 11668 } 11669 if (parent != null && parent != activity) { 11670 sb.append("Parent-Activity: ").append(parent.shortComponentName).append("\n"); 11671 } 11672 if (subject != null) { 11673 sb.append("Subject: ").append(subject).append("\n"); 11674 } 11675 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 11676 if (Debug.isDebuggerConnected()) { 11677 sb.append("Debugger: Connected\n"); 11678 } 11679 sb.append("\n"); 11680 11681 // Do the rest in a worker thread to avoid blocking the caller on I/O 11682 // (After this point, we shouldn't access AMS internal data structures.) 11683 Thread worker = new Thread("Error dump: " + dropboxTag) { 11684 @Override 11685 public void run() { 11686 if (report != null) { 11687 sb.append(report); 11688 } 11689 if (logFile != null) { 11690 try { 11691 sb.append(FileUtils.readTextFile(logFile, DROPBOX_MAX_SIZE, 11692 "\n\n[[TRUNCATED]]")); 11693 } catch (IOException e) { 11694 Slog.e(TAG, "Error reading " + logFile, e); 11695 } 11696 } 11697 if (crashInfo != null && crashInfo.stackTrace != null) { 11698 sb.append(crashInfo.stackTrace); 11699 } 11700 11701 String setting = Settings.Global.ERROR_LOGCAT_PREFIX + dropboxTag; 11702 int lines = Settings.Global.getInt(mContext.getContentResolver(), setting, 0); 11703 if (lines > 0) { 11704 sb.append("\n"); 11705 11706 // Merge several logcat streams, and take the last N lines 11707 InputStreamReader input = null; 11708 try { 11709 java.lang.Process logcat = new ProcessBuilder("/system/bin/logcat", 11710 "-v", "time", "-b", "events", "-b", "system", "-b", "main", 11711 "-b", "crash", 11712 "-t", String.valueOf(lines)).redirectErrorStream(true).start(); 11713 11714 try { logcat.getOutputStream().close(); } catch (IOException e) {} 11715 try { logcat.getErrorStream().close(); } catch (IOException e) {} 11716 input = new InputStreamReader(logcat.getInputStream()); 11717 11718 int num; 11719 char[] buf = new char[8192]; 11720 while ((num = input.read(buf)) > 0) sb.append(buf, 0, num); 11721 } catch (IOException e) { 11722 Slog.e(TAG, "Error running logcat", e); 11723 } finally { 11724 if (input != null) try { input.close(); } catch (IOException e) {} 11725 } 11726 } 11727 11728 dbox.addText(dropboxTag, sb.toString()); 11729 } 11730 }; 11731 11732 if (process == null) { 11733 // If process is null, we are being called from some internal code 11734 // and may be about to die -- run this synchronously. 11735 worker.run(); 11736 } else { 11737 worker.start(); 11738 } 11739 } 11740 11741 /** 11742 * Bring up the "unexpected error" dialog box for a crashing app. 11743 * Deal with edge cases (intercepts from instrumented applications, 11744 * ActivityController, error intent receivers, that sort of thing). 11745 * @param r the application crashing 11746 * @param crashInfo describing the failure 11747 */ 11748 private void crashApplication(ProcessRecord r, ApplicationErrorReport.CrashInfo crashInfo) { 11749 long timeMillis = System.currentTimeMillis(); 11750 String shortMsg = crashInfo.exceptionClassName; 11751 String longMsg = crashInfo.exceptionMessage; 11752 String stackTrace = crashInfo.stackTrace; 11753 if (shortMsg != null && longMsg != null) { 11754 longMsg = shortMsg + ": " + longMsg; 11755 } else if (shortMsg != null) { 11756 longMsg = shortMsg; 11757 } 11758 11759 AppErrorResult result = new AppErrorResult(); 11760 synchronized (this) { 11761 if (mController != null) { 11762 try { 11763 String name = r != null ? r.processName : null; 11764 int pid = r != null ? r.pid : Binder.getCallingPid(); 11765 int uid = r != null ? r.info.uid : Binder.getCallingUid(); 11766 if (!mController.appCrashed(name, pid, 11767 shortMsg, longMsg, timeMillis, crashInfo.stackTrace)) { 11768 if ("1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")) 11769 && "Native crash".equals(crashInfo.exceptionClassName)) { 11770 Slog.w(TAG, "Skip killing native crashed app " + name 11771 + "(" + pid + ") during testing"); 11772 } else { 11773 Slog.w(TAG, "Force-killing crashed app " + name 11774 + " at watcher's request"); 11775 if (r != null) { 11776 r.kill("crash", true); 11777 } else { 11778 // Huh. 11779 Process.killProcess(pid); 11780 Process.killProcessGroup(uid, pid); 11781 } 11782 } 11783 return; 11784 } 11785 } catch (RemoteException e) { 11786 mController = null; 11787 Watchdog.getInstance().setActivityController(null); 11788 } 11789 } 11790 11791 final long origId = Binder.clearCallingIdentity(); 11792 11793 // If this process is running instrumentation, finish it. 11794 if (r != null && r.instrumentationClass != null) { 11795 Slog.w(TAG, "Error in app " + r.processName 11796 + " running instrumentation " + r.instrumentationClass + ":"); 11797 if (shortMsg != null) Slog.w(TAG, " " + shortMsg); 11798 if (longMsg != null) Slog.w(TAG, " " + longMsg); 11799 Bundle info = new Bundle(); 11800 info.putString("shortMsg", shortMsg); 11801 info.putString("longMsg", longMsg); 11802 finishInstrumentationLocked(r, Activity.RESULT_CANCELED, info); 11803 Binder.restoreCallingIdentity(origId); 11804 return; 11805 } 11806 11807 // If we can't identify the process or it's already exceeded its crash quota, 11808 // quit right away without showing a crash dialog. 11809 if (r == null || !makeAppCrashingLocked(r, shortMsg, longMsg, stackTrace)) { 11810 Binder.restoreCallingIdentity(origId); 11811 return; 11812 } 11813 11814 Message msg = Message.obtain(); 11815 msg.what = SHOW_ERROR_MSG; 11816 HashMap data = new HashMap(); 11817 data.put("result", result); 11818 data.put("app", r); 11819 msg.obj = data; 11820 mHandler.sendMessage(msg); 11821 11822 Binder.restoreCallingIdentity(origId); 11823 } 11824 11825 int res = result.get(); 11826 11827 Intent appErrorIntent = null; 11828 synchronized (this) { 11829 if (r != null && !r.isolated) { 11830 // XXX Can't keep track of crash time for isolated processes, 11831 // since they don't have a persistent identity. 11832 mProcessCrashTimes.put(r.info.processName, r.uid, 11833 SystemClock.uptimeMillis()); 11834 } 11835 if (res == AppErrorDialog.FORCE_QUIT_AND_REPORT) { 11836 appErrorIntent = createAppErrorIntentLocked(r, timeMillis, crashInfo); 11837 } 11838 } 11839 11840 if (appErrorIntent != null) { 11841 try { 11842 mContext.startActivityAsUser(appErrorIntent, new UserHandle(r.userId)); 11843 } catch (ActivityNotFoundException e) { 11844 Slog.w(TAG, "bug report receiver dissappeared", e); 11845 } 11846 } 11847 } 11848 11849 Intent createAppErrorIntentLocked(ProcessRecord r, 11850 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 11851 ApplicationErrorReport report = createAppErrorReportLocked(r, timeMillis, crashInfo); 11852 if (report == null) { 11853 return null; 11854 } 11855 Intent result = new Intent(Intent.ACTION_APP_ERROR); 11856 result.setComponent(r.errorReportReceiver); 11857 result.putExtra(Intent.EXTRA_BUG_REPORT, report); 11858 result.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 11859 return result; 11860 } 11861 11862 private ApplicationErrorReport createAppErrorReportLocked(ProcessRecord r, 11863 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 11864 if (r.errorReportReceiver == null) { 11865 return null; 11866 } 11867 11868 if (!r.crashing && !r.notResponding && !r.forceCrashReport) { 11869 return null; 11870 } 11871 11872 ApplicationErrorReport report = new ApplicationErrorReport(); 11873 report.packageName = r.info.packageName; 11874 report.installerPackageName = r.errorReportReceiver.getPackageName(); 11875 report.processName = r.processName; 11876 report.time = timeMillis; 11877 report.systemApp = (r.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0; 11878 11879 if (r.crashing || r.forceCrashReport) { 11880 report.type = ApplicationErrorReport.TYPE_CRASH; 11881 report.crashInfo = crashInfo; 11882 } else if (r.notResponding) { 11883 report.type = ApplicationErrorReport.TYPE_ANR; 11884 report.anrInfo = new ApplicationErrorReport.AnrInfo(); 11885 11886 report.anrInfo.activity = r.notRespondingReport.tag; 11887 report.anrInfo.cause = r.notRespondingReport.shortMsg; 11888 report.anrInfo.info = r.notRespondingReport.longMsg; 11889 } 11890 11891 return report; 11892 } 11893 11894 public List<ActivityManager.ProcessErrorStateInfo> getProcessesInErrorState() { 11895 enforceNotIsolatedCaller("getProcessesInErrorState"); 11896 // assume our apps are happy - lazy create the list 11897 List<ActivityManager.ProcessErrorStateInfo> errList = null; 11898 11899 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 11900 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 11901 int userId = UserHandle.getUserId(Binder.getCallingUid()); 11902 11903 synchronized (this) { 11904 11905 // iterate across all processes 11906 for (int i=mLruProcesses.size()-1; i>=0; i--) { 11907 ProcessRecord app = mLruProcesses.get(i); 11908 if (!allUsers && app.userId != userId) { 11909 continue; 11910 } 11911 if ((app.thread != null) && (app.crashing || app.notResponding)) { 11912 // This one's in trouble, so we'll generate a report for it 11913 // crashes are higher priority (in case there's a crash *and* an anr) 11914 ActivityManager.ProcessErrorStateInfo report = null; 11915 if (app.crashing) { 11916 report = app.crashingReport; 11917 } else if (app.notResponding) { 11918 report = app.notRespondingReport; 11919 } 11920 11921 if (report != null) { 11922 if (errList == null) { 11923 errList = new ArrayList<ActivityManager.ProcessErrorStateInfo>(1); 11924 } 11925 errList.add(report); 11926 } else { 11927 Slog.w(TAG, "Missing app error report, app = " + app.processName + 11928 " crashing = " + app.crashing + 11929 " notResponding = " + app.notResponding); 11930 } 11931 } 11932 } 11933 } 11934 11935 return errList; 11936 } 11937 11938 static int procStateToImportance(int procState, int memAdj, 11939 ActivityManager.RunningAppProcessInfo currApp) { 11940 int imp = ActivityManager.RunningAppProcessInfo.procStateToImportance(procState); 11941 if (imp == ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND) { 11942 currApp.lru = memAdj; 11943 } else { 11944 currApp.lru = 0; 11945 } 11946 return imp; 11947 } 11948 11949 private void fillInProcMemInfo(ProcessRecord app, 11950 ActivityManager.RunningAppProcessInfo outInfo) { 11951 outInfo.pid = app.pid; 11952 outInfo.uid = app.info.uid; 11953 if (mHeavyWeightProcess == app) { 11954 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_CANT_SAVE_STATE; 11955 } 11956 if (app.persistent) { 11957 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_PERSISTENT; 11958 } 11959 if (app.activities.size() > 0) { 11960 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_HAS_ACTIVITIES; 11961 } 11962 outInfo.lastTrimLevel = app.trimMemoryLevel; 11963 int adj = app.curAdj; 11964 int procState = app.curProcState; 11965 outInfo.importance = procStateToImportance(procState, adj, outInfo); 11966 outInfo.importanceReasonCode = app.adjTypeCode; 11967 outInfo.processState = app.curProcState; 11968 } 11969 11970 public List<ActivityManager.RunningAppProcessInfo> getRunningAppProcesses() { 11971 enforceNotIsolatedCaller("getRunningAppProcesses"); 11972 // Lazy instantiation of list 11973 List<ActivityManager.RunningAppProcessInfo> runList = null; 11974 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 11975 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 11976 int userId = UserHandle.getUserId(Binder.getCallingUid()); 11977 synchronized (this) { 11978 // Iterate across all processes 11979 for (int i=mLruProcesses.size()-1; i>=0; i--) { 11980 ProcessRecord app = mLruProcesses.get(i); 11981 if (!allUsers && app.userId != userId) { 11982 continue; 11983 } 11984 if ((app.thread != null) && (!app.crashing && !app.notResponding)) { 11985 // Generate process state info for running application 11986 ActivityManager.RunningAppProcessInfo currApp = 11987 new ActivityManager.RunningAppProcessInfo(app.processName, 11988 app.pid, app.getPackageList()); 11989 fillInProcMemInfo(app, currApp); 11990 if (app.adjSource instanceof ProcessRecord) { 11991 currApp.importanceReasonPid = ((ProcessRecord)app.adjSource).pid; 11992 currApp.importanceReasonImportance = 11993 ActivityManager.RunningAppProcessInfo.procStateToImportance( 11994 app.adjSourceProcState); 11995 } else if (app.adjSource instanceof ActivityRecord) { 11996 ActivityRecord r = (ActivityRecord)app.adjSource; 11997 if (r.app != null) currApp.importanceReasonPid = r.app.pid; 11998 } 11999 if (app.adjTarget instanceof ComponentName) { 12000 currApp.importanceReasonComponent = (ComponentName)app.adjTarget; 12001 } 12002 //Slog.v(TAG, "Proc " + app.processName + ": imp=" + currApp.importance 12003 // + " lru=" + currApp.lru); 12004 if (runList == null) { 12005 runList = new ArrayList<ActivityManager.RunningAppProcessInfo>(); 12006 } 12007 runList.add(currApp); 12008 } 12009 } 12010 } 12011 return runList; 12012 } 12013 12014 public List<ApplicationInfo> getRunningExternalApplications() { 12015 enforceNotIsolatedCaller("getRunningExternalApplications"); 12016 List<ActivityManager.RunningAppProcessInfo> runningApps = getRunningAppProcesses(); 12017 List<ApplicationInfo> retList = new ArrayList<ApplicationInfo>(); 12018 if (runningApps != null && runningApps.size() > 0) { 12019 Set<String> extList = new HashSet<String>(); 12020 for (ActivityManager.RunningAppProcessInfo app : runningApps) { 12021 if (app.pkgList != null) { 12022 for (String pkg : app.pkgList) { 12023 extList.add(pkg); 12024 } 12025 } 12026 } 12027 IPackageManager pm = AppGlobals.getPackageManager(); 12028 for (String pkg : extList) { 12029 try { 12030 ApplicationInfo info = pm.getApplicationInfo(pkg, 0, UserHandle.getCallingUserId()); 12031 if ((info.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0) { 12032 retList.add(info); 12033 } 12034 } catch (RemoteException e) { 12035 } 12036 } 12037 } 12038 return retList; 12039 } 12040 12041 @Override 12042 public void getMyMemoryState(ActivityManager.RunningAppProcessInfo outInfo) { 12043 enforceNotIsolatedCaller("getMyMemoryState"); 12044 synchronized (this) { 12045 ProcessRecord proc; 12046 synchronized (mPidsSelfLocked) { 12047 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 12048 } 12049 fillInProcMemInfo(proc, outInfo); 12050 } 12051 } 12052 12053 @Override 12054 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 12055 if (checkCallingPermission(android.Manifest.permission.DUMP) 12056 != PackageManager.PERMISSION_GRANTED) { 12057 pw.println("Permission Denial: can't dump ActivityManager from from pid=" 12058 + Binder.getCallingPid() 12059 + ", uid=" + Binder.getCallingUid() 12060 + " without permission " 12061 + android.Manifest.permission.DUMP); 12062 return; 12063 } 12064 12065 boolean dumpAll = false; 12066 boolean dumpClient = false; 12067 String dumpPackage = null; 12068 12069 int opti = 0; 12070 while (opti < args.length) { 12071 String opt = args[opti]; 12072 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 12073 break; 12074 } 12075 opti++; 12076 if ("-a".equals(opt)) { 12077 dumpAll = true; 12078 } else if ("-c".equals(opt)) { 12079 dumpClient = true; 12080 } else if ("-h".equals(opt)) { 12081 pw.println("Activity manager dump options:"); 12082 pw.println(" [-a] [-c] [-h] [cmd] ..."); 12083 pw.println(" cmd may be one of:"); 12084 pw.println(" a[ctivities]: activity stack state"); 12085 pw.println(" r[recents]: recent activities state"); 12086 pw.println(" b[roadcasts] [PACKAGE_NAME] [history [-s]]: broadcast state"); 12087 pw.println(" i[ntents] [PACKAGE_NAME]: pending intent state"); 12088 pw.println(" p[rocesses] [PACKAGE_NAME]: process state"); 12089 pw.println(" o[om]: out of memory management"); 12090 pw.println(" prov[iders] [COMP_SPEC ...]: content provider state"); 12091 pw.println(" provider [COMP_SPEC]: provider client-side state"); 12092 pw.println(" s[ervices] [COMP_SPEC ...]: service state"); 12093 pw.println(" service [COMP_SPEC]: service client-side state"); 12094 pw.println(" package [PACKAGE_NAME]: all state related to given package"); 12095 pw.println(" all: dump all activities"); 12096 pw.println(" top: dump the top activity"); 12097 pw.println(" cmd may also be a COMP_SPEC to dump activities."); 12098 pw.println(" COMP_SPEC may be a component name (com.foo/.myApp),"); 12099 pw.println(" a partial substring in a component name, a"); 12100 pw.println(" hex object identifier."); 12101 pw.println(" -a: include all available server state."); 12102 pw.println(" -c: include client state."); 12103 return; 12104 } else { 12105 pw.println("Unknown argument: " + opt + "; use -h for help"); 12106 } 12107 } 12108 12109 long origId = Binder.clearCallingIdentity(); 12110 boolean more = false; 12111 // Is the caller requesting to dump a particular piece of data? 12112 if (opti < args.length) { 12113 String cmd = args[opti]; 12114 opti++; 12115 if ("activities".equals(cmd) || "a".equals(cmd)) { 12116 synchronized (this) { 12117 dumpActivitiesLocked(fd, pw, args, opti, true, dumpClient, null); 12118 } 12119 } else if ("recents".equals(cmd) || "r".equals(cmd)) { 12120 synchronized (this) { 12121 dumpRecentsLocked(fd, pw, args, opti, true, null); 12122 } 12123 } else if ("broadcasts".equals(cmd) || "b".equals(cmd)) { 12124 String[] newArgs; 12125 String name; 12126 if (opti >= args.length) { 12127 name = null; 12128 newArgs = EMPTY_STRING_ARRAY; 12129 } else { 12130 name = args[opti]; 12131 opti++; 12132 newArgs = new String[args.length - opti]; 12133 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12134 args.length - opti); 12135 } 12136 synchronized (this) { 12137 dumpBroadcastsLocked(fd, pw, args, opti, true, name); 12138 } 12139 } else if ("intents".equals(cmd) || "i".equals(cmd)) { 12140 String[] newArgs; 12141 String name; 12142 if (opti >= args.length) { 12143 name = null; 12144 newArgs = EMPTY_STRING_ARRAY; 12145 } else { 12146 name = args[opti]; 12147 opti++; 12148 newArgs = new String[args.length - opti]; 12149 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12150 args.length - opti); 12151 } 12152 synchronized (this) { 12153 dumpPendingIntentsLocked(fd, pw, args, opti, true, name); 12154 } 12155 } else if ("processes".equals(cmd) || "p".equals(cmd)) { 12156 String[] newArgs; 12157 String name; 12158 if (opti >= args.length) { 12159 name = null; 12160 newArgs = EMPTY_STRING_ARRAY; 12161 } else { 12162 name = args[opti]; 12163 opti++; 12164 newArgs = new String[args.length - opti]; 12165 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12166 args.length - opti); 12167 } 12168 synchronized (this) { 12169 dumpProcessesLocked(fd, pw, args, opti, true, name); 12170 } 12171 } else if ("oom".equals(cmd) || "o".equals(cmd)) { 12172 synchronized (this) { 12173 dumpOomLocked(fd, pw, args, opti, true); 12174 } 12175 } else if ("provider".equals(cmd)) { 12176 String[] newArgs; 12177 String name; 12178 if (opti >= args.length) { 12179 name = null; 12180 newArgs = EMPTY_STRING_ARRAY; 12181 } else { 12182 name = args[opti]; 12183 opti++; 12184 newArgs = new String[args.length - opti]; 12185 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, args.length - opti); 12186 } 12187 if (!dumpProvider(fd, pw, name, newArgs, 0, dumpAll)) { 12188 pw.println("No providers match: " + name); 12189 pw.println("Use -h for help."); 12190 } 12191 } else if ("providers".equals(cmd) || "prov".equals(cmd)) { 12192 synchronized (this) { 12193 dumpProvidersLocked(fd, pw, args, opti, true, null); 12194 } 12195 } else if ("service".equals(cmd)) { 12196 String[] newArgs; 12197 String name; 12198 if (opti >= args.length) { 12199 name = null; 12200 newArgs = EMPTY_STRING_ARRAY; 12201 } else { 12202 name = args[opti]; 12203 opti++; 12204 newArgs = new String[args.length - opti]; 12205 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12206 args.length - opti); 12207 } 12208 if (!mServices.dumpService(fd, pw, name, newArgs, 0, dumpAll)) { 12209 pw.println("No services match: " + name); 12210 pw.println("Use -h for help."); 12211 } 12212 } else if ("package".equals(cmd)) { 12213 String[] newArgs; 12214 if (opti >= args.length) { 12215 pw.println("package: no package name specified"); 12216 pw.println("Use -h for help."); 12217 } else { 12218 dumpPackage = args[opti]; 12219 opti++; 12220 newArgs = new String[args.length - opti]; 12221 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 12222 args.length - opti); 12223 args = newArgs; 12224 opti = 0; 12225 more = true; 12226 } 12227 } else if ("services".equals(cmd) || "s".equals(cmd)) { 12228 synchronized (this) { 12229 mServices.dumpServicesLocked(fd, pw, args, opti, true, dumpClient, null); 12230 } 12231 } else { 12232 // Dumping a single activity? 12233 if (!dumpActivity(fd, pw, cmd, args, opti, dumpAll)) { 12234 pw.println("Bad activity command, or no activities match: " + cmd); 12235 pw.println("Use -h for help."); 12236 } 12237 } 12238 if (!more) { 12239 Binder.restoreCallingIdentity(origId); 12240 return; 12241 } 12242 } 12243 12244 // No piece of data specified, dump everything. 12245 synchronized (this) { 12246 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12247 pw.println(); 12248 if (dumpAll) { 12249 pw.println("-------------------------------------------------------------------------------"); 12250 } 12251 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12252 pw.println(); 12253 if (dumpAll) { 12254 pw.println("-------------------------------------------------------------------------------"); 12255 } 12256 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12257 pw.println(); 12258 if (dumpAll) { 12259 pw.println("-------------------------------------------------------------------------------"); 12260 } 12261 mServices.dumpServicesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 12262 pw.println(); 12263 if (dumpAll) { 12264 pw.println("-------------------------------------------------------------------------------"); 12265 } 12266 dumpRecentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12267 pw.println(); 12268 if (dumpAll) { 12269 pw.println("-------------------------------------------------------------------------------"); 12270 } 12271 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 12272 pw.println(); 12273 if (dumpAll) { 12274 pw.println("-------------------------------------------------------------------------------"); 12275 } 12276 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage); 12277 } 12278 Binder.restoreCallingIdentity(origId); 12279 } 12280 12281 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12282 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) { 12283 pw.println("ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)"); 12284 12285 boolean printedAnything = mStackSupervisor.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient, 12286 dumpPackage); 12287 boolean needSep = printedAnything; 12288 12289 boolean printed = ActivityStackSupervisor.printThisActivity(pw, mFocusedActivity, 12290 dumpPackage, needSep, " mFocusedActivity: "); 12291 if (printed) { 12292 printedAnything = true; 12293 needSep = false; 12294 } 12295 12296 if (dumpPackage == null) { 12297 if (needSep) { 12298 pw.println(); 12299 } 12300 needSep = true; 12301 printedAnything = true; 12302 mStackSupervisor.dump(pw, " "); 12303 } 12304 12305 if (!printedAnything) { 12306 pw.println(" (nothing)"); 12307 } 12308 } 12309 12310 void dumpRecentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12311 int opti, boolean dumpAll, String dumpPackage) { 12312 pw.println("ACTIVITY MANAGER RECENT ACTIVITIES (dumpsys activity recents)"); 12313 12314 boolean printedAnything = false; 12315 12316 if (mRecentTasks.size() > 0) { 12317 boolean printedHeader = false; 12318 12319 final int N = mRecentTasks.size(); 12320 for (int i=0; i<N; i++) { 12321 TaskRecord tr = mRecentTasks.get(i); 12322 if (dumpPackage != null) { 12323 if (tr.realActivity == null || 12324 !dumpPackage.equals(tr.realActivity)) { 12325 continue; 12326 } 12327 } 12328 if (!printedHeader) { 12329 pw.println(" Recent tasks:"); 12330 printedHeader = true; 12331 printedAnything = true; 12332 } 12333 pw.print(" * Recent #"); pw.print(i); pw.print(": "); 12334 pw.println(tr); 12335 if (dumpAll) { 12336 mRecentTasks.get(i).dump(pw, " "); 12337 } 12338 } 12339 } 12340 12341 if (!printedAnything) { 12342 pw.println(" (nothing)"); 12343 } 12344 } 12345 12346 void dumpProcessesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12347 int opti, boolean dumpAll, String dumpPackage) { 12348 boolean needSep = false; 12349 boolean printedAnything = false; 12350 int numPers = 0; 12351 12352 pw.println("ACTIVITY MANAGER RUNNING PROCESSES (dumpsys activity processes)"); 12353 12354 if (dumpAll) { 12355 final int NP = mProcessNames.getMap().size(); 12356 for (int ip=0; ip<NP; ip++) { 12357 SparseArray<ProcessRecord> procs = mProcessNames.getMap().valueAt(ip); 12358 final int NA = procs.size(); 12359 for (int ia=0; ia<NA; ia++) { 12360 ProcessRecord r = procs.valueAt(ia); 12361 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 12362 continue; 12363 } 12364 if (!needSep) { 12365 pw.println(" All known processes:"); 12366 needSep = true; 12367 printedAnything = true; 12368 } 12369 pw.print(r.persistent ? " *PERS*" : " *APP*"); 12370 pw.print(" UID "); pw.print(procs.keyAt(ia)); 12371 pw.print(" "); pw.println(r); 12372 r.dump(pw, " "); 12373 if (r.persistent) { 12374 numPers++; 12375 } 12376 } 12377 } 12378 } 12379 12380 if (mIsolatedProcesses.size() > 0) { 12381 boolean printed = false; 12382 for (int i=0; i<mIsolatedProcesses.size(); i++) { 12383 ProcessRecord r = mIsolatedProcesses.valueAt(i); 12384 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 12385 continue; 12386 } 12387 if (!printed) { 12388 if (needSep) { 12389 pw.println(); 12390 } 12391 pw.println(" Isolated process list (sorted by uid):"); 12392 printedAnything = true; 12393 printed = true; 12394 needSep = true; 12395 } 12396 pw.println(String.format("%sIsolated #%2d: %s", 12397 " ", i, r.toString())); 12398 } 12399 } 12400 12401 if (mLruProcesses.size() > 0) { 12402 if (needSep) { 12403 pw.println(); 12404 } 12405 pw.print(" Process LRU list (sorted by oom_adj, "); pw.print(mLruProcesses.size()); 12406 pw.print(" total, non-act at "); 12407 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 12408 pw.print(", non-svc at "); 12409 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 12410 pw.println("):"); 12411 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", false, dumpPackage); 12412 needSep = true; 12413 printedAnything = true; 12414 } 12415 12416 if (dumpAll || dumpPackage != null) { 12417 synchronized (mPidsSelfLocked) { 12418 boolean printed = false; 12419 for (int i=0; i<mPidsSelfLocked.size(); i++) { 12420 ProcessRecord r = mPidsSelfLocked.valueAt(i); 12421 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 12422 continue; 12423 } 12424 if (!printed) { 12425 if (needSep) pw.println(); 12426 needSep = true; 12427 pw.println(" PID mappings:"); 12428 printed = true; 12429 printedAnything = true; 12430 } 12431 pw.print(" PID #"); pw.print(mPidsSelfLocked.keyAt(i)); 12432 pw.print(": "); pw.println(mPidsSelfLocked.valueAt(i)); 12433 } 12434 } 12435 } 12436 12437 if (mForegroundProcesses.size() > 0) { 12438 synchronized (mPidsSelfLocked) { 12439 boolean printed = false; 12440 for (int i=0; i<mForegroundProcesses.size(); i++) { 12441 ProcessRecord r = mPidsSelfLocked.get( 12442 mForegroundProcesses.valueAt(i).pid); 12443 if (dumpPackage != null && (r == null 12444 || !r.pkgList.containsKey(dumpPackage))) { 12445 continue; 12446 } 12447 if (!printed) { 12448 if (needSep) pw.println(); 12449 needSep = true; 12450 pw.println(" Foreground Processes:"); 12451 printed = true; 12452 printedAnything = true; 12453 } 12454 pw.print(" PID #"); pw.print(mForegroundProcesses.keyAt(i)); 12455 pw.print(": "); pw.println(mForegroundProcesses.valueAt(i)); 12456 } 12457 } 12458 } 12459 12460 if (mPersistentStartingProcesses.size() > 0) { 12461 if (needSep) pw.println(); 12462 needSep = true; 12463 printedAnything = true; 12464 pw.println(" Persisent processes that are starting:"); 12465 dumpProcessList(pw, this, mPersistentStartingProcesses, " ", 12466 "Starting Norm", "Restarting PERS", dumpPackage); 12467 } 12468 12469 if (mRemovedProcesses.size() > 0) { 12470 if (needSep) pw.println(); 12471 needSep = true; 12472 printedAnything = true; 12473 pw.println(" Processes that are being removed:"); 12474 dumpProcessList(pw, this, mRemovedProcesses, " ", 12475 "Removed Norm", "Removed PERS", dumpPackage); 12476 } 12477 12478 if (mProcessesOnHold.size() > 0) { 12479 if (needSep) pw.println(); 12480 needSep = true; 12481 printedAnything = true; 12482 pw.println(" Processes that are on old until the system is ready:"); 12483 dumpProcessList(pw, this, mProcessesOnHold, " ", 12484 "OnHold Norm", "OnHold PERS", dumpPackage); 12485 } 12486 12487 needSep = dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, dumpPackage); 12488 12489 if (mProcessCrashTimes.getMap().size() > 0) { 12490 boolean printed = false; 12491 long now = SystemClock.uptimeMillis(); 12492 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 12493 final int NP = pmap.size(); 12494 for (int ip=0; ip<NP; ip++) { 12495 String pname = pmap.keyAt(ip); 12496 SparseArray<Long> uids = pmap.valueAt(ip); 12497 final int N = uids.size(); 12498 for (int i=0; i<N; i++) { 12499 int puid = uids.keyAt(i); 12500 ProcessRecord r = mProcessNames.get(pname, puid); 12501 if (dumpPackage != null && (r == null 12502 || !r.pkgList.containsKey(dumpPackage))) { 12503 continue; 12504 } 12505 if (!printed) { 12506 if (needSep) pw.println(); 12507 needSep = true; 12508 pw.println(" Time since processes crashed:"); 12509 printed = true; 12510 printedAnything = true; 12511 } 12512 pw.print(" Process "); pw.print(pname); 12513 pw.print(" uid "); pw.print(puid); 12514 pw.print(": last crashed "); 12515 TimeUtils.formatDuration(now-uids.valueAt(i), pw); 12516 pw.println(" ago"); 12517 } 12518 } 12519 } 12520 12521 if (mBadProcesses.getMap().size() > 0) { 12522 boolean printed = false; 12523 final ArrayMap<String, SparseArray<BadProcessInfo>> pmap = mBadProcesses.getMap(); 12524 final int NP = pmap.size(); 12525 for (int ip=0; ip<NP; ip++) { 12526 String pname = pmap.keyAt(ip); 12527 SparseArray<BadProcessInfo> uids = pmap.valueAt(ip); 12528 final int N = uids.size(); 12529 for (int i=0; i<N; i++) { 12530 int puid = uids.keyAt(i); 12531 ProcessRecord r = mProcessNames.get(pname, puid); 12532 if (dumpPackage != null && (r == null 12533 || !r.pkgList.containsKey(dumpPackage))) { 12534 continue; 12535 } 12536 if (!printed) { 12537 if (needSep) pw.println(); 12538 needSep = true; 12539 pw.println(" Bad processes:"); 12540 printedAnything = true; 12541 } 12542 BadProcessInfo info = uids.valueAt(i); 12543 pw.print(" Bad process "); pw.print(pname); 12544 pw.print(" uid "); pw.print(puid); 12545 pw.print(": crashed at time "); pw.println(info.time); 12546 if (info.shortMsg != null) { 12547 pw.print(" Short msg: "); pw.println(info.shortMsg); 12548 } 12549 if (info.longMsg != null) { 12550 pw.print(" Long msg: "); pw.println(info.longMsg); 12551 } 12552 if (info.stack != null) { 12553 pw.println(" Stack:"); 12554 int lastPos = 0; 12555 for (int pos=0; pos<info.stack.length(); pos++) { 12556 if (info.stack.charAt(pos) == '\n') { 12557 pw.print(" "); 12558 pw.write(info.stack, lastPos, pos-lastPos); 12559 pw.println(); 12560 lastPos = pos+1; 12561 } 12562 } 12563 if (lastPos < info.stack.length()) { 12564 pw.print(" "); 12565 pw.write(info.stack, lastPos, info.stack.length()-lastPos); 12566 pw.println(); 12567 } 12568 } 12569 } 12570 } 12571 } 12572 12573 if (dumpPackage == null) { 12574 pw.println(); 12575 needSep = false; 12576 pw.println(" mStartedUsers:"); 12577 for (int i=0; i<mStartedUsers.size(); i++) { 12578 UserStartedState uss = mStartedUsers.valueAt(i); 12579 pw.print(" User #"); pw.print(uss.mHandle.getIdentifier()); 12580 pw.print(": "); uss.dump("", pw); 12581 } 12582 pw.print(" mStartedUserArray: ["); 12583 for (int i=0; i<mStartedUserArray.length; i++) { 12584 if (i > 0) pw.print(", "); 12585 pw.print(mStartedUserArray[i]); 12586 } 12587 pw.println("]"); 12588 pw.print(" mUserLru: ["); 12589 for (int i=0; i<mUserLru.size(); i++) { 12590 if (i > 0) pw.print(", "); 12591 pw.print(mUserLru.get(i)); 12592 } 12593 pw.println("]"); 12594 if (dumpAll) { 12595 pw.print(" mStartedUserArray: "); pw.println(Arrays.toString(mStartedUserArray)); 12596 } 12597 synchronized (mUserProfileGroupIdsSelfLocked) { 12598 if (mUserProfileGroupIdsSelfLocked.size() > 0) { 12599 pw.println(" mUserProfileGroupIds:"); 12600 for (int i=0; i<mUserProfileGroupIdsSelfLocked.size(); i++) { 12601 pw.print(" User #"); 12602 pw.print(mUserProfileGroupIdsSelfLocked.keyAt(i)); 12603 pw.print(" -> profile #"); 12604 pw.println(mUserProfileGroupIdsSelfLocked.valueAt(i)); 12605 } 12606 } 12607 } 12608 } 12609 if (mHomeProcess != null && (dumpPackage == null 12610 || mHomeProcess.pkgList.containsKey(dumpPackage))) { 12611 if (needSep) { 12612 pw.println(); 12613 needSep = false; 12614 } 12615 pw.println(" mHomeProcess: " + mHomeProcess); 12616 } 12617 if (mPreviousProcess != null && (dumpPackage == null 12618 || mPreviousProcess.pkgList.containsKey(dumpPackage))) { 12619 if (needSep) { 12620 pw.println(); 12621 needSep = false; 12622 } 12623 pw.println(" mPreviousProcess: " + mPreviousProcess); 12624 } 12625 if (dumpAll) { 12626 StringBuilder sb = new StringBuilder(128); 12627 sb.append(" mPreviousProcessVisibleTime: "); 12628 TimeUtils.formatDuration(mPreviousProcessVisibleTime, sb); 12629 pw.println(sb); 12630 } 12631 if (mHeavyWeightProcess != null && (dumpPackage == null 12632 || mHeavyWeightProcess.pkgList.containsKey(dumpPackage))) { 12633 if (needSep) { 12634 pw.println(); 12635 needSep = false; 12636 } 12637 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 12638 } 12639 if (dumpPackage == null) { 12640 pw.println(" mConfiguration: " + mConfiguration); 12641 } 12642 if (dumpAll) { 12643 pw.println(" mConfigWillChange: " + getFocusedStack().mConfigWillChange); 12644 if (mCompatModePackages.getPackages().size() > 0) { 12645 boolean printed = false; 12646 for (Map.Entry<String, Integer> entry 12647 : mCompatModePackages.getPackages().entrySet()) { 12648 String pkg = entry.getKey(); 12649 int mode = entry.getValue(); 12650 if (dumpPackage != null && !dumpPackage.equals(pkg)) { 12651 continue; 12652 } 12653 if (!printed) { 12654 pw.println(" mScreenCompatPackages:"); 12655 printed = true; 12656 } 12657 pw.print(" "); pw.print(pkg); pw.print(": "); 12658 pw.print(mode); pw.println(); 12659 } 12660 } 12661 } 12662 if (dumpPackage == null) { 12663 if (mSleeping || mWentToSleep || mLockScreenShown) { 12664 pw.println(" mSleeping=" + mSleeping + " mWentToSleep=" + mWentToSleep 12665 + " mLockScreenShown " + mLockScreenShown); 12666 } 12667 if (mShuttingDown || mRunningVoice) { 12668 pw.print(" mShuttingDown=" + mShuttingDown + " mRunningVoice=" + mRunningVoice); 12669 } 12670 } 12671 if (mDebugApp != null || mOrigDebugApp != null || mDebugTransient 12672 || mOrigWaitForDebugger) { 12673 if (dumpPackage == null || dumpPackage.equals(mDebugApp) 12674 || dumpPackage.equals(mOrigDebugApp)) { 12675 if (needSep) { 12676 pw.println(); 12677 needSep = false; 12678 } 12679 pw.println(" mDebugApp=" + mDebugApp + "/orig=" + mOrigDebugApp 12680 + " mDebugTransient=" + mDebugTransient 12681 + " mOrigWaitForDebugger=" + mOrigWaitForDebugger); 12682 } 12683 } 12684 if (mOpenGlTraceApp != null) { 12685 if (dumpPackage == null || dumpPackage.equals(mOpenGlTraceApp)) { 12686 if (needSep) { 12687 pw.println(); 12688 needSep = false; 12689 } 12690 pw.println(" mOpenGlTraceApp=" + mOpenGlTraceApp); 12691 } 12692 } 12693 if (mProfileApp != null || mProfileProc != null || mProfileFile != null 12694 || mProfileFd != null) { 12695 if (dumpPackage == null || dumpPackage.equals(mProfileApp)) { 12696 if (needSep) { 12697 pw.println(); 12698 needSep = false; 12699 } 12700 pw.println(" mProfileApp=" + mProfileApp + " mProfileProc=" + mProfileProc); 12701 pw.println(" mProfileFile=" + mProfileFile + " mProfileFd=" + mProfileFd); 12702 pw.println(" mSamplingInterval=" + mSamplingInterval + " mAutoStopProfiler=" 12703 + mAutoStopProfiler); 12704 pw.println(" mProfileType=" + mProfileType); 12705 } 12706 } 12707 if (dumpPackage == null) { 12708 if (mAlwaysFinishActivities || mController != null) { 12709 pw.println(" mAlwaysFinishActivities=" + mAlwaysFinishActivities 12710 + " mController=" + mController); 12711 } 12712 if (dumpAll) { 12713 pw.println(" Total persistent processes: " + numPers); 12714 pw.println(" mProcessesReady=" + mProcessesReady 12715 + " mSystemReady=" + mSystemReady); 12716 pw.println(" mBooting=" + mBooting 12717 + " mBooted=" + mBooted 12718 + " mFactoryTest=" + mFactoryTest); 12719 pw.print(" mLastPowerCheckRealtime="); 12720 TimeUtils.formatDuration(mLastPowerCheckRealtime, pw); 12721 pw.println(""); 12722 pw.print(" mLastPowerCheckUptime="); 12723 TimeUtils.formatDuration(mLastPowerCheckUptime, pw); 12724 pw.println(""); 12725 pw.println(" mGoingToSleep=" + mStackSupervisor.mGoingToSleep); 12726 pw.println(" mLaunchingActivity=" + mStackSupervisor.mLaunchingActivity); 12727 pw.println(" mAdjSeq=" + mAdjSeq + " mLruSeq=" + mLruSeq); 12728 pw.println(" mNumNonCachedProcs=" + mNumNonCachedProcs 12729 + " (" + mLruProcesses.size() + " total)" 12730 + " mNumCachedHiddenProcs=" + mNumCachedHiddenProcs 12731 + " mNumServiceProcs=" + mNumServiceProcs 12732 + " mNewNumServiceProcs=" + mNewNumServiceProcs); 12733 pw.println(" mAllowLowerMemLevel=" + mAllowLowerMemLevel 12734 + " mLastMemoryLevel" + mLastMemoryLevel 12735 + " mLastNumProcesses" + mLastNumProcesses); 12736 long now = SystemClock.uptimeMillis(); 12737 pw.print(" mLastIdleTime="); 12738 TimeUtils.formatDuration(now, mLastIdleTime, pw); 12739 pw.print(" mLowRamSinceLastIdle="); 12740 TimeUtils.formatDuration(getLowRamTimeSinceIdle(now), pw); 12741 pw.println(); 12742 } 12743 } 12744 12745 if (!printedAnything) { 12746 pw.println(" (nothing)"); 12747 } 12748 } 12749 12750 boolean dumpProcessesToGc(FileDescriptor fd, PrintWriter pw, String[] args, 12751 int opti, boolean needSep, boolean dumpAll, String dumpPackage) { 12752 if (mProcessesToGc.size() > 0) { 12753 boolean printed = false; 12754 long now = SystemClock.uptimeMillis(); 12755 for (int i=0; i<mProcessesToGc.size(); i++) { 12756 ProcessRecord proc = mProcessesToGc.get(i); 12757 if (dumpPackage != null && !dumpPackage.equals(proc.info.packageName)) { 12758 continue; 12759 } 12760 if (!printed) { 12761 if (needSep) pw.println(); 12762 needSep = true; 12763 pw.println(" Processes that are waiting to GC:"); 12764 printed = true; 12765 } 12766 pw.print(" Process "); pw.println(proc); 12767 pw.print(" lowMem="); pw.print(proc.reportLowMemory); 12768 pw.print(", last gced="); 12769 pw.print(now-proc.lastRequestedGc); 12770 pw.print(" ms ago, last lowMem="); 12771 pw.print(now-proc.lastLowMemory); 12772 pw.println(" ms ago"); 12773 12774 } 12775 } 12776 return needSep; 12777 } 12778 12779 void printOomLevel(PrintWriter pw, String name, int adj) { 12780 pw.print(" "); 12781 if (adj >= 0) { 12782 pw.print(' '); 12783 if (adj < 10) pw.print(' '); 12784 } else { 12785 if (adj > -10) pw.print(' '); 12786 } 12787 pw.print(adj); 12788 pw.print(": "); 12789 pw.print(name); 12790 pw.print(" ("); 12791 pw.print(mProcessList.getMemLevel(adj)/1024); 12792 pw.println(" kB)"); 12793 } 12794 12795 boolean dumpOomLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12796 int opti, boolean dumpAll) { 12797 boolean needSep = false; 12798 12799 if (mLruProcesses.size() > 0) { 12800 if (needSep) pw.println(); 12801 needSep = true; 12802 pw.println(" OOM levels:"); 12803 printOomLevel(pw, "SYSTEM_ADJ", ProcessList.SYSTEM_ADJ); 12804 printOomLevel(pw, "PERSISTENT_PROC_ADJ", ProcessList.PERSISTENT_PROC_ADJ); 12805 printOomLevel(pw, "FOREGROUND_APP_ADJ", ProcessList.FOREGROUND_APP_ADJ); 12806 printOomLevel(pw, "VISIBLE_APP_ADJ", ProcessList.VISIBLE_APP_ADJ); 12807 printOomLevel(pw, "PERCEPTIBLE_APP_ADJ", ProcessList.PERCEPTIBLE_APP_ADJ); 12808 printOomLevel(pw, "BACKUP_APP_ADJ", ProcessList.BACKUP_APP_ADJ); 12809 printOomLevel(pw, "HEAVY_WEIGHT_APP_ADJ", ProcessList.HEAVY_WEIGHT_APP_ADJ); 12810 printOomLevel(pw, "SERVICE_ADJ", ProcessList.SERVICE_ADJ); 12811 printOomLevel(pw, "HOME_APP_ADJ", ProcessList.HOME_APP_ADJ); 12812 printOomLevel(pw, "PREVIOUS_APP_ADJ", ProcessList.PREVIOUS_APP_ADJ); 12813 printOomLevel(pw, "SERVICE_B_ADJ", ProcessList.SERVICE_B_ADJ); 12814 printOomLevel(pw, "CACHED_APP_MIN_ADJ", ProcessList.CACHED_APP_MIN_ADJ); 12815 printOomLevel(pw, "CACHED_APP_MAX_ADJ", ProcessList.CACHED_APP_MAX_ADJ); 12816 12817 if (needSep) pw.println(); 12818 pw.print(" Process OOM control ("); pw.print(mLruProcesses.size()); 12819 pw.print(" total, non-act at "); 12820 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 12821 pw.print(", non-svc at "); 12822 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 12823 pw.println("):"); 12824 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", true, null); 12825 needSep = true; 12826 } 12827 12828 dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, null); 12829 12830 pw.println(); 12831 pw.println(" mHomeProcess: " + mHomeProcess); 12832 pw.println(" mPreviousProcess: " + mPreviousProcess); 12833 if (mHeavyWeightProcess != null) { 12834 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 12835 } 12836 12837 return true; 12838 } 12839 12840 /** 12841 * There are three ways to call this: 12842 * - no provider specified: dump all the providers 12843 * - a flattened component name that matched an existing provider was specified as the 12844 * first arg: dump that one provider 12845 * - the first arg isn't the flattened component name of an existing provider: 12846 * dump all providers whose component contains the first arg as a substring 12847 */ 12848 protected boolean dumpProvider(FileDescriptor fd, PrintWriter pw, String name, String[] args, 12849 int opti, boolean dumpAll) { 12850 return mProviderMap.dumpProvider(fd, pw, name, args, opti, dumpAll); 12851 } 12852 12853 static class ItemMatcher { 12854 ArrayList<ComponentName> components; 12855 ArrayList<String> strings; 12856 ArrayList<Integer> objects; 12857 boolean all; 12858 12859 ItemMatcher() { 12860 all = true; 12861 } 12862 12863 void build(String name) { 12864 ComponentName componentName = ComponentName.unflattenFromString(name); 12865 if (componentName != null) { 12866 if (components == null) { 12867 components = new ArrayList<ComponentName>(); 12868 } 12869 components.add(componentName); 12870 all = false; 12871 } else { 12872 int objectId = 0; 12873 // Not a '/' separated full component name; maybe an object ID? 12874 try { 12875 objectId = Integer.parseInt(name, 16); 12876 if (objects == null) { 12877 objects = new ArrayList<Integer>(); 12878 } 12879 objects.add(objectId); 12880 all = false; 12881 } catch (RuntimeException e) { 12882 // Not an integer; just do string match. 12883 if (strings == null) { 12884 strings = new ArrayList<String>(); 12885 } 12886 strings.add(name); 12887 all = false; 12888 } 12889 } 12890 } 12891 12892 int build(String[] args, int opti) { 12893 for (; opti<args.length; opti++) { 12894 String name = args[opti]; 12895 if ("--".equals(name)) { 12896 return opti+1; 12897 } 12898 build(name); 12899 } 12900 return opti; 12901 } 12902 12903 boolean match(Object object, ComponentName comp) { 12904 if (all) { 12905 return true; 12906 } 12907 if (components != null) { 12908 for (int i=0; i<components.size(); i++) { 12909 if (components.get(i).equals(comp)) { 12910 return true; 12911 } 12912 } 12913 } 12914 if (objects != null) { 12915 for (int i=0; i<objects.size(); i++) { 12916 if (System.identityHashCode(object) == objects.get(i)) { 12917 return true; 12918 } 12919 } 12920 } 12921 if (strings != null) { 12922 String flat = comp.flattenToString(); 12923 for (int i=0; i<strings.size(); i++) { 12924 if (flat.contains(strings.get(i))) { 12925 return true; 12926 } 12927 } 12928 } 12929 return false; 12930 } 12931 } 12932 12933 /** 12934 * There are three things that cmd can be: 12935 * - a flattened component name that matches an existing activity 12936 * - the cmd arg isn't the flattened component name of an existing activity: 12937 * dump all activity whose component contains the cmd as a substring 12938 * - A hex number of the ActivityRecord object instance. 12939 */ 12940 protected boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name, String[] args, 12941 int opti, boolean dumpAll) { 12942 ArrayList<ActivityRecord> activities; 12943 12944 synchronized (this) { 12945 activities = mStackSupervisor.getDumpActivitiesLocked(name); 12946 } 12947 12948 if (activities.size() <= 0) { 12949 return false; 12950 } 12951 12952 String[] newArgs = new String[args.length - opti]; 12953 System.arraycopy(args, opti, newArgs, 0, args.length - opti); 12954 12955 TaskRecord lastTask = null; 12956 boolean needSep = false; 12957 for (int i=activities.size()-1; i>=0; i--) { 12958 ActivityRecord r = activities.get(i); 12959 if (needSep) { 12960 pw.println(); 12961 } 12962 needSep = true; 12963 synchronized (this) { 12964 if (lastTask != r.task) { 12965 lastTask = r.task; 12966 pw.print("TASK "); pw.print(lastTask.affinity); 12967 pw.print(" id="); pw.println(lastTask.taskId); 12968 if (dumpAll) { 12969 lastTask.dump(pw, " "); 12970 } 12971 } 12972 } 12973 dumpActivity(" ", fd, pw, activities.get(i), newArgs, dumpAll); 12974 } 12975 return true; 12976 } 12977 12978 /** 12979 * Invokes IApplicationThread.dumpActivity() on the thread of the specified activity if 12980 * there is a thread associated with the activity. 12981 */ 12982 private void dumpActivity(String prefix, FileDescriptor fd, PrintWriter pw, 12983 final ActivityRecord r, String[] args, boolean dumpAll) { 12984 String innerPrefix = prefix + " "; 12985 synchronized (this) { 12986 pw.print(prefix); pw.print("ACTIVITY "); pw.print(r.shortComponentName); 12987 pw.print(" "); pw.print(Integer.toHexString(System.identityHashCode(r))); 12988 pw.print(" pid="); 12989 if (r.app != null) pw.println(r.app.pid); 12990 else pw.println("(not running)"); 12991 if (dumpAll) { 12992 r.dump(pw, innerPrefix); 12993 } 12994 } 12995 if (r.app != null && r.app.thread != null) { 12996 // flush anything that is already in the PrintWriter since the thread is going 12997 // to write to the file descriptor directly 12998 pw.flush(); 12999 try { 13000 TransferPipe tp = new TransferPipe(); 13001 try { 13002 r.app.thread.dumpActivity(tp.getWriteFd().getFileDescriptor(), 13003 r.appToken, innerPrefix, args); 13004 tp.go(fd); 13005 } finally { 13006 tp.kill(); 13007 } 13008 } catch (IOException e) { 13009 pw.println(innerPrefix + "Failure while dumping the activity: " + e); 13010 } catch (RemoteException e) { 13011 pw.println(innerPrefix + "Got a RemoteException while dumping the activity"); 13012 } 13013 } 13014 } 13015 13016 void dumpBroadcastsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 13017 int opti, boolean dumpAll, String dumpPackage) { 13018 boolean needSep = false; 13019 boolean onlyHistory = false; 13020 boolean printedAnything = false; 13021 13022 if ("history".equals(dumpPackage)) { 13023 if (opti < args.length && "-s".equals(args[opti])) { 13024 dumpAll = false; 13025 } 13026 onlyHistory = true; 13027 dumpPackage = null; 13028 } 13029 13030 pw.println("ACTIVITY MANAGER BROADCAST STATE (dumpsys activity broadcasts)"); 13031 if (!onlyHistory && dumpAll) { 13032 if (mRegisteredReceivers.size() > 0) { 13033 boolean printed = false; 13034 Iterator it = mRegisteredReceivers.values().iterator(); 13035 while (it.hasNext()) { 13036 ReceiverList r = (ReceiverList)it.next(); 13037 if (dumpPackage != null && (r.app == null || 13038 !dumpPackage.equals(r.app.info.packageName))) { 13039 continue; 13040 } 13041 if (!printed) { 13042 pw.println(" Registered Receivers:"); 13043 needSep = true; 13044 printed = true; 13045 printedAnything = true; 13046 } 13047 pw.print(" * "); pw.println(r); 13048 r.dump(pw, " "); 13049 } 13050 } 13051 13052 if (mReceiverResolver.dump(pw, needSep ? 13053 "\n Receiver Resolver Table:" : " Receiver Resolver Table:", 13054 " ", dumpPackage, false)) { 13055 needSep = true; 13056 printedAnything = true; 13057 } 13058 } 13059 13060 for (BroadcastQueue q : mBroadcastQueues) { 13061 needSep = q.dumpLocked(fd, pw, args, opti, dumpAll, dumpPackage, needSep); 13062 printedAnything |= needSep; 13063 } 13064 13065 needSep = true; 13066 13067 if (!onlyHistory && mStickyBroadcasts != null && dumpPackage == null) { 13068 for (int user=0; user<mStickyBroadcasts.size(); user++) { 13069 if (needSep) { 13070 pw.println(); 13071 } 13072 needSep = true; 13073 printedAnything = true; 13074 pw.print(" Sticky broadcasts for user "); 13075 pw.print(mStickyBroadcasts.keyAt(user)); pw.println(":"); 13076 StringBuilder sb = new StringBuilder(128); 13077 for (Map.Entry<String, ArrayList<Intent>> ent 13078 : mStickyBroadcasts.valueAt(user).entrySet()) { 13079 pw.print(" * Sticky action "); pw.print(ent.getKey()); 13080 if (dumpAll) { 13081 pw.println(":"); 13082 ArrayList<Intent> intents = ent.getValue(); 13083 final int N = intents.size(); 13084 for (int i=0; i<N; i++) { 13085 sb.setLength(0); 13086 sb.append(" Intent: "); 13087 intents.get(i).toShortString(sb, false, true, false, false); 13088 pw.println(sb.toString()); 13089 Bundle bundle = intents.get(i).getExtras(); 13090 if (bundle != null) { 13091 pw.print(" "); 13092 pw.println(bundle.toString()); 13093 } 13094 } 13095 } else { 13096 pw.println(""); 13097 } 13098 } 13099 } 13100 } 13101 13102 if (!onlyHistory && dumpAll) { 13103 pw.println(); 13104 for (BroadcastQueue queue : mBroadcastQueues) { 13105 pw.println(" mBroadcastsScheduled [" + queue.mQueueName + "]=" 13106 + queue.mBroadcastsScheduled); 13107 } 13108 pw.println(" mHandler:"); 13109 mHandler.dump(new PrintWriterPrinter(pw), " "); 13110 needSep = true; 13111 printedAnything = true; 13112 } 13113 13114 if (!printedAnything) { 13115 pw.println(" (nothing)"); 13116 } 13117 } 13118 13119 void dumpProvidersLocked(FileDescriptor fd, PrintWriter pw, String[] args, 13120 int opti, boolean dumpAll, String dumpPackage) { 13121 boolean needSep; 13122 boolean printedAnything = false; 13123 13124 ItemMatcher matcher = new ItemMatcher(); 13125 matcher.build(args, opti); 13126 13127 pw.println("ACTIVITY MANAGER CONTENT PROVIDERS (dumpsys activity providers)"); 13128 13129 needSep = mProviderMap.dumpProvidersLocked(pw, dumpAll, dumpPackage); 13130 printedAnything |= needSep; 13131 13132 if (mLaunchingProviders.size() > 0) { 13133 boolean printed = false; 13134 for (int i=mLaunchingProviders.size()-1; i>=0; i--) { 13135 ContentProviderRecord r = mLaunchingProviders.get(i); 13136 if (dumpPackage != null && !dumpPackage.equals(r.name.getPackageName())) { 13137 continue; 13138 } 13139 if (!printed) { 13140 if (needSep) pw.println(); 13141 needSep = true; 13142 pw.println(" Launching content providers:"); 13143 printed = true; 13144 printedAnything = true; 13145 } 13146 pw.print(" Launching #"); pw.print(i); pw.print(": "); 13147 pw.println(r); 13148 } 13149 } 13150 13151 if (mGrantedUriPermissions.size() > 0) { 13152 boolean printed = false; 13153 int dumpUid = -2; 13154 if (dumpPackage != null) { 13155 try { 13156 dumpUid = mContext.getPackageManager().getPackageUid(dumpPackage, 0); 13157 } catch (NameNotFoundException e) { 13158 dumpUid = -1; 13159 } 13160 } 13161 for (int i=0; i<mGrantedUriPermissions.size(); i++) { 13162 int uid = mGrantedUriPermissions.keyAt(i); 13163 if (dumpUid >= -1 && UserHandle.getAppId(uid) != dumpUid) { 13164 continue; 13165 } 13166 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 13167 if (!printed) { 13168 if (needSep) pw.println(); 13169 needSep = true; 13170 pw.println(" Granted Uri Permissions:"); 13171 printed = true; 13172 printedAnything = true; 13173 } 13174 pw.print(" * UID "); pw.print(uid); pw.println(" holds:"); 13175 for (UriPermission perm : perms.values()) { 13176 pw.print(" "); pw.println(perm); 13177 if (dumpAll) { 13178 perm.dump(pw, " "); 13179 } 13180 } 13181 } 13182 } 13183 13184 if (!printedAnything) { 13185 pw.println(" (nothing)"); 13186 } 13187 } 13188 13189 void dumpPendingIntentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 13190 int opti, boolean dumpAll, String dumpPackage) { 13191 boolean printed = false; 13192 13193 pw.println("ACTIVITY MANAGER PENDING INTENTS (dumpsys activity intents)"); 13194 13195 if (mIntentSenderRecords.size() > 0) { 13196 Iterator<WeakReference<PendingIntentRecord>> it 13197 = mIntentSenderRecords.values().iterator(); 13198 while (it.hasNext()) { 13199 WeakReference<PendingIntentRecord> ref = it.next(); 13200 PendingIntentRecord rec = ref != null ? ref.get(): null; 13201 if (dumpPackage != null && (rec == null 13202 || !dumpPackage.equals(rec.key.packageName))) { 13203 continue; 13204 } 13205 printed = true; 13206 if (rec != null) { 13207 pw.print(" * "); pw.println(rec); 13208 if (dumpAll) { 13209 rec.dump(pw, " "); 13210 } 13211 } else { 13212 pw.print(" * "); pw.println(ref); 13213 } 13214 } 13215 } 13216 13217 if (!printed) { 13218 pw.println(" (nothing)"); 13219 } 13220 } 13221 13222 private static final int dumpProcessList(PrintWriter pw, 13223 ActivityManagerService service, List list, 13224 String prefix, String normalLabel, String persistentLabel, 13225 String dumpPackage) { 13226 int numPers = 0; 13227 final int N = list.size()-1; 13228 for (int i=N; i>=0; i--) { 13229 ProcessRecord r = (ProcessRecord)list.get(i); 13230 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 13231 continue; 13232 } 13233 pw.println(String.format("%s%s #%2d: %s", 13234 prefix, (r.persistent ? persistentLabel : normalLabel), 13235 i, r.toString())); 13236 if (r.persistent) { 13237 numPers++; 13238 } 13239 } 13240 return numPers; 13241 } 13242 13243 private static final boolean dumpProcessOomList(PrintWriter pw, 13244 ActivityManagerService service, List<ProcessRecord> origList, 13245 String prefix, String normalLabel, String persistentLabel, 13246 boolean inclDetails, String dumpPackage) { 13247 13248 ArrayList<Pair<ProcessRecord, Integer>> list 13249 = new ArrayList<Pair<ProcessRecord, Integer>>(origList.size()); 13250 for (int i=0; i<origList.size(); i++) { 13251 ProcessRecord r = origList.get(i); 13252 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 13253 continue; 13254 } 13255 list.add(new Pair<ProcessRecord, Integer>(origList.get(i), i)); 13256 } 13257 13258 if (list.size() <= 0) { 13259 return false; 13260 } 13261 13262 Comparator<Pair<ProcessRecord, Integer>> comparator 13263 = new Comparator<Pair<ProcessRecord, Integer>>() { 13264 @Override 13265 public int compare(Pair<ProcessRecord, Integer> object1, 13266 Pair<ProcessRecord, Integer> object2) { 13267 if (object1.first.setAdj != object2.first.setAdj) { 13268 return object1.first.setAdj > object2.first.setAdj ? -1 : 1; 13269 } 13270 if (object1.second.intValue() != object2.second.intValue()) { 13271 return object1.second.intValue() > object2.second.intValue() ? -1 : 1; 13272 } 13273 return 0; 13274 } 13275 }; 13276 13277 Collections.sort(list, comparator); 13278 13279 final long curRealtime = SystemClock.elapsedRealtime(); 13280 final long realtimeSince = curRealtime - service.mLastPowerCheckRealtime; 13281 final long curUptime = SystemClock.uptimeMillis(); 13282 final long uptimeSince = curUptime - service.mLastPowerCheckUptime; 13283 13284 for (int i=list.size()-1; i>=0; i--) { 13285 ProcessRecord r = list.get(i).first; 13286 String oomAdj = ProcessList.makeOomAdjString(r.setAdj); 13287 char schedGroup; 13288 switch (r.setSchedGroup) { 13289 case Process.THREAD_GROUP_BG_NONINTERACTIVE: 13290 schedGroup = 'B'; 13291 break; 13292 case Process.THREAD_GROUP_DEFAULT: 13293 schedGroup = 'F'; 13294 break; 13295 default: 13296 schedGroup = '?'; 13297 break; 13298 } 13299 char foreground; 13300 if (r.foregroundActivities) { 13301 foreground = 'A'; 13302 } else if (r.foregroundServices) { 13303 foreground = 'S'; 13304 } else { 13305 foreground = ' '; 13306 } 13307 String procState = ProcessList.makeProcStateString(r.curProcState); 13308 pw.print(prefix); 13309 pw.print(r.persistent ? persistentLabel : normalLabel); 13310 pw.print(" #"); 13311 int num = (origList.size()-1)-list.get(i).second; 13312 if (num < 10) pw.print(' '); 13313 pw.print(num); 13314 pw.print(": "); 13315 pw.print(oomAdj); 13316 pw.print(' '); 13317 pw.print(schedGroup); 13318 pw.print('/'); 13319 pw.print(foreground); 13320 pw.print('/'); 13321 pw.print(procState); 13322 pw.print(" trm:"); 13323 if (r.trimMemoryLevel < 10) pw.print(' '); 13324 pw.print(r.trimMemoryLevel); 13325 pw.print(' '); 13326 pw.print(r.toShortString()); 13327 pw.print(" ("); 13328 pw.print(r.adjType); 13329 pw.println(')'); 13330 if (r.adjSource != null || r.adjTarget != null) { 13331 pw.print(prefix); 13332 pw.print(" "); 13333 if (r.adjTarget instanceof ComponentName) { 13334 pw.print(((ComponentName)r.adjTarget).flattenToShortString()); 13335 } else if (r.adjTarget != null) { 13336 pw.print(r.adjTarget.toString()); 13337 } else { 13338 pw.print("{null}"); 13339 } 13340 pw.print("<="); 13341 if (r.adjSource instanceof ProcessRecord) { 13342 pw.print("Proc{"); 13343 pw.print(((ProcessRecord)r.adjSource).toShortString()); 13344 pw.println("}"); 13345 } else if (r.adjSource != null) { 13346 pw.println(r.adjSource.toString()); 13347 } else { 13348 pw.println("{null}"); 13349 } 13350 } 13351 if (inclDetails) { 13352 pw.print(prefix); 13353 pw.print(" "); 13354 pw.print("oom: max="); pw.print(r.maxAdj); 13355 pw.print(" curRaw="); pw.print(r.curRawAdj); 13356 pw.print(" setRaw="); pw.print(r.setRawAdj); 13357 pw.print(" cur="); pw.print(r.curAdj); 13358 pw.print(" set="); pw.println(r.setAdj); 13359 pw.print(prefix); 13360 pw.print(" "); 13361 pw.print("state: cur="); pw.print(ProcessList.makeProcStateString(r.curProcState)); 13362 pw.print(" set="); pw.print(ProcessList.makeProcStateString(r.setProcState)); 13363 pw.print(" lastPss="); pw.print(r.lastPss); 13364 pw.print(" lastCachedPss="); pw.println(r.lastCachedPss); 13365 pw.print(prefix); 13366 pw.print(" "); 13367 pw.print("cached="); pw.print(r.cached); 13368 pw.print(" empty="); pw.print(r.empty); 13369 pw.print(" hasAboveClient="); pw.println(r.hasAboveClient); 13370 13371 if (r.setProcState >= ActivityManager.PROCESS_STATE_SERVICE) { 13372 if (r.lastWakeTime != 0) { 13373 long wtime; 13374 BatteryStatsImpl stats = service.mBatteryStatsService.getActiveStatistics(); 13375 synchronized (stats) { 13376 wtime = stats.getProcessWakeTime(r.info.uid, 13377 r.pid, curRealtime); 13378 } 13379 long timeUsed = wtime - r.lastWakeTime; 13380 pw.print(prefix); 13381 pw.print(" "); 13382 pw.print("keep awake over "); 13383 TimeUtils.formatDuration(realtimeSince, pw); 13384 pw.print(" used "); 13385 TimeUtils.formatDuration(timeUsed, pw); 13386 pw.print(" ("); 13387 pw.print((timeUsed*100)/realtimeSince); 13388 pw.println("%)"); 13389 } 13390 if (r.lastCpuTime != 0) { 13391 long timeUsed = r.curCpuTime - r.lastCpuTime; 13392 pw.print(prefix); 13393 pw.print(" "); 13394 pw.print("run cpu over "); 13395 TimeUtils.formatDuration(uptimeSince, pw); 13396 pw.print(" used "); 13397 TimeUtils.formatDuration(timeUsed, pw); 13398 pw.print(" ("); 13399 pw.print((timeUsed*100)/uptimeSince); 13400 pw.println("%)"); 13401 } 13402 } 13403 } 13404 } 13405 return true; 13406 } 13407 13408 ArrayList<ProcessRecord> collectProcesses(PrintWriter pw, int start, String[] args) { 13409 ArrayList<ProcessRecord> procs; 13410 synchronized (this) { 13411 if (args != null && args.length > start 13412 && args[start].charAt(0) != '-') { 13413 procs = new ArrayList<ProcessRecord>(); 13414 int pid = -1; 13415 try { 13416 pid = Integer.parseInt(args[start]); 13417 } catch (NumberFormatException e) { 13418 } 13419 for (int i=mLruProcesses.size()-1; i>=0; i--) { 13420 ProcessRecord proc = mLruProcesses.get(i); 13421 if (proc.pid == pid) { 13422 procs.add(proc); 13423 } else if (proc.processName.equals(args[start])) { 13424 procs.add(proc); 13425 } 13426 } 13427 if (procs.size() <= 0) { 13428 return null; 13429 } 13430 } else { 13431 procs = new ArrayList<ProcessRecord>(mLruProcesses); 13432 } 13433 } 13434 return procs; 13435 } 13436 13437 final void dumpGraphicsHardwareUsage(FileDescriptor fd, 13438 PrintWriter pw, String[] args) { 13439 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 13440 if (procs == null) { 13441 pw.println("No process found for: " + args[0]); 13442 return; 13443 } 13444 13445 long uptime = SystemClock.uptimeMillis(); 13446 long realtime = SystemClock.elapsedRealtime(); 13447 pw.println("Applications Graphics Acceleration Info:"); 13448 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 13449 13450 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 13451 ProcessRecord r = procs.get(i); 13452 if (r.thread != null) { 13453 pw.println("\n** Graphics info for pid " + r.pid + " [" + r.processName + "] **"); 13454 pw.flush(); 13455 try { 13456 TransferPipe tp = new TransferPipe(); 13457 try { 13458 r.thread.dumpGfxInfo(tp.getWriteFd().getFileDescriptor(), args); 13459 tp.go(fd); 13460 } finally { 13461 tp.kill(); 13462 } 13463 } catch (IOException e) { 13464 pw.println("Failure while dumping the app: " + r); 13465 pw.flush(); 13466 } catch (RemoteException e) { 13467 pw.println("Got a RemoteException while dumping the app " + r); 13468 pw.flush(); 13469 } 13470 } 13471 } 13472 } 13473 13474 final void dumpDbInfo(FileDescriptor fd, PrintWriter pw, String[] args) { 13475 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 13476 if (procs == null) { 13477 pw.println("No process found for: " + args[0]); 13478 return; 13479 } 13480 13481 pw.println("Applications Database Info:"); 13482 13483 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 13484 ProcessRecord r = procs.get(i); 13485 if (r.thread != null) { 13486 pw.println("\n** Database info for pid " + r.pid + " [" + r.processName + "] **"); 13487 pw.flush(); 13488 try { 13489 TransferPipe tp = new TransferPipe(); 13490 try { 13491 r.thread.dumpDbInfo(tp.getWriteFd().getFileDescriptor(), args); 13492 tp.go(fd); 13493 } finally { 13494 tp.kill(); 13495 } 13496 } catch (IOException e) { 13497 pw.println("Failure while dumping the app: " + r); 13498 pw.flush(); 13499 } catch (RemoteException e) { 13500 pw.println("Got a RemoteException while dumping the app " + r); 13501 pw.flush(); 13502 } 13503 } 13504 } 13505 } 13506 13507 final static class MemItem { 13508 final boolean isProc; 13509 final String label; 13510 final String shortLabel; 13511 final long pss; 13512 final int id; 13513 final boolean hasActivities; 13514 ArrayList<MemItem> subitems; 13515 13516 public MemItem(String _label, String _shortLabel, long _pss, int _id, 13517 boolean _hasActivities) { 13518 isProc = true; 13519 label = _label; 13520 shortLabel = _shortLabel; 13521 pss = _pss; 13522 id = _id; 13523 hasActivities = _hasActivities; 13524 } 13525 13526 public MemItem(String _label, String _shortLabel, long _pss, int _id) { 13527 isProc = false; 13528 label = _label; 13529 shortLabel = _shortLabel; 13530 pss = _pss; 13531 id = _id; 13532 hasActivities = false; 13533 } 13534 } 13535 13536 static final void dumpMemItems(PrintWriter pw, String prefix, String tag, 13537 ArrayList<MemItem> items, boolean sort, boolean isCompact) { 13538 if (sort && !isCompact) { 13539 Collections.sort(items, new Comparator<MemItem>() { 13540 @Override 13541 public int compare(MemItem lhs, MemItem rhs) { 13542 if (lhs.pss < rhs.pss) { 13543 return 1; 13544 } else if (lhs.pss > rhs.pss) { 13545 return -1; 13546 } 13547 return 0; 13548 } 13549 }); 13550 } 13551 13552 for (int i=0; i<items.size(); i++) { 13553 MemItem mi = items.get(i); 13554 if (!isCompact) { 13555 pw.print(prefix); pw.printf("%7d kB: ", mi.pss); pw.println(mi.label); 13556 } else if (mi.isProc) { 13557 pw.print("proc,"); pw.print(tag); pw.print(","); pw.print(mi.shortLabel); 13558 pw.print(","); pw.print(mi.id); pw.print(","); pw.print(mi.pss); 13559 pw.println(mi.hasActivities ? ",a" : ",e"); 13560 } else { 13561 pw.print(tag); pw.print(","); pw.print(mi.shortLabel); pw.print(","); 13562 pw.println(mi.pss); 13563 } 13564 if (mi.subitems != null) { 13565 dumpMemItems(pw, prefix + " ", mi.shortLabel, mi.subitems, 13566 true, isCompact); 13567 } 13568 } 13569 } 13570 13571 // These are in KB. 13572 static final long[] DUMP_MEM_BUCKETS = new long[] { 13573 5*1024, 7*1024, 10*1024, 15*1024, 20*1024, 30*1024, 40*1024, 80*1024, 13574 120*1024, 160*1024, 200*1024, 13575 250*1024, 300*1024, 350*1024, 400*1024, 500*1024, 600*1024, 800*1024, 13576 1*1024*1024, 2*1024*1024, 5*1024*1024, 10*1024*1024, 20*1024*1024 13577 }; 13578 13579 static final void appendMemBucket(StringBuilder out, long memKB, String label, 13580 boolean stackLike) { 13581 int start = label.lastIndexOf('.'); 13582 if (start >= 0) start++; 13583 else start = 0; 13584 int end = label.length(); 13585 for (int i=0; i<DUMP_MEM_BUCKETS.length; i++) { 13586 if (DUMP_MEM_BUCKETS[i] >= memKB) { 13587 long bucket = DUMP_MEM_BUCKETS[i]/1024; 13588 out.append(bucket); 13589 out.append(stackLike ? "MB." : "MB "); 13590 out.append(label, start, end); 13591 return; 13592 } 13593 } 13594 out.append(memKB/1024); 13595 out.append(stackLike ? "MB." : "MB "); 13596 out.append(label, start, end); 13597 } 13598 13599 static final int[] DUMP_MEM_OOM_ADJ = new int[] { 13600 ProcessList.NATIVE_ADJ, 13601 ProcessList.SYSTEM_ADJ, ProcessList.PERSISTENT_PROC_ADJ, ProcessList.FOREGROUND_APP_ADJ, 13602 ProcessList.VISIBLE_APP_ADJ, ProcessList.PERCEPTIBLE_APP_ADJ, 13603 ProcessList.BACKUP_APP_ADJ, ProcessList.HEAVY_WEIGHT_APP_ADJ, 13604 ProcessList.SERVICE_ADJ, ProcessList.HOME_APP_ADJ, 13605 ProcessList.PREVIOUS_APP_ADJ, ProcessList.SERVICE_B_ADJ, ProcessList.CACHED_APP_MAX_ADJ 13606 }; 13607 static final String[] DUMP_MEM_OOM_LABEL = new String[] { 13608 "Native", 13609 "System", "Persistent", "Foreground", 13610 "Visible", "Perceptible", 13611 "Heavy Weight", "Backup", 13612 "A Services", "Home", 13613 "Previous", "B Services", "Cached" 13614 }; 13615 static final String[] DUMP_MEM_OOM_COMPACT_LABEL = new String[] { 13616 "native", 13617 "sys", "pers", "fore", 13618 "vis", "percept", 13619 "heavy", "backup", 13620 "servicea", "home", 13621 "prev", "serviceb", "cached" 13622 }; 13623 13624 private final void dumpApplicationMemoryUsageHeader(PrintWriter pw, long uptime, 13625 long realtime, boolean isCheckinRequest, boolean isCompact) { 13626 if (isCheckinRequest || isCompact) { 13627 // short checkin version 13628 pw.print("time,"); pw.print(uptime); pw.print(","); pw.println(realtime); 13629 } else { 13630 pw.println("Applications Memory Usage (kB):"); 13631 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 13632 } 13633 } 13634 13635 final void dumpApplicationMemoryUsage(FileDescriptor fd, 13636 PrintWriter pw, String prefix, String[] args, boolean brief, PrintWriter categoryPw) { 13637 boolean dumpDetails = false; 13638 boolean dumpFullDetails = false; 13639 boolean dumpDalvik = false; 13640 boolean oomOnly = false; 13641 boolean isCompact = false; 13642 boolean localOnly = false; 13643 13644 int opti = 0; 13645 while (opti < args.length) { 13646 String opt = args[opti]; 13647 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 13648 break; 13649 } 13650 opti++; 13651 if ("-a".equals(opt)) { 13652 dumpDetails = true; 13653 dumpFullDetails = true; 13654 dumpDalvik = true; 13655 } else if ("-d".equals(opt)) { 13656 dumpDalvik = true; 13657 } else if ("-c".equals(opt)) { 13658 isCompact = true; 13659 } else if ("--oom".equals(opt)) { 13660 oomOnly = true; 13661 } else if ("--local".equals(opt)) { 13662 localOnly = true; 13663 } else if ("-h".equals(opt)) { 13664 pw.println("meminfo dump options: [-a] [-d] [-c] [--oom] [process]"); 13665 pw.println(" -a: include all available information for each process."); 13666 pw.println(" -d: include dalvik details when dumping process details."); 13667 pw.println(" -c: dump in a compact machine-parseable representation."); 13668 pw.println(" --oom: only show processes organized by oom adj."); 13669 pw.println(" --local: only collect details locally, don't call process."); 13670 pw.println("If [process] is specified it can be the name or "); 13671 pw.println("pid of a specific process to dump."); 13672 return; 13673 } else { 13674 pw.println("Unknown argument: " + opt + "; use -h for help"); 13675 } 13676 } 13677 13678 final boolean isCheckinRequest = scanArgs(args, "--checkin"); 13679 long uptime = SystemClock.uptimeMillis(); 13680 long realtime = SystemClock.elapsedRealtime(); 13681 final long[] tmpLong = new long[1]; 13682 13683 ArrayList<ProcessRecord> procs = collectProcesses(pw, opti, args); 13684 if (procs == null) { 13685 // No Java processes. Maybe they want to print a native process. 13686 if (args != null && args.length > opti 13687 && args[opti].charAt(0) != '-') { 13688 ArrayList<ProcessCpuTracker.Stats> nativeProcs 13689 = new ArrayList<ProcessCpuTracker.Stats>(); 13690 updateCpuStatsNow(); 13691 int findPid = -1; 13692 try { 13693 findPid = Integer.parseInt(args[opti]); 13694 } catch (NumberFormatException e) { 13695 } 13696 synchronized (mProcessCpuThread) { 13697 final int N = mProcessCpuTracker.countStats(); 13698 for (int i=0; i<N; i++) { 13699 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 13700 if (st.pid == findPid || (st.baseName != null 13701 && st.baseName.equals(args[opti]))) { 13702 nativeProcs.add(st); 13703 } 13704 } 13705 } 13706 if (nativeProcs.size() > 0) { 13707 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, 13708 isCompact); 13709 Debug.MemoryInfo mi = null; 13710 for (int i = nativeProcs.size() - 1 ; i >= 0 ; i--) { 13711 final ProcessCpuTracker.Stats r = nativeProcs.get(i); 13712 final int pid = r.pid; 13713 if (!isCheckinRequest && dumpDetails) { 13714 pw.println("\n** MEMINFO in pid " + pid + " [" + r.baseName + "] **"); 13715 } 13716 if (mi == null) { 13717 mi = new Debug.MemoryInfo(); 13718 } 13719 if (dumpDetails || (!brief && !oomOnly)) { 13720 Debug.getMemoryInfo(pid, mi); 13721 } else { 13722 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 13723 mi.dalvikPrivateDirty = (int)tmpLong[0]; 13724 } 13725 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 13726 dumpDalvik, pid, r.baseName, 0, 0, 0, 0, 0, 0); 13727 if (isCheckinRequest) { 13728 pw.println(); 13729 } 13730 } 13731 return; 13732 } 13733 } 13734 pw.println("No process found for: " + args[opti]); 13735 return; 13736 } 13737 13738 if (!brief && !oomOnly && (procs.size() == 1 || isCheckinRequest)) { 13739 dumpDetails = true; 13740 } 13741 13742 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, isCompact); 13743 13744 String[] innerArgs = new String[args.length-opti]; 13745 System.arraycopy(args, opti, innerArgs, 0, args.length-opti); 13746 13747 ArrayList<MemItem> procMems = new ArrayList<MemItem>(); 13748 final SparseArray<MemItem> procMemsMap = new SparseArray<MemItem>(); 13749 long nativePss=0, dalvikPss=0, otherPss=0; 13750 long[] miscPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 13751 13752 long oomPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 13753 ArrayList<MemItem>[] oomProcs = (ArrayList<MemItem>[]) 13754 new ArrayList[DUMP_MEM_OOM_LABEL.length]; 13755 13756 long totalPss = 0; 13757 long cachedPss = 0; 13758 13759 Debug.MemoryInfo mi = null; 13760 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 13761 final ProcessRecord r = procs.get(i); 13762 final IApplicationThread thread; 13763 final int pid; 13764 final int oomAdj; 13765 final boolean hasActivities; 13766 synchronized (this) { 13767 thread = r.thread; 13768 pid = r.pid; 13769 oomAdj = r.getSetAdjWithServices(); 13770 hasActivities = r.activities.size() > 0; 13771 } 13772 if (thread != null) { 13773 if (!isCheckinRequest && dumpDetails) { 13774 pw.println("\n** MEMINFO in pid " + pid + " [" + r.processName + "] **"); 13775 } 13776 if (mi == null) { 13777 mi = new Debug.MemoryInfo(); 13778 } 13779 if (dumpDetails || (!brief && !oomOnly)) { 13780 Debug.getMemoryInfo(pid, mi); 13781 } else { 13782 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 13783 mi.dalvikPrivateDirty = (int)tmpLong[0]; 13784 } 13785 if (dumpDetails) { 13786 if (localOnly) { 13787 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 13788 dumpDalvik, pid, r.processName, 0, 0, 0, 0, 0, 0); 13789 if (isCheckinRequest) { 13790 pw.println(); 13791 } 13792 } else { 13793 try { 13794 pw.flush(); 13795 thread.dumpMemInfo(fd, mi, isCheckinRequest, dumpFullDetails, 13796 dumpDalvik, innerArgs); 13797 } catch (RemoteException e) { 13798 if (!isCheckinRequest) { 13799 pw.println("Got RemoteException!"); 13800 pw.flush(); 13801 } 13802 } 13803 } 13804 } 13805 13806 final long myTotalPss = mi.getTotalPss(); 13807 final long myTotalUss = mi.getTotalUss(); 13808 13809 synchronized (this) { 13810 if (r.thread != null && oomAdj == r.getSetAdjWithServices()) { 13811 // Record this for posterity if the process has been stable. 13812 r.baseProcessTracker.addPss(myTotalPss, myTotalUss, true, r.pkgList); 13813 } 13814 } 13815 13816 if (!isCheckinRequest && mi != null) { 13817 totalPss += myTotalPss; 13818 MemItem pssItem = new MemItem(r.processName + " (pid " + pid + 13819 (hasActivities ? " / activities)" : ")"), 13820 r.processName, myTotalPss, pid, hasActivities); 13821 procMems.add(pssItem); 13822 procMemsMap.put(pid, pssItem); 13823 13824 nativePss += mi.nativePss; 13825 dalvikPss += mi.dalvikPss; 13826 otherPss += mi.otherPss; 13827 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 13828 long mem = mi.getOtherPss(j); 13829 miscPss[j] += mem; 13830 otherPss -= mem; 13831 } 13832 13833 if (oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 13834 cachedPss += myTotalPss; 13835 } 13836 13837 for (int oomIndex=0; oomIndex<oomPss.length; oomIndex++) { 13838 if (oomAdj <= DUMP_MEM_OOM_ADJ[oomIndex] 13839 || oomIndex == (oomPss.length-1)) { 13840 oomPss[oomIndex] += myTotalPss; 13841 if (oomProcs[oomIndex] == null) { 13842 oomProcs[oomIndex] = new ArrayList<MemItem>(); 13843 } 13844 oomProcs[oomIndex].add(pssItem); 13845 break; 13846 } 13847 } 13848 } 13849 } 13850 } 13851 13852 long nativeProcTotalPss = 0; 13853 13854 if (!isCheckinRequest && procs.size() > 1) { 13855 // If we are showing aggregations, also look for native processes to 13856 // include so that our aggregations are more accurate. 13857 updateCpuStatsNow(); 13858 synchronized (mProcessCpuThread) { 13859 final int N = mProcessCpuTracker.countStats(); 13860 for (int i=0; i<N; i++) { 13861 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 13862 if (st.vsize > 0 && procMemsMap.indexOfKey(st.pid) < 0) { 13863 if (mi == null) { 13864 mi = new Debug.MemoryInfo(); 13865 } 13866 if (!brief && !oomOnly) { 13867 Debug.getMemoryInfo(st.pid, mi); 13868 } else { 13869 mi.nativePss = (int)Debug.getPss(st.pid, tmpLong); 13870 mi.nativePrivateDirty = (int)tmpLong[0]; 13871 } 13872 13873 final long myTotalPss = mi.getTotalPss(); 13874 totalPss += myTotalPss; 13875 nativeProcTotalPss += myTotalPss; 13876 13877 MemItem pssItem = new MemItem(st.name + " (pid " + st.pid + ")", 13878 st.name, myTotalPss, st.pid, false); 13879 procMems.add(pssItem); 13880 13881 nativePss += mi.nativePss; 13882 dalvikPss += mi.dalvikPss; 13883 otherPss += mi.otherPss; 13884 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 13885 long mem = mi.getOtherPss(j); 13886 miscPss[j] += mem; 13887 otherPss -= mem; 13888 } 13889 oomPss[0] += myTotalPss; 13890 if (oomProcs[0] == null) { 13891 oomProcs[0] = new ArrayList<MemItem>(); 13892 } 13893 oomProcs[0].add(pssItem); 13894 } 13895 } 13896 } 13897 13898 ArrayList<MemItem> catMems = new ArrayList<MemItem>(); 13899 13900 catMems.add(new MemItem("Native", "Native", nativePss, -1)); 13901 catMems.add(new MemItem("Dalvik", "Dalvik", dalvikPss, -2)); 13902 catMems.add(new MemItem("Unknown", "Unknown", otherPss, -3)); 13903 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 13904 String label = Debug.MemoryInfo.getOtherLabel(j); 13905 catMems.add(new MemItem(label, label, miscPss[j], j)); 13906 } 13907 13908 ArrayList<MemItem> oomMems = new ArrayList<MemItem>(); 13909 for (int j=0; j<oomPss.length; j++) { 13910 if (oomPss[j] != 0) { 13911 String label = isCompact ? DUMP_MEM_OOM_COMPACT_LABEL[j] 13912 : DUMP_MEM_OOM_LABEL[j]; 13913 MemItem item = new MemItem(label, label, oomPss[j], 13914 DUMP_MEM_OOM_ADJ[j]); 13915 item.subitems = oomProcs[j]; 13916 oomMems.add(item); 13917 } 13918 } 13919 13920 if (!brief && !oomOnly && !isCompact) { 13921 pw.println(); 13922 pw.println("Total PSS by process:"); 13923 dumpMemItems(pw, " ", "proc", procMems, true, isCompact); 13924 pw.println(); 13925 } 13926 if (!isCompact) { 13927 pw.println("Total PSS by OOM adjustment:"); 13928 } 13929 dumpMemItems(pw, " ", "oom", oomMems, false, isCompact); 13930 if (!brief && !oomOnly) { 13931 PrintWriter out = categoryPw != null ? categoryPw : pw; 13932 if (!isCompact) { 13933 out.println(); 13934 out.println("Total PSS by category:"); 13935 } 13936 dumpMemItems(out, " ", "cat", catMems, true, isCompact); 13937 } 13938 if (!isCompact) { 13939 pw.println(); 13940 } 13941 MemInfoReader memInfo = new MemInfoReader(); 13942 memInfo.readMemInfo(); 13943 if (nativeProcTotalPss > 0) { 13944 synchronized (this) { 13945 mProcessStats.addSysMemUsageLocked(memInfo.getCachedSizeKb(), 13946 memInfo.getFreeSizeKb(), memInfo.getZramTotalSizeKb(), 13947 memInfo.getBuffersSizeKb()+memInfo.getShmemSizeKb()+memInfo.getSlabSizeKb(), 13948 nativeProcTotalPss); 13949 } 13950 } 13951 if (!brief) { 13952 if (!isCompact) { 13953 pw.print("Total RAM: "); pw.print(memInfo.getTotalSizeKb()); 13954 pw.print(" kB (status "); 13955 switch (mLastMemoryLevel) { 13956 case ProcessStats.ADJ_MEM_FACTOR_NORMAL: 13957 pw.println("normal)"); 13958 break; 13959 case ProcessStats.ADJ_MEM_FACTOR_MODERATE: 13960 pw.println("moderate)"); 13961 break; 13962 case ProcessStats.ADJ_MEM_FACTOR_LOW: 13963 pw.println("low)"); 13964 break; 13965 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 13966 pw.println("critical)"); 13967 break; 13968 default: 13969 pw.print(mLastMemoryLevel); 13970 pw.println(")"); 13971 break; 13972 } 13973 pw.print(" Free RAM: "); pw.print(cachedPss + memInfo.getCachedSizeKb() 13974 + memInfo.getFreeSizeKb()); pw.print(" kB ("); 13975 pw.print(cachedPss); pw.print(" cached pss + "); 13976 pw.print(memInfo.getCachedSizeKb()); pw.print(" cached + "); 13977 pw.print(memInfo.getFreeSizeKb()); pw.println(" free)"); 13978 } else { 13979 pw.print("ram,"); pw.print(memInfo.getTotalSizeKb()); pw.print(","); 13980 pw.print(cachedPss + memInfo.getCachedSizeKb() 13981 + memInfo.getFreeSizeKb()); pw.print(","); 13982 pw.println(totalPss - cachedPss); 13983 } 13984 } 13985 if (!isCompact) { 13986 pw.print(" Used RAM: "); pw.print(totalPss - cachedPss 13987 + memInfo.getBuffersSizeKb() + memInfo.getShmemSizeKb() 13988 + memInfo.getSlabSizeKb()); pw.print(" kB ("); 13989 pw.print(totalPss - cachedPss); pw.print(" used pss + "); 13990 pw.print(memInfo.getBuffersSizeKb()); pw.print(" buffers + "); 13991 pw.print(memInfo.getShmemSizeKb()); pw.print(" shmem + "); 13992 pw.print(memInfo.getSlabSizeKb()); pw.println(" slab)"); 13993 pw.print(" Lost RAM: "); pw.print(memInfo.getTotalSizeKb() 13994 - totalPss - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 13995 - memInfo.getBuffersSizeKb() - memInfo.getShmemSizeKb() 13996 - memInfo.getSlabSizeKb()); pw.println(" kB"); 13997 } 13998 if (!brief) { 13999 if (memInfo.getZramTotalSizeKb() != 0) { 14000 if (!isCompact) { 14001 pw.print(" ZRAM: "); pw.print(memInfo.getZramTotalSizeKb()); 14002 pw.print(" kB physical used for "); 14003 pw.print(memInfo.getSwapTotalSizeKb() 14004 - memInfo.getSwapFreeSizeKb()); 14005 pw.print(" kB in swap ("); 14006 pw.print(memInfo.getSwapTotalSizeKb()); 14007 pw.println(" kB total swap)"); 14008 } else { 14009 pw.print("zram,"); pw.print(memInfo.getZramTotalSizeKb()); pw.print(","); 14010 pw.print(memInfo.getSwapTotalSizeKb()); pw.print(","); 14011 pw.println(memInfo.getSwapFreeSizeKb()); 14012 } 14013 } 14014 final int[] SINGLE_LONG_FORMAT = new int[] { 14015 Process.PROC_SPACE_TERM|Process.PROC_OUT_LONG 14016 }; 14017 long[] longOut = new long[1]; 14018 Process.readProcFile("/sys/kernel/mm/ksm/pages_shared", 14019 SINGLE_LONG_FORMAT, null, longOut, null); 14020 long shared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 14021 longOut[0] = 0; 14022 Process.readProcFile("/sys/kernel/mm/ksm/pages_sharing", 14023 SINGLE_LONG_FORMAT, null, longOut, null); 14024 long sharing = longOut[0] * ProcessList.PAGE_SIZE / 1024; 14025 longOut[0] = 0; 14026 Process.readProcFile("/sys/kernel/mm/ksm/pages_unshared", 14027 SINGLE_LONG_FORMAT, null, longOut, null); 14028 long unshared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 14029 longOut[0] = 0; 14030 Process.readProcFile("/sys/kernel/mm/ksm/pages_volatile", 14031 SINGLE_LONG_FORMAT, null, longOut, null); 14032 long voltile = longOut[0] * ProcessList.PAGE_SIZE / 1024; 14033 if (!isCompact) { 14034 if (sharing != 0 || shared != 0 || unshared != 0 || voltile != 0) { 14035 pw.print(" KSM: "); pw.print(sharing); 14036 pw.print(" kB saved from shared "); 14037 pw.print(shared); pw.println(" kB"); 14038 pw.print(" "); pw.print(unshared); pw.print(" kB unshared; "); 14039 pw.print(voltile); pw.println(" kB volatile"); 14040 } 14041 pw.print(" Tuning: "); 14042 pw.print(ActivityManager.staticGetMemoryClass()); 14043 pw.print(" (large "); 14044 pw.print(ActivityManager.staticGetLargeMemoryClass()); 14045 pw.print("), oom "); 14046 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 14047 pw.print(" kB"); 14048 pw.print(", restore limit "); 14049 pw.print(mProcessList.getCachedRestoreThresholdKb()); 14050 pw.print(" kB"); 14051 if (ActivityManager.isLowRamDeviceStatic()) { 14052 pw.print(" (low-ram)"); 14053 } 14054 if (ActivityManager.isHighEndGfx()) { 14055 pw.print(" (high-end-gfx)"); 14056 } 14057 pw.println(); 14058 } else { 14059 pw.print("ksm,"); pw.print(sharing); pw.print(","); 14060 pw.print(shared); pw.print(","); pw.print(unshared); pw.print(","); 14061 pw.println(voltile); 14062 pw.print("tuning,"); 14063 pw.print(ActivityManager.staticGetMemoryClass()); 14064 pw.print(','); 14065 pw.print(ActivityManager.staticGetLargeMemoryClass()); 14066 pw.print(','); 14067 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 14068 if (ActivityManager.isLowRamDeviceStatic()) { 14069 pw.print(",low-ram"); 14070 } 14071 if (ActivityManager.isHighEndGfx()) { 14072 pw.print(",high-end-gfx"); 14073 } 14074 pw.println(); 14075 } 14076 } 14077 } 14078 } 14079 14080 /** 14081 * Searches array of arguments for the specified string 14082 * @param args array of argument strings 14083 * @param value value to search for 14084 * @return true if the value is contained in the array 14085 */ 14086 private static boolean scanArgs(String[] args, String value) { 14087 if (args != null) { 14088 for (String arg : args) { 14089 if (value.equals(arg)) { 14090 return true; 14091 } 14092 } 14093 } 14094 return false; 14095 } 14096 14097 private final boolean removeDyingProviderLocked(ProcessRecord proc, 14098 ContentProviderRecord cpr, boolean always) { 14099 final boolean inLaunching = mLaunchingProviders.contains(cpr); 14100 14101 if (!inLaunching || always) { 14102 synchronized (cpr) { 14103 cpr.launchingApp = null; 14104 cpr.notifyAll(); 14105 } 14106 mProviderMap.removeProviderByClass(cpr.name, UserHandle.getUserId(cpr.uid)); 14107 String names[] = cpr.info.authority.split(";"); 14108 for (int j = 0; j < names.length; j++) { 14109 mProviderMap.removeProviderByName(names[j], UserHandle.getUserId(cpr.uid)); 14110 } 14111 } 14112 14113 for (int i=0; i<cpr.connections.size(); i++) { 14114 ContentProviderConnection conn = cpr.connections.get(i); 14115 if (conn.waiting) { 14116 // If this connection is waiting for the provider, then we don't 14117 // need to mess with its process unless we are always removing 14118 // or for some reason the provider is not currently launching. 14119 if (inLaunching && !always) { 14120 continue; 14121 } 14122 } 14123 ProcessRecord capp = conn.client; 14124 conn.dead = true; 14125 if (conn.stableCount > 0) { 14126 if (!capp.persistent && capp.thread != null 14127 && capp.pid != 0 14128 && capp.pid != MY_PID) { 14129 capp.kill("depends on provider " 14130 + cpr.name.flattenToShortString() 14131 + " in dying proc " + (proc != null ? proc.processName : "??"), true); 14132 } 14133 } else if (capp.thread != null && conn.provider.provider != null) { 14134 try { 14135 capp.thread.unstableProviderDied(conn.provider.provider.asBinder()); 14136 } catch (RemoteException e) { 14137 } 14138 // In the protocol here, we don't expect the client to correctly 14139 // clean up this connection, we'll just remove it. 14140 cpr.connections.remove(i); 14141 conn.client.conProviders.remove(conn); 14142 } 14143 } 14144 14145 if (inLaunching && always) { 14146 mLaunchingProviders.remove(cpr); 14147 } 14148 return inLaunching; 14149 } 14150 14151 /** 14152 * Main code for cleaning up a process when it has gone away. This is 14153 * called both as a result of the process dying, or directly when stopping 14154 * a process when running in single process mode. 14155 */ 14156 private final void cleanUpApplicationRecordLocked(ProcessRecord app, 14157 boolean restarting, boolean allowRestart, int index) { 14158 if (index >= 0) { 14159 removeLruProcessLocked(app); 14160 ProcessList.remove(app.pid); 14161 } 14162 14163 mProcessesToGc.remove(app); 14164 mPendingPssProcesses.remove(app); 14165 14166 // Dismiss any open dialogs. 14167 if (app.crashDialog != null && !app.forceCrashReport) { 14168 app.crashDialog.dismiss(); 14169 app.crashDialog = null; 14170 } 14171 if (app.anrDialog != null) { 14172 app.anrDialog.dismiss(); 14173 app.anrDialog = null; 14174 } 14175 if (app.waitDialog != null) { 14176 app.waitDialog.dismiss(); 14177 app.waitDialog = null; 14178 } 14179 14180 app.crashing = false; 14181 app.notResponding = false; 14182 14183 app.resetPackageList(mProcessStats); 14184 app.unlinkDeathRecipient(); 14185 app.makeInactive(mProcessStats); 14186 app.waitingToKill = null; 14187 app.forcingToForeground = null; 14188 updateProcessForegroundLocked(app, false, false); 14189 app.foregroundActivities = false; 14190 app.hasShownUi = false; 14191 app.treatLikeActivity = false; 14192 app.hasAboveClient = false; 14193 app.hasClientActivities = false; 14194 14195 mServices.killServicesLocked(app, allowRestart); 14196 14197 boolean restart = false; 14198 14199 // Remove published content providers. 14200 for (int i=app.pubProviders.size()-1; i>=0; i--) { 14201 ContentProviderRecord cpr = app.pubProviders.valueAt(i); 14202 final boolean always = app.bad || !allowRestart; 14203 if (removeDyingProviderLocked(app, cpr, always) || always) { 14204 // We left the provider in the launching list, need to 14205 // restart it. 14206 restart = true; 14207 } 14208 14209 cpr.provider = null; 14210 cpr.proc = null; 14211 } 14212 app.pubProviders.clear(); 14213 14214 // Take care of any launching providers waiting for this process. 14215 if (checkAppInLaunchingProvidersLocked(app, false)) { 14216 restart = true; 14217 } 14218 14219 // Unregister from connected content providers. 14220 if (!app.conProviders.isEmpty()) { 14221 for (int i=0; i<app.conProviders.size(); i++) { 14222 ContentProviderConnection conn = app.conProviders.get(i); 14223 conn.provider.connections.remove(conn); 14224 } 14225 app.conProviders.clear(); 14226 } 14227 14228 // At this point there may be remaining entries in mLaunchingProviders 14229 // where we were the only one waiting, so they are no longer of use. 14230 // Look for these and clean up if found. 14231 // XXX Commented out for now. Trying to figure out a way to reproduce 14232 // the actual situation to identify what is actually going on. 14233 if (false) { 14234 for (int i=0; i<mLaunchingProviders.size(); i++) { 14235 ContentProviderRecord cpr = (ContentProviderRecord) 14236 mLaunchingProviders.get(i); 14237 if (cpr.connections.size() <= 0 && !cpr.hasExternalProcessHandles()) { 14238 synchronized (cpr) { 14239 cpr.launchingApp = null; 14240 cpr.notifyAll(); 14241 } 14242 } 14243 } 14244 } 14245 14246 skipCurrentReceiverLocked(app); 14247 14248 // Unregister any receivers. 14249 for (int i=app.receivers.size()-1; i>=0; i--) { 14250 removeReceiverLocked(app.receivers.valueAt(i)); 14251 } 14252 app.receivers.clear(); 14253 14254 // If the app is undergoing backup, tell the backup manager about it 14255 if (mBackupTarget != null && app.pid == mBackupTarget.app.pid) { 14256 if (DEBUG_BACKUP || DEBUG_CLEANUP) Slog.d(TAG, "App " 14257 + mBackupTarget.appInfo + " died during backup"); 14258 try { 14259 IBackupManager bm = IBackupManager.Stub.asInterface( 14260 ServiceManager.getService(Context.BACKUP_SERVICE)); 14261 bm.agentDisconnected(app.info.packageName); 14262 } catch (RemoteException e) { 14263 // can't happen; backup manager is local 14264 } 14265 } 14266 14267 for (int i = mPendingProcessChanges.size()-1; i>=0; i--) { 14268 ProcessChangeItem item = mPendingProcessChanges.get(i); 14269 if (item.pid == app.pid) { 14270 mPendingProcessChanges.remove(i); 14271 mAvailProcessChanges.add(item); 14272 } 14273 } 14274 mHandler.obtainMessage(DISPATCH_PROCESS_DIED, app.pid, app.info.uid, null).sendToTarget(); 14275 14276 // If the caller is restarting this app, then leave it in its 14277 // current lists and let the caller take care of it. 14278 if (restarting) { 14279 return; 14280 } 14281 14282 if (!app.persistent || app.isolated) { 14283 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, 14284 "Removing non-persistent process during cleanup: " + app); 14285 mProcessNames.remove(app.processName, app.uid); 14286 mIsolatedProcesses.remove(app.uid); 14287 if (mHeavyWeightProcess == app) { 14288 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 14289 mHeavyWeightProcess.userId, 0)); 14290 mHeavyWeightProcess = null; 14291 } 14292 } else if (!app.removed) { 14293 // This app is persistent, so we need to keep its record around. 14294 // If it is not already on the pending app list, add it there 14295 // and start a new process for it. 14296 if (mPersistentStartingProcesses.indexOf(app) < 0) { 14297 mPersistentStartingProcesses.add(app); 14298 restart = true; 14299 } 14300 } 14301 if ((DEBUG_PROCESSES || DEBUG_CLEANUP) && mProcessesOnHold.contains(app)) Slog.v(TAG, 14302 "Clean-up removing on hold: " + app); 14303 mProcessesOnHold.remove(app); 14304 14305 if (app == mHomeProcess) { 14306 mHomeProcess = null; 14307 } 14308 if (app == mPreviousProcess) { 14309 mPreviousProcess = null; 14310 } 14311 14312 if (restart && !app.isolated) { 14313 // We have components that still need to be running in the 14314 // process, so re-launch it. 14315 mProcessNames.put(app.processName, app.uid, app); 14316 startProcessLocked(app, "restart", app.processName); 14317 } else if (app.pid > 0 && app.pid != MY_PID) { 14318 // Goodbye! 14319 boolean removed; 14320 synchronized (mPidsSelfLocked) { 14321 mPidsSelfLocked.remove(app.pid); 14322 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 14323 } 14324 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 14325 if (app.isolated) { 14326 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 14327 } 14328 app.setPid(0); 14329 } 14330 } 14331 14332 boolean checkAppInLaunchingProvidersLocked(ProcessRecord app, boolean alwaysBad) { 14333 // Look through the content providers we are waiting to have launched, 14334 // and if any run in this process then either schedule a restart of 14335 // the process or kill the client waiting for it if this process has 14336 // gone bad. 14337 int NL = mLaunchingProviders.size(); 14338 boolean restart = false; 14339 for (int i=0; i<NL; i++) { 14340 ContentProviderRecord cpr = mLaunchingProviders.get(i); 14341 if (cpr.launchingApp == app) { 14342 if (!alwaysBad && !app.bad) { 14343 restart = true; 14344 } else { 14345 removeDyingProviderLocked(app, cpr, true); 14346 // cpr should have been removed from mLaunchingProviders 14347 NL = mLaunchingProviders.size(); 14348 i--; 14349 } 14350 } 14351 } 14352 return restart; 14353 } 14354 14355 // ========================================================= 14356 // SERVICES 14357 // ========================================================= 14358 14359 @Override 14360 public List<ActivityManager.RunningServiceInfo> getServices(int maxNum, 14361 int flags) { 14362 enforceNotIsolatedCaller("getServices"); 14363 synchronized (this) { 14364 return mServices.getRunningServiceInfoLocked(maxNum, flags); 14365 } 14366 } 14367 14368 @Override 14369 public PendingIntent getRunningServiceControlPanel(ComponentName name) { 14370 enforceNotIsolatedCaller("getRunningServiceControlPanel"); 14371 synchronized (this) { 14372 return mServices.getRunningServiceControlPanelLocked(name); 14373 } 14374 } 14375 14376 @Override 14377 public ComponentName startService(IApplicationThread caller, Intent service, 14378 String resolvedType, int userId) { 14379 enforceNotIsolatedCaller("startService"); 14380 // Refuse possible leaked file descriptors 14381 if (service != null && service.hasFileDescriptors() == true) { 14382 throw new IllegalArgumentException("File descriptors passed in Intent"); 14383 } 14384 14385 if (DEBUG_SERVICE) 14386 Slog.v(TAG, "startService: " + service + " type=" + resolvedType); 14387 synchronized(this) { 14388 final int callingPid = Binder.getCallingPid(); 14389 final int callingUid = Binder.getCallingUid(); 14390 final long origId = Binder.clearCallingIdentity(); 14391 ComponentName res = mServices.startServiceLocked(caller, service, 14392 resolvedType, callingPid, callingUid, userId); 14393 Binder.restoreCallingIdentity(origId); 14394 return res; 14395 } 14396 } 14397 14398 ComponentName startServiceInPackage(int uid, 14399 Intent service, String resolvedType, int userId) { 14400 synchronized(this) { 14401 if (DEBUG_SERVICE) 14402 Slog.v(TAG, "startServiceInPackage: " + service + " type=" + resolvedType); 14403 final long origId = Binder.clearCallingIdentity(); 14404 ComponentName res = mServices.startServiceLocked(null, service, 14405 resolvedType, -1, uid, userId); 14406 Binder.restoreCallingIdentity(origId); 14407 return res; 14408 } 14409 } 14410 14411 @Override 14412 public int stopService(IApplicationThread caller, Intent service, 14413 String resolvedType, int userId) { 14414 enforceNotIsolatedCaller("stopService"); 14415 // Refuse possible leaked file descriptors 14416 if (service != null && service.hasFileDescriptors() == true) { 14417 throw new IllegalArgumentException("File descriptors passed in Intent"); 14418 } 14419 14420 synchronized(this) { 14421 return mServices.stopServiceLocked(caller, service, resolvedType, userId); 14422 } 14423 } 14424 14425 @Override 14426 public IBinder peekService(Intent service, String resolvedType) { 14427 enforceNotIsolatedCaller("peekService"); 14428 // Refuse possible leaked file descriptors 14429 if (service != null && service.hasFileDescriptors() == true) { 14430 throw new IllegalArgumentException("File descriptors passed in Intent"); 14431 } 14432 synchronized(this) { 14433 return mServices.peekServiceLocked(service, resolvedType); 14434 } 14435 } 14436 14437 @Override 14438 public boolean stopServiceToken(ComponentName className, IBinder token, 14439 int startId) { 14440 synchronized(this) { 14441 return mServices.stopServiceTokenLocked(className, token, startId); 14442 } 14443 } 14444 14445 @Override 14446 public void setServiceForeground(ComponentName className, IBinder token, 14447 int id, Notification notification, boolean removeNotification) { 14448 synchronized(this) { 14449 mServices.setServiceForegroundLocked(className, token, id, notification, 14450 removeNotification); 14451 } 14452 } 14453 14454 @Override 14455 public int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 14456 boolean requireFull, String name, String callerPackage) { 14457 return handleIncomingUser(callingPid, callingUid, userId, allowAll, 14458 requireFull ? ALLOW_FULL_ONLY : ALLOW_NON_FULL, name, callerPackage); 14459 } 14460 14461 int unsafeConvertIncomingUser(int userId) { 14462 return (userId == UserHandle.USER_CURRENT || userId == UserHandle.USER_CURRENT_OR_SELF) 14463 ? mCurrentUserId : userId; 14464 } 14465 14466 int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 14467 int allowMode, String name, String callerPackage) { 14468 final int callingUserId = UserHandle.getUserId(callingUid); 14469 if (callingUserId == userId) { 14470 return userId; 14471 } 14472 14473 // Note that we may be accessing mCurrentUserId outside of a lock... 14474 // shouldn't be a big deal, if this is being called outside 14475 // of a locked context there is intrinsically a race with 14476 // the value the caller will receive and someone else changing it. 14477 // We assume that USER_CURRENT_OR_SELF will use the current user; later 14478 // we will switch to the calling user if access to the current user fails. 14479 int targetUserId = unsafeConvertIncomingUser(userId); 14480 14481 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 14482 final boolean allow; 14483 if (checkComponentPermission(INTERACT_ACROSS_USERS_FULL, callingPid, 14484 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED) { 14485 // If the caller has this permission, they always pass go. And collect $200. 14486 allow = true; 14487 } else if (allowMode == ALLOW_FULL_ONLY) { 14488 // We require full access, sucks to be you. 14489 allow = false; 14490 } else if (checkComponentPermission(INTERACT_ACROSS_USERS, callingPid, 14491 callingUid, -1, true) != PackageManager.PERMISSION_GRANTED) { 14492 // If the caller does not have either permission, they are always doomed. 14493 allow = false; 14494 } else if (allowMode == ALLOW_NON_FULL) { 14495 // We are blanket allowing non-full access, you lucky caller! 14496 allow = true; 14497 } else if (allowMode == ALLOW_NON_FULL_IN_PROFILE) { 14498 // We may or may not allow this depending on whether the two users are 14499 // in the same profile. 14500 synchronized (mUserProfileGroupIdsSelfLocked) { 14501 int callingProfile = mUserProfileGroupIdsSelfLocked.get(callingUserId, 14502 UserInfo.NO_PROFILE_GROUP_ID); 14503 int targetProfile = mUserProfileGroupIdsSelfLocked.get(targetUserId, 14504 UserInfo.NO_PROFILE_GROUP_ID); 14505 allow = callingProfile != UserInfo.NO_PROFILE_GROUP_ID 14506 && callingProfile == targetProfile; 14507 } 14508 } else { 14509 throw new IllegalArgumentException("Unknown mode: " + allowMode); 14510 } 14511 if (!allow) { 14512 if (userId == UserHandle.USER_CURRENT_OR_SELF) { 14513 // In this case, they would like to just execute as their 14514 // owner user instead of failing. 14515 targetUserId = callingUserId; 14516 } else { 14517 StringBuilder builder = new StringBuilder(128); 14518 builder.append("Permission Denial: "); 14519 builder.append(name); 14520 if (callerPackage != null) { 14521 builder.append(" from "); 14522 builder.append(callerPackage); 14523 } 14524 builder.append(" asks to run as user "); 14525 builder.append(userId); 14526 builder.append(" but is calling from user "); 14527 builder.append(UserHandle.getUserId(callingUid)); 14528 builder.append("; this requires "); 14529 builder.append(INTERACT_ACROSS_USERS_FULL); 14530 if (allowMode != ALLOW_FULL_ONLY) { 14531 builder.append(" or "); 14532 builder.append(INTERACT_ACROSS_USERS); 14533 } 14534 String msg = builder.toString(); 14535 Slog.w(TAG, msg); 14536 throw new SecurityException(msg); 14537 } 14538 } 14539 } 14540 if (!allowAll && targetUserId < 0) { 14541 throw new IllegalArgumentException( 14542 "Call does not support special user #" + targetUserId); 14543 } 14544 return targetUserId; 14545 } 14546 14547 boolean isSingleton(String componentProcessName, ApplicationInfo aInfo, 14548 String className, int flags) { 14549 boolean result = false; 14550 // For apps that don't have pre-defined UIDs, check for permission 14551 if (UserHandle.getAppId(aInfo.uid) >= Process.FIRST_APPLICATION_UID) { 14552 if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 14553 if (ActivityManager.checkUidPermission( 14554 INTERACT_ACROSS_USERS, 14555 aInfo.uid) != PackageManager.PERMISSION_GRANTED) { 14556 ComponentName comp = new ComponentName(aInfo.packageName, className); 14557 String msg = "Permission Denial: Component " + comp.flattenToShortString() 14558 + " requests FLAG_SINGLE_USER, but app does not hold " 14559 + INTERACT_ACROSS_USERS; 14560 Slog.w(TAG, msg); 14561 throw new SecurityException(msg); 14562 } 14563 // Permission passed 14564 result = true; 14565 } 14566 } else if ("system".equals(componentProcessName)) { 14567 result = true; 14568 } else if (UserHandle.isSameApp(aInfo.uid, Process.PHONE_UID) 14569 && (flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 14570 // Phone app is allowed to export singleuser providers. 14571 result = true; 14572 } else { 14573 // App with pre-defined UID, check if it's a persistent app 14574 result = (aInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0; 14575 } 14576 if (DEBUG_MU) { 14577 Slog.v(TAG, "isSingleton(" + componentProcessName + ", " + aInfo 14578 + ", " + className + ", 0x" + Integer.toHexString(flags) + ") = " + result); 14579 } 14580 return result; 14581 } 14582 14583 /** 14584 * Checks to see if the caller is in the same app as the singleton 14585 * component, or the component is in a special app. It allows special apps 14586 * to export singleton components but prevents exporting singleton 14587 * components for regular apps. 14588 */ 14589 boolean isValidSingletonCall(int callingUid, int componentUid) { 14590 int componentAppId = UserHandle.getAppId(componentUid); 14591 return UserHandle.isSameApp(callingUid, componentUid) 14592 || componentAppId == Process.SYSTEM_UID 14593 || componentAppId == Process.PHONE_UID 14594 || ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, componentUid) 14595 == PackageManager.PERMISSION_GRANTED; 14596 } 14597 14598 public int bindService(IApplicationThread caller, IBinder token, 14599 Intent service, String resolvedType, 14600 IServiceConnection connection, int flags, int userId) { 14601 enforceNotIsolatedCaller("bindService"); 14602 // Refuse possible leaked file descriptors 14603 if (service != null && service.hasFileDescriptors() == true) { 14604 throw new IllegalArgumentException("File descriptors passed in Intent"); 14605 } 14606 14607 synchronized(this) { 14608 return mServices.bindServiceLocked(caller, token, service, resolvedType, 14609 connection, flags, userId); 14610 } 14611 } 14612 14613 public boolean unbindService(IServiceConnection connection) { 14614 synchronized (this) { 14615 return mServices.unbindServiceLocked(connection); 14616 } 14617 } 14618 14619 public void publishService(IBinder token, Intent intent, IBinder service) { 14620 // Refuse possible leaked file descriptors 14621 if (intent != null && intent.hasFileDescriptors() == true) { 14622 throw new IllegalArgumentException("File descriptors passed in Intent"); 14623 } 14624 14625 synchronized(this) { 14626 if (!(token instanceof ServiceRecord)) { 14627 throw new IllegalArgumentException("Invalid service token"); 14628 } 14629 mServices.publishServiceLocked((ServiceRecord)token, intent, service); 14630 } 14631 } 14632 14633 public void unbindFinished(IBinder token, Intent intent, boolean doRebind) { 14634 // Refuse possible leaked file descriptors 14635 if (intent != null && intent.hasFileDescriptors() == true) { 14636 throw new IllegalArgumentException("File descriptors passed in Intent"); 14637 } 14638 14639 synchronized(this) { 14640 mServices.unbindFinishedLocked((ServiceRecord)token, intent, doRebind); 14641 } 14642 } 14643 14644 public void serviceDoneExecuting(IBinder token, int type, int startId, int res) { 14645 synchronized(this) { 14646 if (!(token instanceof ServiceRecord)) { 14647 throw new IllegalArgumentException("Invalid service token"); 14648 } 14649 mServices.serviceDoneExecutingLocked((ServiceRecord)token, type, startId, res); 14650 } 14651 } 14652 14653 // ========================================================= 14654 // BACKUP AND RESTORE 14655 // ========================================================= 14656 14657 // Cause the target app to be launched if necessary and its backup agent 14658 // instantiated. The backup agent will invoke backupAgentCreated() on the 14659 // activity manager to announce its creation. 14660 public boolean bindBackupAgent(ApplicationInfo app, int backupMode) { 14661 if (DEBUG_BACKUP) Slog.v(TAG, "bindBackupAgent: app=" + app + " mode=" + backupMode); 14662 enforceCallingPermission("android.permission.CONFIRM_FULL_BACKUP", "bindBackupAgent"); 14663 14664 synchronized(this) { 14665 // !!! TODO: currently no check here that we're already bound 14666 BatteryStatsImpl.Uid.Pkg.Serv ss = null; 14667 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 14668 synchronized (stats) { 14669 ss = stats.getServiceStatsLocked(app.uid, app.packageName, app.name); 14670 } 14671 14672 // Backup agent is now in use, its package can't be stopped. 14673 try { 14674 AppGlobals.getPackageManager().setPackageStoppedState( 14675 app.packageName, false, UserHandle.getUserId(app.uid)); 14676 } catch (RemoteException e) { 14677 } catch (IllegalArgumentException e) { 14678 Slog.w(TAG, "Failed trying to unstop package " 14679 + app.packageName + ": " + e); 14680 } 14681 14682 BackupRecord r = new BackupRecord(ss, app, backupMode); 14683 ComponentName hostingName = (backupMode == IApplicationThread.BACKUP_MODE_INCREMENTAL) 14684 ? new ComponentName(app.packageName, app.backupAgentName) 14685 : new ComponentName("android", "FullBackupAgent"); 14686 // startProcessLocked() returns existing proc's record if it's already running 14687 ProcessRecord proc = startProcessLocked(app.processName, app, 14688 false, 0, "backup", hostingName, false, false, false); 14689 if (proc == null) { 14690 Slog.e(TAG, "Unable to start backup agent process " + r); 14691 return false; 14692 } 14693 14694 r.app = proc; 14695 mBackupTarget = r; 14696 mBackupAppName = app.packageName; 14697 14698 // Try not to kill the process during backup 14699 updateOomAdjLocked(proc); 14700 14701 // If the process is already attached, schedule the creation of the backup agent now. 14702 // If it is not yet live, this will be done when it attaches to the framework. 14703 if (proc.thread != null) { 14704 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc already running: " + proc); 14705 try { 14706 proc.thread.scheduleCreateBackupAgent(app, 14707 compatibilityInfoForPackageLocked(app), backupMode); 14708 } catch (RemoteException e) { 14709 // Will time out on the backup manager side 14710 } 14711 } else { 14712 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc not running, waiting for attach"); 14713 } 14714 // Invariants: at this point, the target app process exists and the application 14715 // is either already running or in the process of coming up. mBackupTarget and 14716 // mBackupAppName describe the app, so that when it binds back to the AM we 14717 // know that it's scheduled for a backup-agent operation. 14718 } 14719 14720 return true; 14721 } 14722 14723 @Override 14724 public void clearPendingBackup() { 14725 if (DEBUG_BACKUP) Slog.v(TAG, "clearPendingBackup"); 14726 enforceCallingPermission("android.permission.BACKUP", "clearPendingBackup"); 14727 14728 synchronized (this) { 14729 mBackupTarget = null; 14730 mBackupAppName = null; 14731 } 14732 } 14733 14734 // A backup agent has just come up 14735 public void backupAgentCreated(String agentPackageName, IBinder agent) { 14736 if (DEBUG_BACKUP) Slog.v(TAG, "backupAgentCreated: " + agentPackageName 14737 + " = " + agent); 14738 14739 synchronized(this) { 14740 if (!agentPackageName.equals(mBackupAppName)) { 14741 Slog.e(TAG, "Backup agent created for " + agentPackageName + " but not requested!"); 14742 return; 14743 } 14744 } 14745 14746 long oldIdent = Binder.clearCallingIdentity(); 14747 try { 14748 IBackupManager bm = IBackupManager.Stub.asInterface( 14749 ServiceManager.getService(Context.BACKUP_SERVICE)); 14750 bm.agentConnected(agentPackageName, agent); 14751 } catch (RemoteException e) { 14752 // can't happen; the backup manager service is local 14753 } catch (Exception e) { 14754 Slog.w(TAG, "Exception trying to deliver BackupAgent binding: "); 14755 e.printStackTrace(); 14756 } finally { 14757 Binder.restoreCallingIdentity(oldIdent); 14758 } 14759 } 14760 14761 // done with this agent 14762 public void unbindBackupAgent(ApplicationInfo appInfo) { 14763 if (DEBUG_BACKUP) Slog.v(TAG, "unbindBackupAgent: " + appInfo); 14764 if (appInfo == null) { 14765 Slog.w(TAG, "unbind backup agent for null app"); 14766 return; 14767 } 14768 14769 synchronized(this) { 14770 try { 14771 if (mBackupAppName == null) { 14772 Slog.w(TAG, "Unbinding backup agent with no active backup"); 14773 return; 14774 } 14775 14776 if (!mBackupAppName.equals(appInfo.packageName)) { 14777 Slog.e(TAG, "Unbind of " + appInfo + " but is not the current backup target"); 14778 return; 14779 } 14780 14781 // Not backing this app up any more; reset its OOM adjustment 14782 final ProcessRecord proc = mBackupTarget.app; 14783 updateOomAdjLocked(proc); 14784 14785 // If the app crashed during backup, 'thread' will be null here 14786 if (proc.thread != null) { 14787 try { 14788 proc.thread.scheduleDestroyBackupAgent(appInfo, 14789 compatibilityInfoForPackageLocked(appInfo)); 14790 } catch (Exception e) { 14791 Slog.e(TAG, "Exception when unbinding backup agent:"); 14792 e.printStackTrace(); 14793 } 14794 } 14795 } finally { 14796 mBackupTarget = null; 14797 mBackupAppName = null; 14798 } 14799 } 14800 } 14801 // ========================================================= 14802 // BROADCASTS 14803 // ========================================================= 14804 14805 private final List getStickiesLocked(String action, IntentFilter filter, 14806 List cur, int userId) { 14807 final ContentResolver resolver = mContext.getContentResolver(); 14808 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 14809 if (stickies == null) { 14810 return cur; 14811 } 14812 final ArrayList<Intent> list = stickies.get(action); 14813 if (list == null) { 14814 return cur; 14815 } 14816 int N = list.size(); 14817 for (int i=0; i<N; i++) { 14818 Intent intent = list.get(i); 14819 if (filter.match(resolver, intent, true, TAG) >= 0) { 14820 if (cur == null) { 14821 cur = new ArrayList<Intent>(); 14822 } 14823 cur.add(intent); 14824 } 14825 } 14826 return cur; 14827 } 14828 14829 boolean isPendingBroadcastProcessLocked(int pid) { 14830 return mFgBroadcastQueue.isPendingBroadcastProcessLocked(pid) 14831 || mBgBroadcastQueue.isPendingBroadcastProcessLocked(pid); 14832 } 14833 14834 void skipPendingBroadcastLocked(int pid) { 14835 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 14836 for (BroadcastQueue queue : mBroadcastQueues) { 14837 queue.skipPendingBroadcastLocked(pid); 14838 } 14839 } 14840 14841 // The app just attached; send any pending broadcasts that it should receive 14842 boolean sendPendingBroadcastsLocked(ProcessRecord app) { 14843 boolean didSomething = false; 14844 for (BroadcastQueue queue : mBroadcastQueues) { 14845 didSomething |= queue.sendPendingBroadcastsLocked(app); 14846 } 14847 return didSomething; 14848 } 14849 14850 public Intent registerReceiver(IApplicationThread caller, String callerPackage, 14851 IIntentReceiver receiver, IntentFilter filter, String permission, int userId) { 14852 enforceNotIsolatedCaller("registerReceiver"); 14853 int callingUid; 14854 int callingPid; 14855 synchronized(this) { 14856 ProcessRecord callerApp = null; 14857 if (caller != null) { 14858 callerApp = getRecordForAppLocked(caller); 14859 if (callerApp == null) { 14860 throw new SecurityException( 14861 "Unable to find app for caller " + caller 14862 + " (pid=" + Binder.getCallingPid() 14863 + ") when registering receiver " + receiver); 14864 } 14865 if (callerApp.info.uid != Process.SYSTEM_UID && 14866 !callerApp.pkgList.containsKey(callerPackage) && 14867 !"android".equals(callerPackage)) { 14868 throw new SecurityException("Given caller package " + callerPackage 14869 + " is not running in process " + callerApp); 14870 } 14871 callingUid = callerApp.info.uid; 14872 callingPid = callerApp.pid; 14873 } else { 14874 callerPackage = null; 14875 callingUid = Binder.getCallingUid(); 14876 callingPid = Binder.getCallingPid(); 14877 } 14878 14879 userId = this.handleIncomingUser(callingPid, callingUid, userId, 14880 true, ALLOW_FULL_ONLY, "registerReceiver", callerPackage); 14881 14882 List allSticky = null; 14883 14884 // Look for any matching sticky broadcasts... 14885 Iterator actions = filter.actionsIterator(); 14886 if (actions != null) { 14887 while (actions.hasNext()) { 14888 String action = (String)actions.next(); 14889 allSticky = getStickiesLocked(action, filter, allSticky, 14890 UserHandle.USER_ALL); 14891 allSticky = getStickiesLocked(action, filter, allSticky, 14892 UserHandle.getUserId(callingUid)); 14893 } 14894 } else { 14895 allSticky = getStickiesLocked(null, filter, allSticky, 14896 UserHandle.USER_ALL); 14897 allSticky = getStickiesLocked(null, filter, allSticky, 14898 UserHandle.getUserId(callingUid)); 14899 } 14900 14901 // The first sticky in the list is returned directly back to 14902 // the client. 14903 Intent sticky = allSticky != null ? (Intent)allSticky.get(0) : null; 14904 14905 if (DEBUG_BROADCAST) Slog.v(TAG, "Register receiver " + filter 14906 + ": " + sticky); 14907 14908 if (receiver == null) { 14909 return sticky; 14910 } 14911 14912 ReceiverList rl 14913 = (ReceiverList)mRegisteredReceivers.get(receiver.asBinder()); 14914 if (rl == null) { 14915 rl = new ReceiverList(this, callerApp, callingPid, callingUid, 14916 userId, receiver); 14917 if (rl.app != null) { 14918 rl.app.receivers.add(rl); 14919 } else { 14920 try { 14921 receiver.asBinder().linkToDeath(rl, 0); 14922 } catch (RemoteException e) { 14923 return sticky; 14924 } 14925 rl.linkedToDeath = true; 14926 } 14927 mRegisteredReceivers.put(receiver.asBinder(), rl); 14928 } else if (rl.uid != callingUid) { 14929 throw new IllegalArgumentException( 14930 "Receiver requested to register for uid " + callingUid 14931 + " was previously registered for uid " + rl.uid); 14932 } else if (rl.pid != callingPid) { 14933 throw new IllegalArgumentException( 14934 "Receiver requested to register for pid " + callingPid 14935 + " was previously registered for pid " + rl.pid); 14936 } else if (rl.userId != userId) { 14937 throw new IllegalArgumentException( 14938 "Receiver requested to register for user " + userId 14939 + " was previously registered for user " + rl.userId); 14940 } 14941 BroadcastFilter bf = new BroadcastFilter(filter, rl, callerPackage, 14942 permission, callingUid, userId); 14943 rl.add(bf); 14944 if (!bf.debugCheck()) { 14945 Slog.w(TAG, "==> For Dynamic broadast"); 14946 } 14947 mReceiverResolver.addFilter(bf); 14948 14949 // Enqueue broadcasts for all existing stickies that match 14950 // this filter. 14951 if (allSticky != null) { 14952 ArrayList receivers = new ArrayList(); 14953 receivers.add(bf); 14954 14955 int N = allSticky.size(); 14956 for (int i=0; i<N; i++) { 14957 Intent intent = (Intent)allSticky.get(i); 14958 BroadcastQueue queue = broadcastQueueForIntent(intent); 14959 BroadcastRecord r = new BroadcastRecord(queue, intent, null, 14960 null, -1, -1, null, null, AppOpsManager.OP_NONE, receivers, null, 0, 14961 null, null, false, true, true, -1); 14962 queue.enqueueParallelBroadcastLocked(r); 14963 queue.scheduleBroadcastsLocked(); 14964 } 14965 } 14966 14967 return sticky; 14968 } 14969 } 14970 14971 public void unregisterReceiver(IIntentReceiver receiver) { 14972 if (DEBUG_BROADCAST) Slog.v(TAG, "Unregister receiver: " + receiver); 14973 14974 final long origId = Binder.clearCallingIdentity(); 14975 try { 14976 boolean doTrim = false; 14977 14978 synchronized(this) { 14979 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder()); 14980 if (rl != null) { 14981 if (rl.curBroadcast != null) { 14982 BroadcastRecord r = rl.curBroadcast; 14983 final boolean doNext = finishReceiverLocked( 14984 receiver.asBinder(), r.resultCode, r.resultData, 14985 r.resultExtras, r.resultAbort); 14986 if (doNext) { 14987 doTrim = true; 14988 r.queue.processNextBroadcast(false); 14989 } 14990 } 14991 14992 if (rl.app != null) { 14993 rl.app.receivers.remove(rl); 14994 } 14995 removeReceiverLocked(rl); 14996 if (rl.linkedToDeath) { 14997 rl.linkedToDeath = false; 14998 rl.receiver.asBinder().unlinkToDeath(rl, 0); 14999 } 15000 } 15001 } 15002 15003 // If we actually concluded any broadcasts, we might now be able 15004 // to trim the recipients' apps from our working set 15005 if (doTrim) { 15006 trimApplications(); 15007 return; 15008 } 15009 15010 } finally { 15011 Binder.restoreCallingIdentity(origId); 15012 } 15013 } 15014 15015 void removeReceiverLocked(ReceiverList rl) { 15016 mRegisteredReceivers.remove(rl.receiver.asBinder()); 15017 int N = rl.size(); 15018 for (int i=0; i<N; i++) { 15019 mReceiverResolver.removeFilter(rl.get(i)); 15020 } 15021 } 15022 15023 private final void sendPackageBroadcastLocked(int cmd, String[] packages, int userId) { 15024 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 15025 ProcessRecord r = mLruProcesses.get(i); 15026 if (r.thread != null && (userId == UserHandle.USER_ALL || r.userId == userId)) { 15027 try { 15028 r.thread.dispatchPackageBroadcast(cmd, packages); 15029 } catch (RemoteException ex) { 15030 } 15031 } 15032 } 15033 } 15034 15035 private List<ResolveInfo> collectReceiverComponents(Intent intent, String resolvedType, 15036 int[] users) { 15037 List<ResolveInfo> receivers = null; 15038 try { 15039 HashSet<ComponentName> singleUserReceivers = null; 15040 boolean scannedFirstReceivers = false; 15041 for (int user : users) { 15042 List<ResolveInfo> newReceivers = AppGlobals.getPackageManager() 15043 .queryIntentReceivers(intent, resolvedType, STOCK_PM_FLAGS, user); 15044 if (user != 0 && newReceivers != null) { 15045 // If this is not the primary user, we need to check for 15046 // any receivers that should be filtered out. 15047 for (int i=0; i<newReceivers.size(); i++) { 15048 ResolveInfo ri = newReceivers.get(i); 15049 if ((ri.activityInfo.flags&ActivityInfo.FLAG_PRIMARY_USER_ONLY) != 0) { 15050 newReceivers.remove(i); 15051 i--; 15052 } 15053 } 15054 } 15055 if (newReceivers != null && newReceivers.size() == 0) { 15056 newReceivers = null; 15057 } 15058 if (receivers == null) { 15059 receivers = newReceivers; 15060 } else if (newReceivers != null) { 15061 // We need to concatenate the additional receivers 15062 // found with what we have do far. This would be easy, 15063 // but we also need to de-dup any receivers that are 15064 // singleUser. 15065 if (!scannedFirstReceivers) { 15066 // Collect any single user receivers we had already retrieved. 15067 scannedFirstReceivers = true; 15068 for (int i=0; i<receivers.size(); i++) { 15069 ResolveInfo ri = receivers.get(i); 15070 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 15071 ComponentName cn = new ComponentName( 15072 ri.activityInfo.packageName, ri.activityInfo.name); 15073 if (singleUserReceivers == null) { 15074 singleUserReceivers = new HashSet<ComponentName>(); 15075 } 15076 singleUserReceivers.add(cn); 15077 } 15078 } 15079 } 15080 // Add the new results to the existing results, tracking 15081 // and de-dupping single user receivers. 15082 for (int i=0; i<newReceivers.size(); i++) { 15083 ResolveInfo ri = newReceivers.get(i); 15084 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 15085 ComponentName cn = new ComponentName( 15086 ri.activityInfo.packageName, ri.activityInfo.name); 15087 if (singleUserReceivers == null) { 15088 singleUserReceivers = new HashSet<ComponentName>(); 15089 } 15090 if (!singleUserReceivers.contains(cn)) { 15091 singleUserReceivers.add(cn); 15092 receivers.add(ri); 15093 } 15094 } else { 15095 receivers.add(ri); 15096 } 15097 } 15098 } 15099 } 15100 } catch (RemoteException ex) { 15101 // pm is in same process, this will never happen. 15102 } 15103 return receivers; 15104 } 15105 15106 private final int broadcastIntentLocked(ProcessRecord callerApp, 15107 String callerPackage, Intent intent, String resolvedType, 15108 IIntentReceiver resultTo, int resultCode, String resultData, 15109 Bundle map, String requiredPermission, int appOp, 15110 boolean ordered, boolean sticky, int callingPid, int callingUid, 15111 int userId) { 15112 intent = new Intent(intent); 15113 15114 // By default broadcasts do not go to stopped apps. 15115 intent.addFlags(Intent.FLAG_EXCLUDE_STOPPED_PACKAGES); 15116 15117 if (DEBUG_BROADCAST_LIGHT) Slog.v( 15118 TAG, (sticky ? "Broadcast sticky: ": "Broadcast: ") + intent 15119 + " ordered=" + ordered + " userid=" + userId); 15120 if ((resultTo != null) && !ordered) { 15121 Slog.w(TAG, "Broadcast " + intent + " not ordered but result callback requested!"); 15122 } 15123 15124 userId = handleIncomingUser(callingPid, callingUid, userId, 15125 true, ALLOW_NON_FULL, "broadcast", callerPackage); 15126 15127 // Make sure that the user who is receiving this broadcast is started. 15128 // If not, we will just skip it. 15129 15130 15131 if (userId != UserHandle.USER_ALL && mStartedUsers.get(userId) == null) { 15132 if (callingUid != Process.SYSTEM_UID || (intent.getFlags() 15133 & Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) { 15134 Slog.w(TAG, "Skipping broadcast of " + intent 15135 + ": user " + userId + " is stopped"); 15136 return ActivityManager.BROADCAST_SUCCESS; 15137 } 15138 } 15139 15140 /* 15141 * Prevent non-system code (defined here to be non-persistent 15142 * processes) from sending protected broadcasts. 15143 */ 15144 int callingAppId = UserHandle.getAppId(callingUid); 15145 if (callingAppId == Process.SYSTEM_UID || callingAppId == Process.PHONE_UID 15146 || callingAppId == Process.SHELL_UID || callingAppId == Process.BLUETOOTH_UID 15147 || callingAppId == Process.NFC_UID || callingUid == 0) { 15148 // Always okay. 15149 } else if (callerApp == null || !callerApp.persistent) { 15150 try { 15151 if (AppGlobals.getPackageManager().isProtectedBroadcast( 15152 intent.getAction())) { 15153 String msg = "Permission Denial: not allowed to send broadcast " 15154 + intent.getAction() + " from pid=" 15155 + callingPid + ", uid=" + callingUid; 15156 Slog.w(TAG, msg); 15157 throw new SecurityException(msg); 15158 } else if (AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(intent.getAction())) { 15159 // Special case for compatibility: we don't want apps to send this, 15160 // but historically it has not been protected and apps may be using it 15161 // to poke their own app widget. So, instead of making it protected, 15162 // just limit it to the caller. 15163 if (callerApp == null) { 15164 String msg = "Permission Denial: not allowed to send broadcast " 15165 + intent.getAction() + " from unknown caller."; 15166 Slog.w(TAG, msg); 15167 throw new SecurityException(msg); 15168 } else if (intent.getComponent() != null) { 15169 // They are good enough to send to an explicit component... verify 15170 // it is being sent to the calling app. 15171 if (!intent.getComponent().getPackageName().equals( 15172 callerApp.info.packageName)) { 15173 String msg = "Permission Denial: not allowed to send broadcast " 15174 + intent.getAction() + " to " 15175 + intent.getComponent().getPackageName() + " from " 15176 + callerApp.info.packageName; 15177 Slog.w(TAG, msg); 15178 throw new SecurityException(msg); 15179 } 15180 } else { 15181 // Limit broadcast to their own package. 15182 intent.setPackage(callerApp.info.packageName); 15183 } 15184 } 15185 } catch (RemoteException e) { 15186 Slog.w(TAG, "Remote exception", e); 15187 return ActivityManager.BROADCAST_SUCCESS; 15188 } 15189 } 15190 15191 // Handle special intents: if this broadcast is from the package 15192 // manager about a package being removed, we need to remove all of 15193 // its activities from the history stack. 15194 final boolean uidRemoved = Intent.ACTION_UID_REMOVED.equals( 15195 intent.getAction()); 15196 if (Intent.ACTION_PACKAGE_REMOVED.equals(intent.getAction()) 15197 || Intent.ACTION_PACKAGE_CHANGED.equals(intent.getAction()) 15198 || Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction()) 15199 || Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction()) 15200 || uidRemoved) { 15201 if (checkComponentPermission( 15202 android.Manifest.permission.BROADCAST_PACKAGE_REMOVED, 15203 callingPid, callingUid, -1, true) 15204 == PackageManager.PERMISSION_GRANTED) { 15205 if (uidRemoved) { 15206 final Bundle intentExtras = intent.getExtras(); 15207 final int uid = intentExtras != null 15208 ? intentExtras.getInt(Intent.EXTRA_UID) : -1; 15209 if (uid >= 0) { 15210 BatteryStatsImpl bs = mBatteryStatsService.getActiveStatistics(); 15211 synchronized (bs) { 15212 bs.removeUidStatsLocked(uid); 15213 } 15214 mAppOpsService.uidRemoved(uid); 15215 } 15216 } else { 15217 // If resources are unavailable just force stop all 15218 // those packages and flush the attribute cache as well. 15219 if (Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction())) { 15220 String list[] = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 15221 if (list != null && (list.length > 0)) { 15222 for (String pkg : list) { 15223 forceStopPackageLocked(pkg, -1, false, true, true, false, false, userId, 15224 "storage unmount"); 15225 } 15226 cleanupRecentTasksLocked(UserHandle.USER_ALL); 15227 sendPackageBroadcastLocked( 15228 IApplicationThread.EXTERNAL_STORAGE_UNAVAILABLE, list, userId); 15229 } 15230 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals( 15231 intent.getAction())) { 15232 cleanupRecentTasksLocked(UserHandle.USER_ALL); 15233 } else { 15234 Uri data = intent.getData(); 15235 String ssp; 15236 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 15237 boolean removed = Intent.ACTION_PACKAGE_REMOVED.equals( 15238 intent.getAction()); 15239 boolean fullUninstall = removed && 15240 !intent.getBooleanExtra(Intent.EXTRA_REPLACING, false); 15241 if (!intent.getBooleanExtra(Intent.EXTRA_DONT_KILL_APP, false)) { 15242 forceStopPackageLocked(ssp, UserHandle.getAppId( 15243 intent.getIntExtra(Intent.EXTRA_UID, -1)), false, true, true, 15244 false, fullUninstall, userId, 15245 removed ? "pkg removed" : "pkg changed"); 15246 } 15247 if (removed) { 15248 sendPackageBroadcastLocked(IApplicationThread.PACKAGE_REMOVED, 15249 new String[] {ssp}, userId); 15250 if (!intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)) { 15251 mAppOpsService.packageRemoved( 15252 intent.getIntExtra(Intent.EXTRA_UID, -1), ssp); 15253 15254 // Remove all permissions granted from/to this package 15255 removeUriPermissionsForPackageLocked(ssp, userId, true); 15256 } 15257 } 15258 } 15259 } 15260 } 15261 } else { 15262 String msg = "Permission Denial: " + intent.getAction() 15263 + " broadcast from " + callerPackage + " (pid=" + callingPid 15264 + ", uid=" + callingUid + ")" 15265 + " requires " 15266 + android.Manifest.permission.BROADCAST_PACKAGE_REMOVED; 15267 Slog.w(TAG, msg); 15268 throw new SecurityException(msg); 15269 } 15270 15271 // Special case for adding a package: by default turn on compatibility 15272 // mode. 15273 } else if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction())) { 15274 Uri data = intent.getData(); 15275 String ssp; 15276 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 15277 mCompatModePackages.handlePackageAddedLocked(ssp, 15278 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)); 15279 } 15280 } 15281 15282 /* 15283 * If this is the time zone changed action, queue up a message that will reset the timezone 15284 * of all currently running processes. This message will get queued up before the broadcast 15285 * happens. 15286 */ 15287 if (Intent.ACTION_TIMEZONE_CHANGED.equals(intent.getAction())) { 15288 mHandler.sendEmptyMessage(UPDATE_TIME_ZONE); 15289 } 15290 15291 /* 15292 * If the user set the time, let all running processes know. 15293 */ 15294 if (Intent.ACTION_TIME_CHANGED.equals(intent.getAction())) { 15295 final int is24Hour = intent.getBooleanExtra( 15296 Intent.EXTRA_TIME_PREF_24_HOUR_FORMAT, false) ? 1 : 0; 15297 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_TIME, is24Hour, 0)); 15298 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 15299 synchronized (stats) { 15300 stats.noteCurrentTimeChangedLocked(); 15301 } 15302 } 15303 15304 if (Intent.ACTION_CLEAR_DNS_CACHE.equals(intent.getAction())) { 15305 mHandler.sendEmptyMessage(CLEAR_DNS_CACHE_MSG); 15306 } 15307 15308 if (Proxy.PROXY_CHANGE_ACTION.equals(intent.getAction())) { 15309 ProxyInfo proxy = intent.getParcelableExtra(Proxy.EXTRA_PROXY_INFO); 15310 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_HTTP_PROXY_MSG, proxy)); 15311 } 15312 15313 // Add to the sticky list if requested. 15314 if (sticky) { 15315 if (checkPermission(android.Manifest.permission.BROADCAST_STICKY, 15316 callingPid, callingUid) 15317 != PackageManager.PERMISSION_GRANTED) { 15318 String msg = "Permission Denial: broadcastIntent() requesting a sticky broadcast from pid=" 15319 + callingPid + ", uid=" + callingUid 15320 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 15321 Slog.w(TAG, msg); 15322 throw new SecurityException(msg); 15323 } 15324 if (requiredPermission != null) { 15325 Slog.w(TAG, "Can't broadcast sticky intent " + intent 15326 + " and enforce permission " + requiredPermission); 15327 return ActivityManager.BROADCAST_STICKY_CANT_HAVE_PERMISSION; 15328 } 15329 if (intent.getComponent() != null) { 15330 throw new SecurityException( 15331 "Sticky broadcasts can't target a specific component"); 15332 } 15333 // We use userId directly here, since the "all" target is maintained 15334 // as a separate set of sticky broadcasts. 15335 if (userId != UserHandle.USER_ALL) { 15336 // But first, if this is not a broadcast to all users, then 15337 // make sure it doesn't conflict with an existing broadcast to 15338 // all users. 15339 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get( 15340 UserHandle.USER_ALL); 15341 if (stickies != null) { 15342 ArrayList<Intent> list = stickies.get(intent.getAction()); 15343 if (list != null) { 15344 int N = list.size(); 15345 int i; 15346 for (i=0; i<N; i++) { 15347 if (intent.filterEquals(list.get(i))) { 15348 throw new IllegalArgumentException( 15349 "Sticky broadcast " + intent + " for user " 15350 + userId + " conflicts with existing global broadcast"); 15351 } 15352 } 15353 } 15354 } 15355 } 15356 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 15357 if (stickies == null) { 15358 stickies = new ArrayMap<String, ArrayList<Intent>>(); 15359 mStickyBroadcasts.put(userId, stickies); 15360 } 15361 ArrayList<Intent> list = stickies.get(intent.getAction()); 15362 if (list == null) { 15363 list = new ArrayList<Intent>(); 15364 stickies.put(intent.getAction(), list); 15365 } 15366 int N = list.size(); 15367 int i; 15368 for (i=0; i<N; i++) { 15369 if (intent.filterEquals(list.get(i))) { 15370 // This sticky already exists, replace it. 15371 list.set(i, new Intent(intent)); 15372 break; 15373 } 15374 } 15375 if (i >= N) { 15376 list.add(new Intent(intent)); 15377 } 15378 } 15379 15380 int[] users; 15381 if (userId == UserHandle.USER_ALL) { 15382 // Caller wants broadcast to go to all started users. 15383 users = mStartedUserArray; 15384 } else { 15385 // Caller wants broadcast to go to one specific user. 15386 users = new int[] {userId}; 15387 } 15388 15389 // Figure out who all will receive this broadcast. 15390 List receivers = null; 15391 List<BroadcastFilter> registeredReceivers = null; 15392 // Need to resolve the intent to interested receivers... 15393 if ((intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) 15394 == 0) { 15395 receivers = collectReceiverComponents(intent, resolvedType, users); 15396 } 15397 if (intent.getComponent() == null) { 15398 registeredReceivers = mReceiverResolver.queryIntent(intent, 15399 resolvedType, false, userId); 15400 } 15401 15402 final boolean replacePending = 15403 (intent.getFlags()&Intent.FLAG_RECEIVER_REPLACE_PENDING) != 0; 15404 15405 if (DEBUG_BROADCAST) Slog.v(TAG, "Enqueing broadcast: " + intent.getAction() 15406 + " replacePending=" + replacePending); 15407 15408 int NR = registeredReceivers != null ? registeredReceivers.size() : 0; 15409 if (!ordered && NR > 0) { 15410 // If we are not serializing this broadcast, then send the 15411 // registered receivers separately so they don't wait for the 15412 // components to be launched. 15413 final BroadcastQueue queue = broadcastQueueForIntent(intent); 15414 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 15415 callerPackage, callingPid, callingUid, resolvedType, requiredPermission, 15416 appOp, registeredReceivers, resultTo, resultCode, resultData, map, 15417 ordered, sticky, false, userId); 15418 if (DEBUG_BROADCAST) Slog.v( 15419 TAG, "Enqueueing parallel broadcast " + r); 15420 final boolean replaced = replacePending && queue.replaceParallelBroadcastLocked(r); 15421 if (!replaced) { 15422 queue.enqueueParallelBroadcastLocked(r); 15423 queue.scheduleBroadcastsLocked(); 15424 } 15425 registeredReceivers = null; 15426 NR = 0; 15427 } 15428 15429 // Merge into one list. 15430 int ir = 0; 15431 if (receivers != null) { 15432 // A special case for PACKAGE_ADDED: do not allow the package 15433 // being added to see this broadcast. This prevents them from 15434 // using this as a back door to get run as soon as they are 15435 // installed. Maybe in the future we want to have a special install 15436 // broadcast or such for apps, but we'd like to deliberately make 15437 // this decision. 15438 String skipPackages[] = null; 15439 if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction()) 15440 || Intent.ACTION_PACKAGE_RESTARTED.equals(intent.getAction()) 15441 || Intent.ACTION_PACKAGE_DATA_CLEARED.equals(intent.getAction())) { 15442 Uri data = intent.getData(); 15443 if (data != null) { 15444 String pkgName = data.getSchemeSpecificPart(); 15445 if (pkgName != null) { 15446 skipPackages = new String[] { pkgName }; 15447 } 15448 } 15449 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction())) { 15450 skipPackages = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 15451 } 15452 if (skipPackages != null && (skipPackages.length > 0)) { 15453 for (String skipPackage : skipPackages) { 15454 if (skipPackage != null) { 15455 int NT = receivers.size(); 15456 for (int it=0; it<NT; it++) { 15457 ResolveInfo curt = (ResolveInfo)receivers.get(it); 15458 if (curt.activityInfo.packageName.equals(skipPackage)) { 15459 receivers.remove(it); 15460 it--; 15461 NT--; 15462 } 15463 } 15464 } 15465 } 15466 } 15467 15468 int NT = receivers != null ? receivers.size() : 0; 15469 int it = 0; 15470 ResolveInfo curt = null; 15471 BroadcastFilter curr = null; 15472 while (it < NT && ir < NR) { 15473 if (curt == null) { 15474 curt = (ResolveInfo)receivers.get(it); 15475 } 15476 if (curr == null) { 15477 curr = registeredReceivers.get(ir); 15478 } 15479 if (curr.getPriority() >= curt.priority) { 15480 // Insert this broadcast record into the final list. 15481 receivers.add(it, curr); 15482 ir++; 15483 curr = null; 15484 it++; 15485 NT++; 15486 } else { 15487 // Skip to the next ResolveInfo in the final list. 15488 it++; 15489 curt = null; 15490 } 15491 } 15492 } 15493 while (ir < NR) { 15494 if (receivers == null) { 15495 receivers = new ArrayList(); 15496 } 15497 receivers.add(registeredReceivers.get(ir)); 15498 ir++; 15499 } 15500 15501 if ((receivers != null && receivers.size() > 0) 15502 || resultTo != null) { 15503 BroadcastQueue queue = broadcastQueueForIntent(intent); 15504 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 15505 callerPackage, callingPid, callingUid, resolvedType, 15506 requiredPermission, appOp, receivers, resultTo, resultCode, 15507 resultData, map, ordered, sticky, false, userId); 15508 if (DEBUG_BROADCAST) Slog.v( 15509 TAG, "Enqueueing ordered broadcast " + r 15510 + ": prev had " + queue.mOrderedBroadcasts.size()); 15511 if (DEBUG_BROADCAST) { 15512 int seq = r.intent.getIntExtra("seq", -1); 15513 Slog.i(TAG, "Enqueueing broadcast " + r.intent.getAction() + " seq=" + seq); 15514 } 15515 boolean replaced = replacePending && queue.replaceOrderedBroadcastLocked(r); 15516 if (!replaced) { 15517 queue.enqueueOrderedBroadcastLocked(r); 15518 queue.scheduleBroadcastsLocked(); 15519 } 15520 } 15521 15522 return ActivityManager.BROADCAST_SUCCESS; 15523 } 15524 15525 final Intent verifyBroadcastLocked(Intent intent) { 15526 // Refuse possible leaked file descriptors 15527 if (intent != null && intent.hasFileDescriptors() == true) { 15528 throw new IllegalArgumentException("File descriptors passed in Intent"); 15529 } 15530 15531 int flags = intent.getFlags(); 15532 15533 if (!mProcessesReady) { 15534 // if the caller really truly claims to know what they're doing, go 15535 // ahead and allow the broadcast without launching any receivers 15536 if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT) != 0) { 15537 intent = new Intent(intent); 15538 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 15539 } else if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) { 15540 Slog.e(TAG, "Attempt to launch receivers of broadcast intent " + intent 15541 + " before boot completion"); 15542 throw new IllegalStateException("Cannot broadcast before boot completed"); 15543 } 15544 } 15545 15546 if ((flags&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 15547 throw new IllegalArgumentException( 15548 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 15549 } 15550 15551 return intent; 15552 } 15553 15554 public final int broadcastIntent(IApplicationThread caller, 15555 Intent intent, String resolvedType, IIntentReceiver resultTo, 15556 int resultCode, String resultData, Bundle map, 15557 String requiredPermission, int appOp, boolean serialized, boolean sticky, int userId) { 15558 enforceNotIsolatedCaller("broadcastIntent"); 15559 synchronized(this) { 15560 intent = verifyBroadcastLocked(intent); 15561 15562 final ProcessRecord callerApp = getRecordForAppLocked(caller); 15563 final int callingPid = Binder.getCallingPid(); 15564 final int callingUid = Binder.getCallingUid(); 15565 final long origId = Binder.clearCallingIdentity(); 15566 int res = broadcastIntentLocked(callerApp, 15567 callerApp != null ? callerApp.info.packageName : null, 15568 intent, resolvedType, resultTo, 15569 resultCode, resultData, map, requiredPermission, appOp, serialized, sticky, 15570 callingPid, callingUid, userId); 15571 Binder.restoreCallingIdentity(origId); 15572 return res; 15573 } 15574 } 15575 15576 int broadcastIntentInPackage(String packageName, int uid, 15577 Intent intent, String resolvedType, IIntentReceiver resultTo, 15578 int resultCode, String resultData, Bundle map, 15579 String requiredPermission, boolean serialized, boolean sticky, int userId) { 15580 synchronized(this) { 15581 intent = verifyBroadcastLocked(intent); 15582 15583 final long origId = Binder.clearCallingIdentity(); 15584 int res = broadcastIntentLocked(null, packageName, intent, resolvedType, 15585 resultTo, resultCode, resultData, map, requiredPermission, 15586 AppOpsManager.OP_NONE, serialized, sticky, -1, uid, userId); 15587 Binder.restoreCallingIdentity(origId); 15588 return res; 15589 } 15590 } 15591 15592 public final void unbroadcastIntent(IApplicationThread caller, Intent intent, int userId) { 15593 // Refuse possible leaked file descriptors 15594 if (intent != null && intent.hasFileDescriptors() == true) { 15595 throw new IllegalArgumentException("File descriptors passed in Intent"); 15596 } 15597 15598 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 15599 userId, true, ALLOW_NON_FULL, "removeStickyBroadcast", null); 15600 15601 synchronized(this) { 15602 if (checkCallingPermission(android.Manifest.permission.BROADCAST_STICKY) 15603 != PackageManager.PERMISSION_GRANTED) { 15604 String msg = "Permission Denial: unbroadcastIntent() from pid=" 15605 + Binder.getCallingPid() 15606 + ", uid=" + Binder.getCallingUid() 15607 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 15608 Slog.w(TAG, msg); 15609 throw new SecurityException(msg); 15610 } 15611 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 15612 if (stickies != null) { 15613 ArrayList<Intent> list = stickies.get(intent.getAction()); 15614 if (list != null) { 15615 int N = list.size(); 15616 int i; 15617 for (i=0; i<N; i++) { 15618 if (intent.filterEquals(list.get(i))) { 15619 list.remove(i); 15620 break; 15621 } 15622 } 15623 if (list.size() <= 0) { 15624 stickies.remove(intent.getAction()); 15625 } 15626 } 15627 if (stickies.size() <= 0) { 15628 mStickyBroadcasts.remove(userId); 15629 } 15630 } 15631 } 15632 } 15633 15634 private final boolean finishReceiverLocked(IBinder receiver, int resultCode, 15635 String resultData, Bundle resultExtras, boolean resultAbort) { 15636 final BroadcastRecord r = broadcastRecordForReceiverLocked(receiver); 15637 if (r == null) { 15638 Slog.w(TAG, "finishReceiver called but not found on queue"); 15639 return false; 15640 } 15641 15642 return r.queue.finishReceiverLocked(r, resultCode, resultData, resultExtras, resultAbort, false); 15643 } 15644 15645 void backgroundServicesFinishedLocked(int userId) { 15646 for (BroadcastQueue queue : mBroadcastQueues) { 15647 queue.backgroundServicesFinishedLocked(userId); 15648 } 15649 } 15650 15651 public void finishReceiver(IBinder who, int resultCode, String resultData, 15652 Bundle resultExtras, boolean resultAbort) { 15653 if (DEBUG_BROADCAST) Slog.v(TAG, "Finish receiver: " + who); 15654 15655 // Refuse possible leaked file descriptors 15656 if (resultExtras != null && resultExtras.hasFileDescriptors()) { 15657 throw new IllegalArgumentException("File descriptors passed in Bundle"); 15658 } 15659 15660 final long origId = Binder.clearCallingIdentity(); 15661 try { 15662 boolean doNext = false; 15663 BroadcastRecord r; 15664 15665 synchronized(this) { 15666 r = broadcastRecordForReceiverLocked(who); 15667 if (r != null) { 15668 doNext = r.queue.finishReceiverLocked(r, resultCode, 15669 resultData, resultExtras, resultAbort, true); 15670 } 15671 } 15672 15673 if (doNext) { 15674 r.queue.processNextBroadcast(false); 15675 } 15676 trimApplications(); 15677 } finally { 15678 Binder.restoreCallingIdentity(origId); 15679 } 15680 } 15681 15682 // ========================================================= 15683 // INSTRUMENTATION 15684 // ========================================================= 15685 15686 public boolean startInstrumentation(ComponentName className, 15687 String profileFile, int flags, Bundle arguments, 15688 IInstrumentationWatcher watcher, IUiAutomationConnection uiAutomationConnection, 15689 int userId, String abiOverride) { 15690 enforceNotIsolatedCaller("startInstrumentation"); 15691 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 15692 userId, false, ALLOW_FULL_ONLY, "startInstrumentation", null); 15693 // Refuse possible leaked file descriptors 15694 if (arguments != null && arguments.hasFileDescriptors()) { 15695 throw new IllegalArgumentException("File descriptors passed in Bundle"); 15696 } 15697 15698 synchronized(this) { 15699 InstrumentationInfo ii = null; 15700 ApplicationInfo ai = null; 15701 try { 15702 ii = mContext.getPackageManager().getInstrumentationInfo( 15703 className, STOCK_PM_FLAGS); 15704 ai = AppGlobals.getPackageManager().getApplicationInfo( 15705 ii.targetPackage, STOCK_PM_FLAGS, userId); 15706 } catch (PackageManager.NameNotFoundException e) { 15707 } catch (RemoteException e) { 15708 } 15709 if (ii == null) { 15710 reportStartInstrumentationFailure(watcher, className, 15711 "Unable to find instrumentation info for: " + className); 15712 return false; 15713 } 15714 if (ai == null) { 15715 reportStartInstrumentationFailure(watcher, className, 15716 "Unable to find instrumentation target package: " + ii.targetPackage); 15717 return false; 15718 } 15719 15720 int match = mContext.getPackageManager().checkSignatures( 15721 ii.targetPackage, ii.packageName); 15722 if (match < 0 && match != PackageManager.SIGNATURE_FIRST_NOT_SIGNED) { 15723 String msg = "Permission Denial: starting instrumentation " 15724 + className + " from pid=" 15725 + Binder.getCallingPid() 15726 + ", uid=" + Binder.getCallingPid() 15727 + " not allowed because package " + ii.packageName 15728 + " does not have a signature matching the target " 15729 + ii.targetPackage; 15730 reportStartInstrumentationFailure(watcher, className, msg); 15731 throw new SecurityException(msg); 15732 } 15733 15734 final long origId = Binder.clearCallingIdentity(); 15735 // Instrumentation can kill and relaunch even persistent processes 15736 forceStopPackageLocked(ii.targetPackage, -1, true, false, true, true, false, userId, 15737 "start instr"); 15738 ProcessRecord app = addAppLocked(ai, false, abiOverride); 15739 app.instrumentationClass = className; 15740 app.instrumentationInfo = ai; 15741 app.instrumentationProfileFile = profileFile; 15742 app.instrumentationArguments = arguments; 15743 app.instrumentationWatcher = watcher; 15744 app.instrumentationUiAutomationConnection = uiAutomationConnection; 15745 app.instrumentationResultClass = className; 15746 Binder.restoreCallingIdentity(origId); 15747 } 15748 15749 return true; 15750 } 15751 15752 /** 15753 * Report errors that occur while attempting to start Instrumentation. Always writes the 15754 * error to the logs, but if somebody is watching, send the report there too. This enables 15755 * the "am" command to report errors with more information. 15756 * 15757 * @param watcher The IInstrumentationWatcher. Null if there isn't one. 15758 * @param cn The component name of the instrumentation. 15759 * @param report The error report. 15760 */ 15761 private void reportStartInstrumentationFailure(IInstrumentationWatcher watcher, 15762 ComponentName cn, String report) { 15763 Slog.w(TAG, report); 15764 try { 15765 if (watcher != null) { 15766 Bundle results = new Bundle(); 15767 results.putString(Instrumentation.REPORT_KEY_IDENTIFIER, "ActivityManagerService"); 15768 results.putString("Error", report); 15769 watcher.instrumentationStatus(cn, -1, results); 15770 } 15771 } catch (RemoteException e) { 15772 Slog.w(TAG, e); 15773 } 15774 } 15775 15776 void finishInstrumentationLocked(ProcessRecord app, int resultCode, Bundle results) { 15777 if (app.instrumentationWatcher != null) { 15778 try { 15779 // NOTE: IInstrumentationWatcher *must* be oneway here 15780 app.instrumentationWatcher.instrumentationFinished( 15781 app.instrumentationClass, 15782 resultCode, 15783 results); 15784 } catch (RemoteException e) { 15785 } 15786 } 15787 if (app.instrumentationUiAutomationConnection != null) { 15788 try { 15789 app.instrumentationUiAutomationConnection.shutdown(); 15790 } catch (RemoteException re) { 15791 /* ignore */ 15792 } 15793 // Only a UiAutomation can set this flag and now that 15794 // it is finished we make sure it is reset to its default. 15795 mUserIsMonkey = false; 15796 } 15797 app.instrumentationWatcher = null; 15798 app.instrumentationUiAutomationConnection = null; 15799 app.instrumentationClass = null; 15800 app.instrumentationInfo = null; 15801 app.instrumentationProfileFile = null; 15802 app.instrumentationArguments = null; 15803 15804 forceStopPackageLocked(app.info.packageName, -1, false, false, true, true, false, app.userId, 15805 "finished inst"); 15806 } 15807 15808 public void finishInstrumentation(IApplicationThread target, 15809 int resultCode, Bundle results) { 15810 int userId = UserHandle.getCallingUserId(); 15811 // Refuse possible leaked file descriptors 15812 if (results != null && results.hasFileDescriptors()) { 15813 throw new IllegalArgumentException("File descriptors passed in Intent"); 15814 } 15815 15816 synchronized(this) { 15817 ProcessRecord app = getRecordForAppLocked(target); 15818 if (app == null) { 15819 Slog.w(TAG, "finishInstrumentation: no app for " + target); 15820 return; 15821 } 15822 final long origId = Binder.clearCallingIdentity(); 15823 finishInstrumentationLocked(app, resultCode, results); 15824 Binder.restoreCallingIdentity(origId); 15825 } 15826 } 15827 15828 // ========================================================= 15829 // CONFIGURATION 15830 // ========================================================= 15831 15832 public ConfigurationInfo getDeviceConfigurationInfo() { 15833 ConfigurationInfo config = new ConfigurationInfo(); 15834 synchronized (this) { 15835 config.reqTouchScreen = mConfiguration.touchscreen; 15836 config.reqKeyboardType = mConfiguration.keyboard; 15837 config.reqNavigation = mConfiguration.navigation; 15838 if (mConfiguration.navigation == Configuration.NAVIGATION_DPAD 15839 || mConfiguration.navigation == Configuration.NAVIGATION_TRACKBALL) { 15840 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_FIVE_WAY_NAV; 15841 } 15842 if (mConfiguration.keyboard != Configuration.KEYBOARD_UNDEFINED 15843 && mConfiguration.keyboard != Configuration.KEYBOARD_NOKEYS) { 15844 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_HARD_KEYBOARD; 15845 } 15846 config.reqGlEsVersion = GL_ES_VERSION; 15847 } 15848 return config; 15849 } 15850 15851 ActivityStack getFocusedStack() { 15852 return mStackSupervisor.getFocusedStack(); 15853 } 15854 15855 public Configuration getConfiguration() { 15856 Configuration ci; 15857 synchronized(this) { 15858 ci = new Configuration(mConfiguration); 15859 } 15860 return ci; 15861 } 15862 15863 public void updatePersistentConfiguration(Configuration values) { 15864 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 15865 "updateConfiguration()"); 15866 enforceCallingPermission(android.Manifest.permission.WRITE_SETTINGS, 15867 "updateConfiguration()"); 15868 if (values == null) { 15869 throw new NullPointerException("Configuration must not be null"); 15870 } 15871 15872 synchronized(this) { 15873 final long origId = Binder.clearCallingIdentity(); 15874 updateConfigurationLocked(values, null, true, false); 15875 Binder.restoreCallingIdentity(origId); 15876 } 15877 } 15878 15879 public void updateConfiguration(Configuration values) { 15880 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 15881 "updateConfiguration()"); 15882 15883 synchronized(this) { 15884 if (values == null && mWindowManager != null) { 15885 // sentinel: fetch the current configuration from the window manager 15886 values = mWindowManager.computeNewConfiguration(); 15887 } 15888 15889 if (mWindowManager != null) { 15890 mProcessList.applyDisplaySize(mWindowManager); 15891 } 15892 15893 final long origId = Binder.clearCallingIdentity(); 15894 if (values != null) { 15895 Settings.System.clearConfiguration(values); 15896 } 15897 updateConfigurationLocked(values, null, false, false); 15898 Binder.restoreCallingIdentity(origId); 15899 } 15900 } 15901 15902 /** 15903 * Do either or both things: (1) change the current configuration, and (2) 15904 * make sure the given activity is running with the (now) current 15905 * configuration. Returns true if the activity has been left running, or 15906 * false if <var>starting</var> is being destroyed to match the new 15907 * configuration. 15908 * @param persistent TODO 15909 */ 15910 boolean updateConfigurationLocked(Configuration values, 15911 ActivityRecord starting, boolean persistent, boolean initLocale) { 15912 int changes = 0; 15913 15914 if (values != null) { 15915 Configuration newConfig = new Configuration(mConfiguration); 15916 changes = newConfig.updateFrom(values); 15917 if (changes != 0) { 15918 if (DEBUG_SWITCH || DEBUG_CONFIGURATION) { 15919 Slog.i(TAG, "Updating configuration to: " + values); 15920 } 15921 15922 EventLog.writeEvent(EventLogTags.CONFIGURATION_CHANGED, changes); 15923 15924 if (values.locale != null && !initLocale) { 15925 saveLocaleLocked(values.locale, 15926 !values.locale.equals(mConfiguration.locale), 15927 values.userSetLocale); 15928 } 15929 15930 mConfigurationSeq++; 15931 if (mConfigurationSeq <= 0) { 15932 mConfigurationSeq = 1; 15933 } 15934 newConfig.seq = mConfigurationSeq; 15935 mConfiguration = newConfig; 15936 Slog.i(TAG, "Config changes=" + Integer.toHexString(changes) + " " + newConfig); 15937 mUsageStatsService.reportConfigurationChange(newConfig, mCurrentUserId); 15938 //mUsageStatsService.noteStartConfig(newConfig); 15939 15940 final Configuration configCopy = new Configuration(mConfiguration); 15941 15942 // TODO: If our config changes, should we auto dismiss any currently 15943 // showing dialogs? 15944 mShowDialogs = shouldShowDialogs(newConfig); 15945 15946 AttributeCache ac = AttributeCache.instance(); 15947 if (ac != null) { 15948 ac.updateConfiguration(configCopy); 15949 } 15950 15951 // Make sure all resources in our process are updated 15952 // right now, so that anyone who is going to retrieve 15953 // resource values after we return will be sure to get 15954 // the new ones. This is especially important during 15955 // boot, where the first config change needs to guarantee 15956 // all resources have that config before following boot 15957 // code is executed. 15958 mSystemThread.applyConfigurationToResources(configCopy); 15959 15960 if (persistent && Settings.System.hasInterestingConfigurationChanges(changes)) { 15961 Message msg = mHandler.obtainMessage(UPDATE_CONFIGURATION_MSG); 15962 msg.obj = new Configuration(configCopy); 15963 mHandler.sendMessage(msg); 15964 } 15965 15966 for (int i=mLruProcesses.size()-1; i>=0; i--) { 15967 ProcessRecord app = mLruProcesses.get(i); 15968 try { 15969 if (app.thread != null) { 15970 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Sending to proc " 15971 + app.processName + " new config " + mConfiguration); 15972 app.thread.scheduleConfigurationChanged(configCopy); 15973 } 15974 } catch (Exception e) { 15975 } 15976 } 15977 Intent intent = new Intent(Intent.ACTION_CONFIGURATION_CHANGED); 15978 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 15979 | Intent.FLAG_RECEIVER_REPLACE_PENDING 15980 | Intent.FLAG_RECEIVER_FOREGROUND); 15981 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, 15982 null, AppOpsManager.OP_NONE, false, false, MY_PID, 15983 Process.SYSTEM_UID, UserHandle.USER_ALL); 15984 if ((changes&ActivityInfo.CONFIG_LOCALE) != 0) { 15985 intent = new Intent(Intent.ACTION_LOCALE_CHANGED); 15986 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 15987 broadcastIntentLocked(null, null, intent, 15988 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 15989 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 15990 } 15991 } 15992 } 15993 15994 boolean kept = true; 15995 final ActivityStack mainStack = mStackSupervisor.getFocusedStack(); 15996 // mainStack is null during startup. 15997 if (mainStack != null) { 15998 if (changes != 0 && starting == null) { 15999 // If the configuration changed, and the caller is not already 16000 // in the process of starting an activity, then find the top 16001 // activity to check if its configuration needs to change. 16002 starting = mainStack.topRunningActivityLocked(null); 16003 } 16004 16005 if (starting != null) { 16006 kept = mainStack.ensureActivityConfigurationLocked(starting, changes); 16007 // And we need to make sure at this point that all other activities 16008 // are made visible with the correct configuration. 16009 mStackSupervisor.ensureActivitiesVisibleLocked(starting, changes); 16010 } 16011 } 16012 16013 if (values != null && mWindowManager != null) { 16014 mWindowManager.setNewConfiguration(mConfiguration); 16015 } 16016 16017 return kept; 16018 } 16019 16020 /** 16021 * Decide based on the configuration whether we should shouw the ANR, 16022 * crash, etc dialogs. The idea is that if there is no affordnace to 16023 * press the on-screen buttons, we shouldn't show the dialog. 16024 * 16025 * A thought: SystemUI might also want to get told about this, the Power 16026 * dialog / global actions also might want different behaviors. 16027 */ 16028 private static final boolean shouldShowDialogs(Configuration config) { 16029 return !(config.keyboard == Configuration.KEYBOARD_NOKEYS 16030 && config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH); 16031 } 16032 16033 /** 16034 * Save the locale. You must be inside a synchronized (this) block. 16035 */ 16036 private void saveLocaleLocked(Locale l, boolean isDiff, boolean isPersist) { 16037 if(isDiff) { 16038 SystemProperties.set("user.language", l.getLanguage()); 16039 SystemProperties.set("user.region", l.getCountry()); 16040 } 16041 16042 if(isPersist) { 16043 SystemProperties.set("persist.sys.language", l.getLanguage()); 16044 SystemProperties.set("persist.sys.country", l.getCountry()); 16045 SystemProperties.set("persist.sys.localevar", l.getVariant()); 16046 } 16047 } 16048 16049 @Override 16050 public boolean shouldUpRecreateTask(IBinder token, String destAffinity) { 16051 synchronized (this) { 16052 ActivityRecord srec = ActivityRecord.forToken(token); 16053 if (srec.task != null && srec.task.stack != null) { 16054 return srec.task.stack.shouldUpRecreateTaskLocked(srec, destAffinity); 16055 } 16056 } 16057 return false; 16058 } 16059 16060 public boolean navigateUpTo(IBinder token, Intent destIntent, int resultCode, 16061 Intent resultData) { 16062 16063 synchronized (this) { 16064 final ActivityStack stack = ActivityRecord.getStackLocked(token); 16065 if (stack != null) { 16066 return stack.navigateUpToLocked(token, destIntent, resultCode, resultData); 16067 } 16068 return false; 16069 } 16070 } 16071 16072 public int getLaunchedFromUid(IBinder activityToken) { 16073 ActivityRecord srec = ActivityRecord.forToken(activityToken); 16074 if (srec == null) { 16075 return -1; 16076 } 16077 return srec.launchedFromUid; 16078 } 16079 16080 public String getLaunchedFromPackage(IBinder activityToken) { 16081 ActivityRecord srec = ActivityRecord.forToken(activityToken); 16082 if (srec == null) { 16083 return null; 16084 } 16085 return srec.launchedFromPackage; 16086 } 16087 16088 // ========================================================= 16089 // LIFETIME MANAGEMENT 16090 // ========================================================= 16091 16092 // Returns which broadcast queue the app is the current [or imminent] receiver 16093 // on, or 'null' if the app is not an active broadcast recipient. 16094 private BroadcastQueue isReceivingBroadcast(ProcessRecord app) { 16095 BroadcastRecord r = app.curReceiver; 16096 if (r != null) { 16097 return r.queue; 16098 } 16099 16100 // It's not the current receiver, but it might be starting up to become one 16101 synchronized (this) { 16102 for (BroadcastQueue queue : mBroadcastQueues) { 16103 r = queue.mPendingBroadcast; 16104 if (r != null && r.curApp == app) { 16105 // found it; report which queue it's in 16106 return queue; 16107 } 16108 } 16109 } 16110 16111 return null; 16112 } 16113 16114 private final int computeOomAdjLocked(ProcessRecord app, int cachedAdj, ProcessRecord TOP_APP, 16115 boolean doingAll, long now) { 16116 if (mAdjSeq == app.adjSeq) { 16117 // This adjustment has already been computed. 16118 return app.curRawAdj; 16119 } 16120 16121 if (app.thread == null) { 16122 app.adjSeq = mAdjSeq; 16123 app.curSchedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16124 app.curProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16125 return (app.curAdj=app.curRawAdj=ProcessList.CACHED_APP_MAX_ADJ); 16126 } 16127 16128 app.adjTypeCode = ActivityManager.RunningAppProcessInfo.REASON_UNKNOWN; 16129 app.adjSource = null; 16130 app.adjTarget = null; 16131 app.empty = false; 16132 app.cached = false; 16133 16134 final int activitiesSize = app.activities.size(); 16135 16136 if (app.maxAdj <= ProcessList.FOREGROUND_APP_ADJ) { 16137 // The max adjustment doesn't allow this app to be anything 16138 // below foreground, so it is not worth doing work for it. 16139 app.adjType = "fixed"; 16140 app.adjSeq = mAdjSeq; 16141 app.curRawAdj = app.maxAdj; 16142 app.foregroundActivities = false; 16143 app.curSchedGroup = Process.THREAD_GROUP_DEFAULT; 16144 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT; 16145 // System processes can do UI, and when they do we want to have 16146 // them trim their memory after the user leaves the UI. To 16147 // facilitate this, here we need to determine whether or not it 16148 // is currently showing UI. 16149 app.systemNoUi = true; 16150 if (app == TOP_APP) { 16151 app.systemNoUi = false; 16152 } else if (activitiesSize > 0) { 16153 for (int j = 0; j < activitiesSize; j++) { 16154 final ActivityRecord r = app.activities.get(j); 16155 if (r.visible) { 16156 app.systemNoUi = false; 16157 } 16158 } 16159 } 16160 if (!app.systemNoUi) { 16161 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT_UI; 16162 } 16163 return (app.curAdj=app.maxAdj); 16164 } 16165 16166 app.systemNoUi = false; 16167 16168 // Determine the importance of the process, starting with most 16169 // important to least, and assign an appropriate OOM adjustment. 16170 int adj; 16171 int schedGroup; 16172 int procState; 16173 boolean foregroundActivities = false; 16174 BroadcastQueue queue; 16175 if (app == TOP_APP) { 16176 // The last app on the list is the foreground app. 16177 adj = ProcessList.FOREGROUND_APP_ADJ; 16178 schedGroup = Process.THREAD_GROUP_DEFAULT; 16179 app.adjType = "top-activity"; 16180 foregroundActivities = true; 16181 procState = ActivityManager.PROCESS_STATE_TOP; 16182 } else if (app.instrumentationClass != null) { 16183 // Don't want to kill running instrumentation. 16184 adj = ProcessList.FOREGROUND_APP_ADJ; 16185 schedGroup = Process.THREAD_GROUP_DEFAULT; 16186 app.adjType = "instrumentation"; 16187 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16188 } else if ((queue = isReceivingBroadcast(app)) != null) { 16189 // An app that is currently receiving a broadcast also 16190 // counts as being in the foreground for OOM killer purposes. 16191 // It's placed in a sched group based on the nature of the 16192 // broadcast as reflected by which queue it's active in. 16193 adj = ProcessList.FOREGROUND_APP_ADJ; 16194 schedGroup = (queue == mFgBroadcastQueue) 16195 ? Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 16196 app.adjType = "broadcast"; 16197 procState = ActivityManager.PROCESS_STATE_RECEIVER; 16198 } else if (app.executingServices.size() > 0) { 16199 // An app that is currently executing a service callback also 16200 // counts as being in the foreground. 16201 adj = ProcessList.FOREGROUND_APP_ADJ; 16202 schedGroup = app.execServicesFg ? 16203 Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 16204 app.adjType = "exec-service"; 16205 procState = ActivityManager.PROCESS_STATE_SERVICE; 16206 //Slog.i(TAG, "EXEC " + (app.execServicesFg ? "FG" : "BG") + ": " + app); 16207 } else { 16208 // As far as we know the process is empty. We may change our mind later. 16209 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16210 // At this point we don't actually know the adjustment. Use the cached adj 16211 // value that the caller wants us to. 16212 adj = cachedAdj; 16213 procState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16214 app.cached = true; 16215 app.empty = true; 16216 app.adjType = "cch-empty"; 16217 } 16218 16219 // Examine all activities if not already foreground. 16220 if (!foregroundActivities && activitiesSize > 0) { 16221 for (int j = 0; j < activitiesSize; j++) { 16222 final ActivityRecord r = app.activities.get(j); 16223 if (r.app != app) { 16224 Slog.w(TAG, "Wtf, activity " + r + " in proc activity list not using proc " 16225 + app + "?!?"); 16226 continue; 16227 } 16228 if (r.visible) { 16229 // App has a visible activity; only upgrade adjustment. 16230 if (adj > ProcessList.VISIBLE_APP_ADJ) { 16231 adj = ProcessList.VISIBLE_APP_ADJ; 16232 app.adjType = "visible"; 16233 } 16234 if (procState > ActivityManager.PROCESS_STATE_TOP) { 16235 procState = ActivityManager.PROCESS_STATE_TOP; 16236 } 16237 schedGroup = Process.THREAD_GROUP_DEFAULT; 16238 app.cached = false; 16239 app.empty = false; 16240 foregroundActivities = true; 16241 break; 16242 } else if (r.state == ActivityState.PAUSING || r.state == ActivityState.PAUSED) { 16243 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16244 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16245 app.adjType = "pausing"; 16246 } 16247 if (procState > ActivityManager.PROCESS_STATE_TOP) { 16248 procState = ActivityManager.PROCESS_STATE_TOP; 16249 } 16250 schedGroup = Process.THREAD_GROUP_DEFAULT; 16251 app.cached = false; 16252 app.empty = false; 16253 foregroundActivities = true; 16254 } else if (r.state == ActivityState.STOPPING) { 16255 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16256 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16257 app.adjType = "stopping"; 16258 } 16259 // For the process state, we will at this point consider the 16260 // process to be cached. It will be cached either as an activity 16261 // or empty depending on whether the activity is finishing. We do 16262 // this so that we can treat the process as cached for purposes of 16263 // memory trimming (determing current memory level, trim command to 16264 // send to process) since there can be an arbitrary number of stopping 16265 // processes and they should soon all go into the cached state. 16266 if (!r.finishing) { 16267 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 16268 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 16269 } 16270 } 16271 app.cached = false; 16272 app.empty = false; 16273 foregroundActivities = true; 16274 } else { 16275 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 16276 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 16277 app.adjType = "cch-act"; 16278 } 16279 } 16280 } 16281 } 16282 16283 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16284 if (app.foregroundServices) { 16285 // The user is aware of this app, so make it visible. 16286 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16287 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16288 app.cached = false; 16289 app.adjType = "fg-service"; 16290 schedGroup = Process.THREAD_GROUP_DEFAULT; 16291 } else if (app.forcingToForeground != null) { 16292 // The user is aware of this app, so make it visible. 16293 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16294 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16295 app.cached = false; 16296 app.adjType = "force-fg"; 16297 app.adjSource = app.forcingToForeground; 16298 schedGroup = Process.THREAD_GROUP_DEFAULT; 16299 } 16300 } 16301 16302 if (app == mHeavyWeightProcess) { 16303 if (adj > ProcessList.HEAVY_WEIGHT_APP_ADJ) { 16304 // We don't want to kill the current heavy-weight process. 16305 adj = ProcessList.HEAVY_WEIGHT_APP_ADJ; 16306 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16307 app.cached = false; 16308 app.adjType = "heavy"; 16309 } 16310 if (procState > ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 16311 procState = ActivityManager.PROCESS_STATE_HEAVY_WEIGHT; 16312 } 16313 } 16314 16315 if (app == mHomeProcess) { 16316 if (adj > ProcessList.HOME_APP_ADJ) { 16317 // This process is hosting what we currently consider to be the 16318 // home app, so we don't want to let it go into the background. 16319 adj = ProcessList.HOME_APP_ADJ; 16320 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16321 app.cached = false; 16322 app.adjType = "home"; 16323 } 16324 if (procState > ActivityManager.PROCESS_STATE_HOME) { 16325 procState = ActivityManager.PROCESS_STATE_HOME; 16326 } 16327 } 16328 16329 if (app == mPreviousProcess && app.activities.size() > 0) { 16330 if (adj > ProcessList.PREVIOUS_APP_ADJ) { 16331 // This was the previous process that showed UI to the user. 16332 // We want to try to keep it around more aggressively, to give 16333 // a good experience around switching between two apps. 16334 adj = ProcessList.PREVIOUS_APP_ADJ; 16335 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 16336 app.cached = false; 16337 app.adjType = "previous"; 16338 } 16339 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 16340 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 16341 } 16342 } 16343 16344 if (false) Slog.i(TAG, "OOM " + app + ": initial adj=" + adj 16345 + " reason=" + app.adjType); 16346 16347 // By default, we use the computed adjustment. It may be changed if 16348 // there are applications dependent on our services or providers, but 16349 // this gives us a baseline and makes sure we don't get into an 16350 // infinite recursion. 16351 app.adjSeq = mAdjSeq; 16352 app.curRawAdj = adj; 16353 app.hasStartedServices = false; 16354 16355 if (mBackupTarget != null && app == mBackupTarget.app) { 16356 // If possible we want to avoid killing apps while they're being backed up 16357 if (adj > ProcessList.BACKUP_APP_ADJ) { 16358 if (DEBUG_BACKUP) Slog.v(TAG, "oom BACKUP_APP_ADJ for " + app); 16359 adj = ProcessList.BACKUP_APP_ADJ; 16360 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 16361 procState = ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 16362 } 16363 app.adjType = "backup"; 16364 app.cached = false; 16365 } 16366 if (procState > ActivityManager.PROCESS_STATE_BACKUP) { 16367 procState = ActivityManager.PROCESS_STATE_BACKUP; 16368 } 16369 } 16370 16371 boolean mayBeTop = false; 16372 16373 for (int is = app.services.size()-1; 16374 is >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 16375 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16376 || procState > ActivityManager.PROCESS_STATE_TOP); 16377 is--) { 16378 ServiceRecord s = app.services.valueAt(is); 16379 if (s.startRequested) { 16380 app.hasStartedServices = true; 16381 if (procState > ActivityManager.PROCESS_STATE_SERVICE) { 16382 procState = ActivityManager.PROCESS_STATE_SERVICE; 16383 } 16384 if (app.hasShownUi && app != mHomeProcess) { 16385 // If this process has shown some UI, let it immediately 16386 // go to the LRU list because it may be pretty heavy with 16387 // UI stuff. We'll tag it with a label just to help 16388 // debug and understand what is going on. 16389 if (adj > ProcessList.SERVICE_ADJ) { 16390 app.adjType = "cch-started-ui-services"; 16391 } 16392 } else { 16393 if (now < (s.lastActivity + ActiveServices.MAX_SERVICE_INACTIVITY)) { 16394 // This service has seen some activity within 16395 // recent memory, so we will keep its process ahead 16396 // of the background processes. 16397 if (adj > ProcessList.SERVICE_ADJ) { 16398 adj = ProcessList.SERVICE_ADJ; 16399 app.adjType = "started-services"; 16400 app.cached = false; 16401 } 16402 } 16403 // If we have let the service slide into the background 16404 // state, still have some text describing what it is doing 16405 // even though the service no longer has an impact. 16406 if (adj > ProcessList.SERVICE_ADJ) { 16407 app.adjType = "cch-started-services"; 16408 } 16409 } 16410 } 16411 for (int conni = s.connections.size()-1; 16412 conni >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 16413 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16414 || procState > ActivityManager.PROCESS_STATE_TOP); 16415 conni--) { 16416 ArrayList<ConnectionRecord> clist = s.connections.valueAt(conni); 16417 for (int i = 0; 16418 i < clist.size() && (adj > ProcessList.FOREGROUND_APP_ADJ 16419 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16420 || procState > ActivityManager.PROCESS_STATE_TOP); 16421 i++) { 16422 // XXX should compute this based on the max of 16423 // all connected clients. 16424 ConnectionRecord cr = clist.get(i); 16425 if (cr.binding.client == app) { 16426 // Binding to ourself is not interesting. 16427 continue; 16428 } 16429 if ((cr.flags&Context.BIND_WAIVE_PRIORITY) == 0) { 16430 ProcessRecord client = cr.binding.client; 16431 int clientAdj = computeOomAdjLocked(client, cachedAdj, 16432 TOP_APP, doingAll, now); 16433 int clientProcState = client.curProcState; 16434 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 16435 // If the other app is cached for any reason, for purposes here 16436 // we are going to consider it empty. The specific cached state 16437 // doesn't propagate except under certain conditions. 16438 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16439 } 16440 String adjType = null; 16441 if ((cr.flags&Context.BIND_ALLOW_OOM_MANAGEMENT) != 0) { 16442 // Not doing bind OOM management, so treat 16443 // this guy more like a started service. 16444 if (app.hasShownUi && app != mHomeProcess) { 16445 // If this process has shown some UI, let it immediately 16446 // go to the LRU list because it may be pretty heavy with 16447 // UI stuff. We'll tag it with a label just to help 16448 // debug and understand what is going on. 16449 if (adj > clientAdj) { 16450 adjType = "cch-bound-ui-services"; 16451 } 16452 app.cached = false; 16453 clientAdj = adj; 16454 clientProcState = procState; 16455 } else { 16456 if (now >= (s.lastActivity 16457 + ActiveServices.MAX_SERVICE_INACTIVITY)) { 16458 // This service has not seen activity within 16459 // recent memory, so allow it to drop to the 16460 // LRU list if there is no other reason to keep 16461 // it around. We'll also tag it with a label just 16462 // to help debug and undertand what is going on. 16463 if (adj > clientAdj) { 16464 adjType = "cch-bound-services"; 16465 } 16466 clientAdj = adj; 16467 } 16468 } 16469 } 16470 if (adj > clientAdj) { 16471 // If this process has recently shown UI, and 16472 // the process that is binding to it is less 16473 // important than being visible, then we don't 16474 // care about the binding as much as we care 16475 // about letting this process get into the LRU 16476 // list to be killed and restarted if needed for 16477 // memory. 16478 if (app.hasShownUi && app != mHomeProcess 16479 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16480 adjType = "cch-bound-ui-services"; 16481 } else { 16482 if ((cr.flags&(Context.BIND_ABOVE_CLIENT 16483 |Context.BIND_IMPORTANT)) != 0) { 16484 adj = clientAdj; 16485 } else if ((cr.flags&Context.BIND_NOT_VISIBLE) != 0 16486 && clientAdj < ProcessList.PERCEPTIBLE_APP_ADJ 16487 && adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16488 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 16489 } else if (clientAdj > ProcessList.VISIBLE_APP_ADJ) { 16490 adj = clientAdj; 16491 } else { 16492 if (adj > ProcessList.VISIBLE_APP_ADJ) { 16493 adj = ProcessList.VISIBLE_APP_ADJ; 16494 } 16495 } 16496 if (!client.cached) { 16497 app.cached = false; 16498 } 16499 adjType = "service"; 16500 } 16501 } 16502 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 16503 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 16504 schedGroup = Process.THREAD_GROUP_DEFAULT; 16505 } 16506 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 16507 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 16508 // Special handling of clients who are in the top state. 16509 // We *may* want to consider this process to be in the 16510 // top state as well, but only if there is not another 16511 // reason for it to be running. Being on the top is a 16512 // special state, meaning you are specifically running 16513 // for the current top app. If the process is already 16514 // running in the background for some other reason, it 16515 // is more important to continue considering it to be 16516 // in the background state. 16517 mayBeTop = true; 16518 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16519 } else { 16520 // Special handling for above-top states (persistent 16521 // processes). These should not bring the current process 16522 // into the top state, since they are not on top. Instead 16523 // give them the best state after that. 16524 clientProcState = 16525 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16526 } 16527 } 16528 } else { 16529 if (clientProcState < 16530 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 16531 clientProcState = 16532 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 16533 } 16534 } 16535 if (procState > clientProcState) { 16536 procState = clientProcState; 16537 } 16538 if (procState < ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 16539 && (cr.flags&Context.BIND_SHOWING_UI) != 0) { 16540 app.pendingUiClean = true; 16541 } 16542 if (adjType != null) { 16543 app.adjType = adjType; 16544 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 16545 .REASON_SERVICE_IN_USE; 16546 app.adjSource = cr.binding.client; 16547 app.adjSourceProcState = clientProcState; 16548 app.adjTarget = s.name; 16549 } 16550 } 16551 if ((cr.flags&Context.BIND_TREAT_LIKE_ACTIVITY) != 0) { 16552 app.treatLikeActivity = true; 16553 } 16554 final ActivityRecord a = cr.activity; 16555 if ((cr.flags&Context.BIND_ADJUST_WITH_ACTIVITY) != 0) { 16556 if (a != null && adj > ProcessList.FOREGROUND_APP_ADJ && 16557 (a.visible || a.state == ActivityState.RESUMED 16558 || a.state == ActivityState.PAUSING)) { 16559 adj = ProcessList.FOREGROUND_APP_ADJ; 16560 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 16561 schedGroup = Process.THREAD_GROUP_DEFAULT; 16562 } 16563 app.cached = false; 16564 app.adjType = "service"; 16565 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 16566 .REASON_SERVICE_IN_USE; 16567 app.adjSource = a; 16568 app.adjSourceProcState = procState; 16569 app.adjTarget = s.name; 16570 } 16571 } 16572 } 16573 } 16574 } 16575 16576 for (int provi = app.pubProviders.size()-1; 16577 provi >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 16578 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16579 || procState > ActivityManager.PROCESS_STATE_TOP); 16580 provi--) { 16581 ContentProviderRecord cpr = app.pubProviders.valueAt(provi); 16582 for (int i = cpr.connections.size()-1; 16583 i >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 16584 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 16585 || procState > ActivityManager.PROCESS_STATE_TOP); 16586 i--) { 16587 ContentProviderConnection conn = cpr.connections.get(i); 16588 ProcessRecord client = conn.client; 16589 if (client == app) { 16590 // Being our own client is not interesting. 16591 continue; 16592 } 16593 int clientAdj = computeOomAdjLocked(client, cachedAdj, TOP_APP, doingAll, now); 16594 int clientProcState = client.curProcState; 16595 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 16596 // If the other app is cached for any reason, for purposes here 16597 // we are going to consider it empty. 16598 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16599 } 16600 if (adj > clientAdj) { 16601 if (app.hasShownUi && app != mHomeProcess 16602 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 16603 app.adjType = "cch-ui-provider"; 16604 } else { 16605 adj = clientAdj > ProcessList.FOREGROUND_APP_ADJ 16606 ? clientAdj : ProcessList.FOREGROUND_APP_ADJ; 16607 app.adjType = "provider"; 16608 } 16609 app.cached &= client.cached; 16610 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 16611 .REASON_PROVIDER_IN_USE; 16612 app.adjSource = client; 16613 app.adjSourceProcState = clientProcState; 16614 app.adjTarget = cpr.name; 16615 } 16616 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 16617 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 16618 // Special handling of clients who are in the top state. 16619 // We *may* want to consider this process to be in the 16620 // top state as well, but only if there is not another 16621 // reason for it to be running. Being on the top is a 16622 // special state, meaning you are specifically running 16623 // for the current top app. If the process is already 16624 // running in the background for some other reason, it 16625 // is more important to continue considering it to be 16626 // in the background state. 16627 mayBeTop = true; 16628 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 16629 } else { 16630 // Special handling for above-top states (persistent 16631 // processes). These should not bring the current process 16632 // into the top state, since they are not on top. Instead 16633 // give them the best state after that. 16634 clientProcState = 16635 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16636 } 16637 } 16638 if (procState > clientProcState) { 16639 procState = clientProcState; 16640 } 16641 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 16642 schedGroup = Process.THREAD_GROUP_DEFAULT; 16643 } 16644 } 16645 // If the provider has external (non-framework) process 16646 // dependencies, ensure that its adjustment is at least 16647 // FOREGROUND_APP_ADJ. 16648 if (cpr.hasExternalProcessHandles()) { 16649 if (adj > ProcessList.FOREGROUND_APP_ADJ) { 16650 adj = ProcessList.FOREGROUND_APP_ADJ; 16651 schedGroup = Process.THREAD_GROUP_DEFAULT; 16652 app.cached = false; 16653 app.adjType = "provider"; 16654 app.adjTarget = cpr.name; 16655 } 16656 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) { 16657 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16658 } 16659 } 16660 } 16661 16662 if (mayBeTop && procState > ActivityManager.PROCESS_STATE_TOP) { 16663 // A client of one of our services or providers is in the top state. We 16664 // *may* want to be in the top state, but not if we are already running in 16665 // the background for some other reason. For the decision here, we are going 16666 // to pick out a few specific states that we want to remain in when a client 16667 // is top (states that tend to be longer-term) and otherwise allow it to go 16668 // to the top state. 16669 switch (procState) { 16670 case ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND: 16671 case ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND: 16672 case ActivityManager.PROCESS_STATE_SERVICE: 16673 // These all are longer-term states, so pull them up to the top 16674 // of the background states, but not all the way to the top state. 16675 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 16676 break; 16677 default: 16678 // Otherwise, top is a better choice, so take it. 16679 procState = ActivityManager.PROCESS_STATE_TOP; 16680 break; 16681 } 16682 } 16683 16684 if (procState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 16685 if (app.hasClientActivities) { 16686 // This is a cached process, but with client activities. Mark it so. 16687 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT; 16688 app.adjType = "cch-client-act"; 16689 } else if (app.treatLikeActivity) { 16690 // This is a cached process, but somebody wants us to treat it like it has 16691 // an activity, okay! 16692 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 16693 app.adjType = "cch-as-act"; 16694 } 16695 } 16696 16697 if (adj == ProcessList.SERVICE_ADJ) { 16698 if (doingAll) { 16699 app.serviceb = mNewNumAServiceProcs > (mNumServiceProcs/3); 16700 mNewNumServiceProcs++; 16701 //Slog.i(TAG, "ADJ " + app + " serviceb=" + app.serviceb); 16702 if (!app.serviceb) { 16703 // This service isn't far enough down on the LRU list to 16704 // normally be a B service, but if we are low on RAM and it 16705 // is large we want to force it down since we would prefer to 16706 // keep launcher over it. 16707 if (mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 16708 && app.lastPss >= mProcessList.getCachedRestoreThresholdKb()) { 16709 app.serviceHighRam = true; 16710 app.serviceb = true; 16711 //Slog.i(TAG, "ADJ " + app + " high ram!"); 16712 } else { 16713 mNewNumAServiceProcs++; 16714 //Slog.i(TAG, "ADJ " + app + " not high ram!"); 16715 } 16716 } else { 16717 app.serviceHighRam = false; 16718 } 16719 } 16720 if (app.serviceb) { 16721 adj = ProcessList.SERVICE_B_ADJ; 16722 } 16723 } 16724 16725 app.curRawAdj = adj; 16726 16727 //Slog.i(TAG, "OOM ADJ " + app + ": pid=" + app.pid + 16728 // " adj=" + adj + " curAdj=" + app.curAdj + " maxAdj=" + app.maxAdj); 16729 if (adj > app.maxAdj) { 16730 adj = app.maxAdj; 16731 if (app.maxAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 16732 schedGroup = Process.THREAD_GROUP_DEFAULT; 16733 } 16734 } 16735 16736 // Do final modification to adj. Everything we do between here and applying 16737 // the final setAdj must be done in this function, because we will also use 16738 // it when computing the final cached adj later. Note that we don't need to 16739 // worry about this for max adj above, since max adj will always be used to 16740 // keep it out of the cached vaues. 16741 app.curAdj = app.modifyRawOomAdj(adj); 16742 app.curSchedGroup = schedGroup; 16743 app.curProcState = procState; 16744 app.foregroundActivities = foregroundActivities; 16745 16746 return app.curRawAdj; 16747 } 16748 16749 /** 16750 * Schedule PSS collection of a process. 16751 */ 16752 void requestPssLocked(ProcessRecord proc, int procState) { 16753 if (mPendingPssProcesses.contains(proc)) { 16754 return; 16755 } 16756 if (mPendingPssProcesses.size() == 0) { 16757 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 16758 } 16759 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of: " + proc); 16760 proc.pssProcState = procState; 16761 mPendingPssProcesses.add(proc); 16762 } 16763 16764 /** 16765 * Schedule PSS collection of all processes. 16766 */ 16767 void requestPssAllProcsLocked(long now, boolean always, boolean memLowered) { 16768 if (!always) { 16769 if (now < (mLastFullPssTime + 16770 (memLowered ? FULL_PSS_LOWERED_INTERVAL : FULL_PSS_MIN_INTERVAL))) { 16771 return; 16772 } 16773 } 16774 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of all procs! memLowered=" + memLowered); 16775 mLastFullPssTime = now; 16776 mFullPssPending = true; 16777 mPendingPssProcesses.ensureCapacity(mLruProcesses.size()); 16778 mPendingPssProcesses.clear(); 16779 for (int i=mLruProcesses.size()-1; i>=0; i--) { 16780 ProcessRecord app = mLruProcesses.get(i); 16781 if (memLowered || now > (app.lastStateTime+ProcessList.PSS_ALL_INTERVAL)) { 16782 app.pssProcState = app.setProcState; 16783 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 16784 isSleeping(), now); 16785 mPendingPssProcesses.add(app); 16786 } 16787 } 16788 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 16789 } 16790 16791 /** 16792 * Ask a given process to GC right now. 16793 */ 16794 final void performAppGcLocked(ProcessRecord app) { 16795 try { 16796 app.lastRequestedGc = SystemClock.uptimeMillis(); 16797 if (app.thread != null) { 16798 if (app.reportLowMemory) { 16799 app.reportLowMemory = false; 16800 app.thread.scheduleLowMemory(); 16801 } else { 16802 app.thread.processInBackground(); 16803 } 16804 } 16805 } catch (Exception e) { 16806 // whatever. 16807 } 16808 } 16809 16810 /** 16811 * Returns true if things are idle enough to perform GCs. 16812 */ 16813 private final boolean canGcNowLocked() { 16814 boolean processingBroadcasts = false; 16815 for (BroadcastQueue q : mBroadcastQueues) { 16816 if (q.mParallelBroadcasts.size() != 0 || q.mOrderedBroadcasts.size() != 0) { 16817 processingBroadcasts = true; 16818 } 16819 } 16820 return !processingBroadcasts 16821 && (isSleeping() || mStackSupervisor.allResumedActivitiesIdle()); 16822 } 16823 16824 /** 16825 * Perform GCs on all processes that are waiting for it, but only 16826 * if things are idle. 16827 */ 16828 final void performAppGcsLocked() { 16829 final int N = mProcessesToGc.size(); 16830 if (N <= 0) { 16831 return; 16832 } 16833 if (canGcNowLocked()) { 16834 while (mProcessesToGc.size() > 0) { 16835 ProcessRecord proc = mProcessesToGc.remove(0); 16836 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ || proc.reportLowMemory) { 16837 if ((proc.lastRequestedGc+GC_MIN_INTERVAL) 16838 <= SystemClock.uptimeMillis()) { 16839 // To avoid spamming the system, we will GC processes one 16840 // at a time, waiting a few seconds between each. 16841 performAppGcLocked(proc); 16842 scheduleAppGcsLocked(); 16843 return; 16844 } else { 16845 // It hasn't been long enough since we last GCed this 16846 // process... put it in the list to wait for its time. 16847 addProcessToGcListLocked(proc); 16848 break; 16849 } 16850 } 16851 } 16852 16853 scheduleAppGcsLocked(); 16854 } 16855 } 16856 16857 /** 16858 * If all looks good, perform GCs on all processes waiting for them. 16859 */ 16860 final void performAppGcsIfAppropriateLocked() { 16861 if (canGcNowLocked()) { 16862 performAppGcsLocked(); 16863 return; 16864 } 16865 // Still not idle, wait some more. 16866 scheduleAppGcsLocked(); 16867 } 16868 16869 /** 16870 * Schedule the execution of all pending app GCs. 16871 */ 16872 final void scheduleAppGcsLocked() { 16873 mHandler.removeMessages(GC_BACKGROUND_PROCESSES_MSG); 16874 16875 if (mProcessesToGc.size() > 0) { 16876 // Schedule a GC for the time to the next process. 16877 ProcessRecord proc = mProcessesToGc.get(0); 16878 Message msg = mHandler.obtainMessage(GC_BACKGROUND_PROCESSES_MSG); 16879 16880 long when = proc.lastRequestedGc + GC_MIN_INTERVAL; 16881 long now = SystemClock.uptimeMillis(); 16882 if (when < (now+GC_TIMEOUT)) { 16883 when = now + GC_TIMEOUT; 16884 } 16885 mHandler.sendMessageAtTime(msg, when); 16886 } 16887 } 16888 16889 /** 16890 * Add a process to the array of processes waiting to be GCed. Keeps the 16891 * list in sorted order by the last GC time. The process can't already be 16892 * on the list. 16893 */ 16894 final void addProcessToGcListLocked(ProcessRecord proc) { 16895 boolean added = false; 16896 for (int i=mProcessesToGc.size()-1; i>=0; i--) { 16897 if (mProcessesToGc.get(i).lastRequestedGc < 16898 proc.lastRequestedGc) { 16899 added = true; 16900 mProcessesToGc.add(i+1, proc); 16901 break; 16902 } 16903 } 16904 if (!added) { 16905 mProcessesToGc.add(0, proc); 16906 } 16907 } 16908 16909 /** 16910 * Set up to ask a process to GC itself. This will either do it 16911 * immediately, or put it on the list of processes to gc the next 16912 * time things are idle. 16913 */ 16914 final void scheduleAppGcLocked(ProcessRecord app) { 16915 long now = SystemClock.uptimeMillis(); 16916 if ((app.lastRequestedGc+GC_MIN_INTERVAL) > now) { 16917 return; 16918 } 16919 if (!mProcessesToGc.contains(app)) { 16920 addProcessToGcListLocked(app); 16921 scheduleAppGcsLocked(); 16922 } 16923 } 16924 16925 final void checkExcessivePowerUsageLocked(boolean doKills) { 16926 updateCpuStatsNow(); 16927 16928 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 16929 boolean doWakeKills = doKills; 16930 boolean doCpuKills = doKills; 16931 if (mLastPowerCheckRealtime == 0) { 16932 doWakeKills = false; 16933 } 16934 if (mLastPowerCheckUptime == 0) { 16935 doCpuKills = false; 16936 } 16937 if (stats.isScreenOn()) { 16938 doWakeKills = false; 16939 } 16940 final long curRealtime = SystemClock.elapsedRealtime(); 16941 final long realtimeSince = curRealtime - mLastPowerCheckRealtime; 16942 final long curUptime = SystemClock.uptimeMillis(); 16943 final long uptimeSince = curUptime - mLastPowerCheckUptime; 16944 mLastPowerCheckRealtime = curRealtime; 16945 mLastPowerCheckUptime = curUptime; 16946 if (realtimeSince < WAKE_LOCK_MIN_CHECK_DURATION) { 16947 doWakeKills = false; 16948 } 16949 if (uptimeSince < CPU_MIN_CHECK_DURATION) { 16950 doCpuKills = false; 16951 } 16952 int i = mLruProcesses.size(); 16953 while (i > 0) { 16954 i--; 16955 ProcessRecord app = mLruProcesses.get(i); 16956 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 16957 long wtime; 16958 synchronized (stats) { 16959 wtime = stats.getProcessWakeTime(app.info.uid, 16960 app.pid, curRealtime); 16961 } 16962 long wtimeUsed = wtime - app.lastWakeTime; 16963 long cputimeUsed = app.curCpuTime - app.lastCpuTime; 16964 if (DEBUG_POWER) { 16965 StringBuilder sb = new StringBuilder(128); 16966 sb.append("Wake for "); 16967 app.toShortString(sb); 16968 sb.append(": over "); 16969 TimeUtils.formatDuration(realtimeSince, sb); 16970 sb.append(" used "); 16971 TimeUtils.formatDuration(wtimeUsed, sb); 16972 sb.append(" ("); 16973 sb.append((wtimeUsed*100)/realtimeSince); 16974 sb.append("%)"); 16975 Slog.i(TAG, sb.toString()); 16976 sb.setLength(0); 16977 sb.append("CPU for "); 16978 app.toShortString(sb); 16979 sb.append(": over "); 16980 TimeUtils.formatDuration(uptimeSince, sb); 16981 sb.append(" used "); 16982 TimeUtils.formatDuration(cputimeUsed, sb); 16983 sb.append(" ("); 16984 sb.append((cputimeUsed*100)/uptimeSince); 16985 sb.append("%)"); 16986 Slog.i(TAG, sb.toString()); 16987 } 16988 // If a process has held a wake lock for more 16989 // than 50% of the time during this period, 16990 // that sounds bad. Kill! 16991 if (doWakeKills && realtimeSince > 0 16992 && ((wtimeUsed*100)/realtimeSince) >= 50) { 16993 synchronized (stats) { 16994 stats.reportExcessiveWakeLocked(app.info.uid, app.processName, 16995 realtimeSince, wtimeUsed); 16996 } 16997 app.kill("excessive wake held " + wtimeUsed + " during " + realtimeSince, true); 16998 app.baseProcessTracker.reportExcessiveWake(app.pkgList); 16999 } else if (doCpuKills && uptimeSince > 0 17000 && ((cputimeUsed*100)/uptimeSince) >= 25) { 17001 synchronized (stats) { 17002 stats.reportExcessiveCpuLocked(app.info.uid, app.processName, 17003 uptimeSince, cputimeUsed); 17004 } 17005 app.kill("excessive cpu " + cputimeUsed + " during " + uptimeSince, true); 17006 app.baseProcessTracker.reportExcessiveCpu(app.pkgList); 17007 } else { 17008 app.lastWakeTime = wtime; 17009 app.lastCpuTime = app.curCpuTime; 17010 } 17011 } 17012 } 17013 } 17014 17015 private final boolean applyOomAdjLocked(ProcessRecord app, 17016 ProcessRecord TOP_APP, boolean doingAll, long now) { 17017 boolean success = true; 17018 17019 if (app.curRawAdj != app.setRawAdj) { 17020 app.setRawAdj = app.curRawAdj; 17021 } 17022 17023 int changes = 0; 17024 17025 if (app.curAdj != app.setAdj) { 17026 ProcessList.setOomAdj(app.pid, app.info.uid, app.curAdj); 17027 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v( 17028 TAG, "Set " + app.pid + " " + app.processName + 17029 " adj " + app.curAdj + ": " + app.adjType); 17030 app.setAdj = app.curAdj; 17031 } 17032 17033 if (app.setSchedGroup != app.curSchedGroup) { 17034 app.setSchedGroup = app.curSchedGroup; 17035 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17036 "Setting process group of " + app.processName 17037 + " to " + app.curSchedGroup); 17038 if (app.waitingToKill != null && 17039 app.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 17040 app.kill(app.waitingToKill, true); 17041 success = false; 17042 } else { 17043 if (true) { 17044 long oldId = Binder.clearCallingIdentity(); 17045 try { 17046 Process.setProcessGroup(app.pid, app.curSchedGroup); 17047 } catch (Exception e) { 17048 Slog.w(TAG, "Failed setting process group of " + app.pid 17049 + " to " + app.curSchedGroup); 17050 e.printStackTrace(); 17051 } finally { 17052 Binder.restoreCallingIdentity(oldId); 17053 } 17054 } else { 17055 if (app.thread != null) { 17056 try { 17057 app.thread.setSchedulingGroup(app.curSchedGroup); 17058 } catch (RemoteException e) { 17059 } 17060 } 17061 } 17062 Process.setSwappiness(app.pid, 17063 app.curSchedGroup <= Process.THREAD_GROUP_BG_NONINTERACTIVE); 17064 } 17065 } 17066 if (app.repForegroundActivities != app.foregroundActivities) { 17067 app.repForegroundActivities = app.foregroundActivities; 17068 changes |= ProcessChangeItem.CHANGE_ACTIVITIES; 17069 } 17070 if (app.repProcState != app.curProcState) { 17071 app.repProcState = app.curProcState; 17072 changes |= ProcessChangeItem.CHANGE_PROCESS_STATE; 17073 if (app.thread != null) { 17074 try { 17075 if (false) { 17076 //RuntimeException h = new RuntimeException("here"); 17077 Slog.i(TAG, "Sending new process state " + app.repProcState 17078 + " to " + app /*, h*/); 17079 } 17080 app.thread.setProcessState(app.repProcState); 17081 } catch (RemoteException e) { 17082 } 17083 } 17084 } 17085 if (app.setProcState < 0 || ProcessList.procStatesDifferForMem(app.curProcState, 17086 app.setProcState)) { 17087 app.lastStateTime = now; 17088 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 17089 isSleeping(), now); 17090 if (DEBUG_PSS) Slog.d(TAG, "Process state change from " 17091 + ProcessList.makeProcStateString(app.setProcState) + " to " 17092 + ProcessList.makeProcStateString(app.curProcState) + " next pss in " 17093 + (app.nextPssTime-now) + ": " + app); 17094 } else { 17095 if (now > app.nextPssTime || (now > (app.lastPssTime+ProcessList.PSS_MAX_INTERVAL) 17096 && now > (app.lastStateTime+ProcessList.PSS_MIN_TIME_FROM_STATE_CHANGE))) { 17097 requestPssLocked(app, app.setProcState); 17098 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, false, 17099 isSleeping(), now); 17100 } else if (false && DEBUG_PSS) { 17101 Slog.d(TAG, "Not requesting PSS of " + app + ": next=" + (app.nextPssTime-now)); 17102 } 17103 } 17104 if (app.setProcState != app.curProcState) { 17105 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17106 "Proc state change of " + app.processName 17107 + " to " + app.curProcState); 17108 boolean setImportant = app.setProcState < ActivityManager.PROCESS_STATE_SERVICE; 17109 boolean curImportant = app.curProcState < ActivityManager.PROCESS_STATE_SERVICE; 17110 if (setImportant && !curImportant) { 17111 // This app is no longer something we consider important enough to allow to 17112 // use arbitrary amounts of battery power. Note 17113 // its current wake lock time to later know to kill it if 17114 // it is not behaving well. 17115 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 17116 synchronized (stats) { 17117 app.lastWakeTime = stats.getProcessWakeTime(app.info.uid, 17118 app.pid, SystemClock.elapsedRealtime()); 17119 } 17120 app.lastCpuTime = app.curCpuTime; 17121 17122 } 17123 app.setProcState = app.curProcState; 17124 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 17125 app.notCachedSinceIdle = false; 17126 } 17127 if (!doingAll) { 17128 setProcessTrackerStateLocked(app, mProcessStats.getMemFactorLocked(), now); 17129 } else { 17130 app.procStateChanged = true; 17131 } 17132 } 17133 17134 if (changes != 0) { 17135 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Changes in " + app + ": " + changes); 17136 int i = mPendingProcessChanges.size()-1; 17137 ProcessChangeItem item = null; 17138 while (i >= 0) { 17139 item = mPendingProcessChanges.get(i); 17140 if (item.pid == app.pid) { 17141 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Re-using existing item: " + item); 17142 break; 17143 } 17144 i--; 17145 } 17146 if (i < 0) { 17147 // No existing item in pending changes; need a new one. 17148 final int NA = mAvailProcessChanges.size(); 17149 if (NA > 0) { 17150 item = mAvailProcessChanges.remove(NA-1); 17151 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Retreiving available item: " + item); 17152 } else { 17153 item = new ProcessChangeItem(); 17154 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Allocating new item: " + item); 17155 } 17156 item.changes = 0; 17157 item.pid = app.pid; 17158 item.uid = app.info.uid; 17159 if (mPendingProcessChanges.size() == 0) { 17160 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, 17161 "*** Enqueueing dispatch processes changed!"); 17162 mHandler.obtainMessage(DISPATCH_PROCESSES_CHANGED).sendToTarget(); 17163 } 17164 mPendingProcessChanges.add(item); 17165 } 17166 item.changes |= changes; 17167 item.processState = app.repProcState; 17168 item.foregroundActivities = app.repForegroundActivities; 17169 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Item " 17170 + Integer.toHexString(System.identityHashCode(item)) 17171 + " " + app.toShortString() + ": changes=" + item.changes 17172 + " procState=" + item.processState 17173 + " foreground=" + item.foregroundActivities 17174 + " type=" + app.adjType + " source=" + app.adjSource 17175 + " target=" + app.adjTarget); 17176 } 17177 17178 return success; 17179 } 17180 17181 private final void setProcessTrackerStateLocked(ProcessRecord proc, int memFactor, long now) { 17182 if (proc.thread != null) { 17183 if (proc.baseProcessTracker != null) { 17184 proc.baseProcessTracker.setState(proc.repProcState, memFactor, now, proc.pkgList); 17185 } 17186 if (proc.repProcState >= 0) { 17187 mBatteryStatsService.noteProcessState(proc.processName, proc.info.uid, 17188 proc.repProcState); 17189 } 17190 } 17191 } 17192 17193 private final boolean updateOomAdjLocked(ProcessRecord app, int cachedAdj, 17194 ProcessRecord TOP_APP, boolean doingAll, long now) { 17195 if (app.thread == null) { 17196 return false; 17197 } 17198 17199 computeOomAdjLocked(app, cachedAdj, TOP_APP, doingAll, now); 17200 17201 return applyOomAdjLocked(app, TOP_APP, doingAll, now); 17202 } 17203 17204 final void updateProcessForegroundLocked(ProcessRecord proc, boolean isForeground, 17205 boolean oomAdj) { 17206 if (isForeground != proc.foregroundServices) { 17207 proc.foregroundServices = isForeground; 17208 ArrayList<ProcessRecord> curProcs = mForegroundPackages.get(proc.info.packageName, 17209 proc.info.uid); 17210 if (isForeground) { 17211 if (curProcs == null) { 17212 curProcs = new ArrayList<ProcessRecord>(); 17213 mForegroundPackages.put(proc.info.packageName, proc.info.uid, curProcs); 17214 } 17215 if (!curProcs.contains(proc)) { 17216 curProcs.add(proc); 17217 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_FOREGROUND_START, 17218 proc.info.packageName, proc.info.uid); 17219 } 17220 } else { 17221 if (curProcs != null) { 17222 if (curProcs.remove(proc)) { 17223 mBatteryStatsService.noteEvent( 17224 BatteryStats.HistoryItem.EVENT_FOREGROUND_FINISH, 17225 proc.info.packageName, proc.info.uid); 17226 if (curProcs.size() <= 0) { 17227 mForegroundPackages.remove(proc.info.packageName, proc.info.uid); 17228 } 17229 } 17230 } 17231 } 17232 if (oomAdj) { 17233 updateOomAdjLocked(); 17234 } 17235 } 17236 } 17237 17238 private final ActivityRecord resumedAppLocked() { 17239 ActivityRecord act = mStackSupervisor.resumedAppLocked(); 17240 String pkg; 17241 int uid; 17242 if (act != null) { 17243 pkg = act.packageName; 17244 uid = act.info.applicationInfo.uid; 17245 } else { 17246 pkg = null; 17247 uid = -1; 17248 } 17249 // Has the UID or resumed package name changed? 17250 if (uid != mCurResumedUid || (pkg != mCurResumedPackage 17251 && (pkg == null || !pkg.equals(mCurResumedPackage)))) { 17252 if (mCurResumedPackage != null) { 17253 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_FINISH, 17254 mCurResumedPackage, mCurResumedUid); 17255 } 17256 mCurResumedPackage = pkg; 17257 mCurResumedUid = uid; 17258 if (mCurResumedPackage != null) { 17259 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_START, 17260 mCurResumedPackage, mCurResumedUid); 17261 } 17262 } 17263 return act; 17264 } 17265 17266 final boolean updateOomAdjLocked(ProcessRecord app) { 17267 final ActivityRecord TOP_ACT = resumedAppLocked(); 17268 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 17269 final boolean wasCached = app.cached; 17270 17271 mAdjSeq++; 17272 17273 // This is the desired cached adjusment we want to tell it to use. 17274 // If our app is currently cached, we know it, and that is it. Otherwise, 17275 // we don't know it yet, and it needs to now be cached we will then 17276 // need to do a complete oom adj. 17277 final int cachedAdj = app.curRawAdj >= ProcessList.CACHED_APP_MIN_ADJ 17278 ? app.curRawAdj : ProcessList.UNKNOWN_ADJ; 17279 boolean success = updateOomAdjLocked(app, cachedAdj, TOP_APP, false, 17280 SystemClock.uptimeMillis()); 17281 if (wasCached != app.cached || app.curRawAdj == ProcessList.UNKNOWN_ADJ) { 17282 // Changed to/from cached state, so apps after it in the LRU 17283 // list may also be changed. 17284 updateOomAdjLocked(); 17285 } 17286 return success; 17287 } 17288 17289 final void updateOomAdjLocked() { 17290 final ActivityRecord TOP_ACT = resumedAppLocked(); 17291 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 17292 final long now = SystemClock.uptimeMillis(); 17293 final long oldTime = now - ProcessList.MAX_EMPTY_TIME; 17294 final int N = mLruProcesses.size(); 17295 17296 if (false) { 17297 RuntimeException e = new RuntimeException(); 17298 e.fillInStackTrace(); 17299 Slog.i(TAG, "updateOomAdj: top=" + TOP_ACT, e); 17300 } 17301 17302 mAdjSeq++; 17303 mNewNumServiceProcs = 0; 17304 mNewNumAServiceProcs = 0; 17305 17306 final int emptyProcessLimit; 17307 final int cachedProcessLimit; 17308 if (mProcessLimit <= 0) { 17309 emptyProcessLimit = cachedProcessLimit = 0; 17310 } else if (mProcessLimit == 1) { 17311 emptyProcessLimit = 1; 17312 cachedProcessLimit = 0; 17313 } else { 17314 emptyProcessLimit = ProcessList.computeEmptyProcessLimit(mProcessLimit); 17315 cachedProcessLimit = mProcessLimit - emptyProcessLimit; 17316 } 17317 17318 // Let's determine how many processes we have running vs. 17319 // how many slots we have for background processes; we may want 17320 // to put multiple processes in a slot of there are enough of 17321 // them. 17322 int numSlots = (ProcessList.CACHED_APP_MAX_ADJ 17323 - ProcessList.CACHED_APP_MIN_ADJ + 1) / 2; 17324 int numEmptyProcs = N - mNumNonCachedProcs - mNumCachedHiddenProcs; 17325 if (numEmptyProcs > cachedProcessLimit) { 17326 // If there are more empty processes than our limit on cached 17327 // processes, then use the cached process limit for the factor. 17328 // This ensures that the really old empty processes get pushed 17329 // down to the bottom, so if we are running low on memory we will 17330 // have a better chance at keeping around more cached processes 17331 // instead of a gazillion empty processes. 17332 numEmptyProcs = cachedProcessLimit; 17333 } 17334 int emptyFactor = numEmptyProcs/numSlots; 17335 if (emptyFactor < 1) emptyFactor = 1; 17336 int cachedFactor = (mNumCachedHiddenProcs > 0 ? mNumCachedHiddenProcs : 1)/numSlots; 17337 if (cachedFactor < 1) cachedFactor = 1; 17338 int stepCached = 0; 17339 int stepEmpty = 0; 17340 int numCached = 0; 17341 int numEmpty = 0; 17342 int numTrimming = 0; 17343 17344 mNumNonCachedProcs = 0; 17345 mNumCachedHiddenProcs = 0; 17346 17347 // First update the OOM adjustment for each of the 17348 // application processes based on their current state. 17349 int curCachedAdj = ProcessList.CACHED_APP_MIN_ADJ; 17350 int nextCachedAdj = curCachedAdj+1; 17351 int curEmptyAdj = ProcessList.CACHED_APP_MIN_ADJ; 17352 int nextEmptyAdj = curEmptyAdj+2; 17353 for (int i=N-1; i>=0; i--) { 17354 ProcessRecord app = mLruProcesses.get(i); 17355 if (!app.killedByAm && app.thread != null) { 17356 app.procStateChanged = false; 17357 computeOomAdjLocked(app, ProcessList.UNKNOWN_ADJ, TOP_APP, true, now); 17358 17359 // If we haven't yet assigned the final cached adj 17360 // to the process, do that now. 17361 if (app.curAdj >= ProcessList.UNKNOWN_ADJ) { 17362 switch (app.curProcState) { 17363 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 17364 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 17365 // This process is a cached process holding activities... 17366 // assign it the next cached value for that type, and then 17367 // step that cached level. 17368 app.curRawAdj = curCachedAdj; 17369 app.curAdj = app.modifyRawOomAdj(curCachedAdj); 17370 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning activity LRU #" + i 17371 + " adj: " + app.curAdj + " (curCachedAdj=" + curCachedAdj 17372 + ")"); 17373 if (curCachedAdj != nextCachedAdj) { 17374 stepCached++; 17375 if (stepCached >= cachedFactor) { 17376 stepCached = 0; 17377 curCachedAdj = nextCachedAdj; 17378 nextCachedAdj += 2; 17379 if (nextCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) { 17380 nextCachedAdj = ProcessList.CACHED_APP_MAX_ADJ; 17381 } 17382 } 17383 } 17384 break; 17385 default: 17386 // For everything else, assign next empty cached process 17387 // level and bump that up. Note that this means that 17388 // long-running services that have dropped down to the 17389 // cached level will be treated as empty (since their process 17390 // state is still as a service), which is what we want. 17391 app.curRawAdj = curEmptyAdj; 17392 app.curAdj = app.modifyRawOomAdj(curEmptyAdj); 17393 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning empty LRU #" + i 17394 + " adj: " + app.curAdj + " (curEmptyAdj=" + curEmptyAdj 17395 + ")"); 17396 if (curEmptyAdj != nextEmptyAdj) { 17397 stepEmpty++; 17398 if (stepEmpty >= emptyFactor) { 17399 stepEmpty = 0; 17400 curEmptyAdj = nextEmptyAdj; 17401 nextEmptyAdj += 2; 17402 if (nextEmptyAdj > ProcessList.CACHED_APP_MAX_ADJ) { 17403 nextEmptyAdj = ProcessList.CACHED_APP_MAX_ADJ; 17404 } 17405 } 17406 } 17407 break; 17408 } 17409 } 17410 17411 applyOomAdjLocked(app, TOP_APP, true, now); 17412 17413 // Count the number of process types. 17414 switch (app.curProcState) { 17415 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 17416 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 17417 mNumCachedHiddenProcs++; 17418 numCached++; 17419 if (numCached > cachedProcessLimit) { 17420 app.kill("cached #" + numCached, true); 17421 } 17422 break; 17423 case ActivityManager.PROCESS_STATE_CACHED_EMPTY: 17424 if (numEmpty > ProcessList.TRIM_EMPTY_APPS 17425 && app.lastActivityTime < oldTime) { 17426 app.kill("empty for " 17427 + ((oldTime + ProcessList.MAX_EMPTY_TIME - app.lastActivityTime) 17428 / 1000) + "s", true); 17429 } else { 17430 numEmpty++; 17431 if (numEmpty > emptyProcessLimit) { 17432 app.kill("empty #" + numEmpty, true); 17433 } 17434 } 17435 break; 17436 default: 17437 mNumNonCachedProcs++; 17438 break; 17439 } 17440 17441 if (app.isolated && app.services.size() <= 0) { 17442 // If this is an isolated process, and there are no 17443 // services running in it, then the process is no longer 17444 // needed. We agressively kill these because we can by 17445 // definition not re-use the same process again, and it is 17446 // good to avoid having whatever code was running in them 17447 // left sitting around after no longer needed. 17448 app.kill("isolated not needed", true); 17449 } 17450 17451 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 17452 && !app.killedByAm) { 17453 numTrimming++; 17454 } 17455 } 17456 } 17457 17458 mNumServiceProcs = mNewNumServiceProcs; 17459 17460 // Now determine the memory trimming level of background processes. 17461 // Unfortunately we need to start at the back of the list to do this 17462 // properly. We only do this if the number of background apps we 17463 // are managing to keep around is less than half the maximum we desire; 17464 // if we are keeping a good number around, we'll let them use whatever 17465 // memory they want. 17466 final int numCachedAndEmpty = numCached + numEmpty; 17467 int memFactor; 17468 if (numCached <= ProcessList.TRIM_CACHED_APPS 17469 && numEmpty <= ProcessList.TRIM_EMPTY_APPS) { 17470 if (numCachedAndEmpty <= ProcessList.TRIM_CRITICAL_THRESHOLD) { 17471 memFactor = ProcessStats.ADJ_MEM_FACTOR_CRITICAL; 17472 } else if (numCachedAndEmpty <= ProcessList.TRIM_LOW_THRESHOLD) { 17473 memFactor = ProcessStats.ADJ_MEM_FACTOR_LOW; 17474 } else { 17475 memFactor = ProcessStats.ADJ_MEM_FACTOR_MODERATE; 17476 } 17477 } else { 17478 memFactor = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 17479 } 17480 // We always allow the memory level to go up (better). We only allow it to go 17481 // down if we are in a state where that is allowed, *and* the total number of processes 17482 // has gone down since last time. 17483 if (DEBUG_OOM_ADJ) Slog.d(TAG, "oom: memFactor=" + memFactor + " last=" + mLastMemoryLevel 17484 + " allowLow=" + mAllowLowerMemLevel + " numProcs=" + mLruProcesses.size() 17485 + " last=" + mLastNumProcesses); 17486 if (memFactor > mLastMemoryLevel) { 17487 if (!mAllowLowerMemLevel || mLruProcesses.size() >= mLastNumProcesses) { 17488 memFactor = mLastMemoryLevel; 17489 if (DEBUG_OOM_ADJ) Slog.d(TAG, "Keeping last mem factor!"); 17490 } 17491 } 17492 mLastMemoryLevel = memFactor; 17493 mLastNumProcesses = mLruProcesses.size(); 17494 boolean allChanged = mProcessStats.setMemFactorLocked(memFactor, !isSleeping(), now); 17495 final int trackerMemFactor = mProcessStats.getMemFactorLocked(); 17496 if (memFactor != ProcessStats.ADJ_MEM_FACTOR_NORMAL) { 17497 if (mLowRamStartTime == 0) { 17498 mLowRamStartTime = now; 17499 } 17500 int step = 0; 17501 int fgTrimLevel; 17502 switch (memFactor) { 17503 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 17504 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_CRITICAL; 17505 break; 17506 case ProcessStats.ADJ_MEM_FACTOR_LOW: 17507 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_LOW; 17508 break; 17509 default: 17510 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_MODERATE; 17511 break; 17512 } 17513 int factor = numTrimming/3; 17514 int minFactor = 2; 17515 if (mHomeProcess != null) minFactor++; 17516 if (mPreviousProcess != null) minFactor++; 17517 if (factor < minFactor) factor = minFactor; 17518 int curLevel = ComponentCallbacks2.TRIM_MEMORY_COMPLETE; 17519 for (int i=N-1; i>=0; i--) { 17520 ProcessRecord app = mLruProcesses.get(i); 17521 if (allChanged || app.procStateChanged) { 17522 setProcessTrackerStateLocked(app, trackerMemFactor, now); 17523 app.procStateChanged = false; 17524 } 17525 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 17526 && !app.killedByAm) { 17527 if (app.trimMemoryLevel < curLevel && app.thread != null) { 17528 try { 17529 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17530 "Trimming memory of " + app.processName 17531 + " to " + curLevel); 17532 app.thread.scheduleTrimMemory(curLevel); 17533 } catch (RemoteException e) { 17534 } 17535 if (false) { 17536 // For now we won't do this; our memory trimming seems 17537 // to be good enough at this point that destroying 17538 // activities causes more harm than good. 17539 if (curLevel >= ComponentCallbacks2.TRIM_MEMORY_COMPLETE 17540 && app != mHomeProcess && app != mPreviousProcess) { 17541 // Need to do this on its own message because the stack may not 17542 // be in a consistent state at this point. 17543 // For these apps we will also finish their activities 17544 // to help them free memory. 17545 mStackSupervisor.scheduleDestroyAllActivities(app, "trim"); 17546 } 17547 } 17548 } 17549 app.trimMemoryLevel = curLevel; 17550 step++; 17551 if (step >= factor) { 17552 step = 0; 17553 switch (curLevel) { 17554 case ComponentCallbacks2.TRIM_MEMORY_COMPLETE: 17555 curLevel = ComponentCallbacks2.TRIM_MEMORY_MODERATE; 17556 break; 17557 case ComponentCallbacks2.TRIM_MEMORY_MODERATE: 17558 curLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 17559 break; 17560 } 17561 } 17562 } else if (app.curProcState == ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 17563 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_BACKGROUND 17564 && app.thread != null) { 17565 try { 17566 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17567 "Trimming memory of heavy-weight " + app.processName 17568 + " to " + ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 17569 app.thread.scheduleTrimMemory( 17570 ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 17571 } catch (RemoteException e) { 17572 } 17573 } 17574 app.trimMemoryLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 17575 } else { 17576 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 17577 || app.systemNoUi) && app.pendingUiClean) { 17578 // If this application is now in the background and it 17579 // had done UI, then give it the special trim level to 17580 // have it free UI resources. 17581 final int level = ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN; 17582 if (app.trimMemoryLevel < level && app.thread != null) { 17583 try { 17584 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17585 "Trimming memory of bg-ui " + app.processName 17586 + " to " + level); 17587 app.thread.scheduleTrimMemory(level); 17588 } catch (RemoteException e) { 17589 } 17590 } 17591 app.pendingUiClean = false; 17592 } 17593 if (app.trimMemoryLevel < fgTrimLevel && app.thread != null) { 17594 try { 17595 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17596 "Trimming memory of fg " + app.processName 17597 + " to " + fgTrimLevel); 17598 app.thread.scheduleTrimMemory(fgTrimLevel); 17599 } catch (RemoteException e) { 17600 } 17601 } 17602 app.trimMemoryLevel = fgTrimLevel; 17603 } 17604 } 17605 } else { 17606 if (mLowRamStartTime != 0) { 17607 mLowRamTimeSinceLastIdle += now - mLowRamStartTime; 17608 mLowRamStartTime = 0; 17609 } 17610 for (int i=N-1; i>=0; i--) { 17611 ProcessRecord app = mLruProcesses.get(i); 17612 if (allChanged || app.procStateChanged) { 17613 setProcessTrackerStateLocked(app, trackerMemFactor, now); 17614 app.procStateChanged = false; 17615 } 17616 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 17617 || app.systemNoUi) && app.pendingUiClean) { 17618 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN 17619 && app.thread != null) { 17620 try { 17621 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 17622 "Trimming memory of ui hidden " + app.processName 17623 + " to " + ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 17624 app.thread.scheduleTrimMemory( 17625 ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 17626 } catch (RemoteException e) { 17627 } 17628 } 17629 app.pendingUiClean = false; 17630 } 17631 app.trimMemoryLevel = 0; 17632 } 17633 } 17634 17635 if (mAlwaysFinishActivities) { 17636 // Need to do this on its own message because the stack may not 17637 // be in a consistent state at this point. 17638 mStackSupervisor.scheduleDestroyAllActivities(null, "always-finish"); 17639 } 17640 17641 if (allChanged) { 17642 requestPssAllProcsLocked(now, false, mProcessStats.isMemFactorLowered()); 17643 } 17644 17645 if (mProcessStats.shouldWriteNowLocked(now)) { 17646 mHandler.post(new Runnable() { 17647 @Override public void run() { 17648 synchronized (ActivityManagerService.this) { 17649 mProcessStats.writeStateAsyncLocked(); 17650 } 17651 } 17652 }); 17653 } 17654 17655 if (DEBUG_OOM_ADJ) { 17656 Slog.d(TAG, "Did OOM ADJ in " + (SystemClock.uptimeMillis()-now) + "ms"); 17657 } 17658 } 17659 17660 final void trimApplications() { 17661 synchronized (this) { 17662 int i; 17663 17664 // First remove any unused application processes whose package 17665 // has been removed. 17666 for (i=mRemovedProcesses.size()-1; i>=0; i--) { 17667 final ProcessRecord app = mRemovedProcesses.get(i); 17668 if (app.activities.size() == 0 17669 && app.curReceiver == null && app.services.size() == 0) { 17670 Slog.i( 17671 TAG, "Exiting empty application process " 17672 + app.processName + " (" 17673 + (app.thread != null ? app.thread.asBinder() : null) 17674 + ")\n"); 17675 if (app.pid > 0 && app.pid != MY_PID) { 17676 app.kill("empty", false); 17677 } else { 17678 try { 17679 app.thread.scheduleExit(); 17680 } catch (Exception e) { 17681 // Ignore exceptions. 17682 } 17683 } 17684 cleanUpApplicationRecordLocked(app, false, true, -1); 17685 mRemovedProcesses.remove(i); 17686 17687 if (app.persistent) { 17688 addAppLocked(app.info, false, null /* ABI override */); 17689 } 17690 } 17691 } 17692 17693 // Now update the oom adj for all processes. 17694 updateOomAdjLocked(); 17695 } 17696 } 17697 17698 /** This method sends the specified signal to each of the persistent apps */ 17699 public void signalPersistentProcesses(int sig) throws RemoteException { 17700 if (sig != Process.SIGNAL_USR1) { 17701 throw new SecurityException("Only SIGNAL_USR1 is allowed"); 17702 } 17703 17704 synchronized (this) { 17705 if (checkCallingPermission(android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES) 17706 != PackageManager.PERMISSION_GRANTED) { 17707 throw new SecurityException("Requires permission " 17708 + android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES); 17709 } 17710 17711 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 17712 ProcessRecord r = mLruProcesses.get(i); 17713 if (r.thread != null && r.persistent) { 17714 Process.sendSignal(r.pid, sig); 17715 } 17716 } 17717 } 17718 } 17719 17720 private void stopProfilerLocked(ProcessRecord proc, int profileType) { 17721 if (proc == null || proc == mProfileProc) { 17722 proc = mProfileProc; 17723 profileType = mProfileType; 17724 clearProfilerLocked(); 17725 } 17726 if (proc == null) { 17727 return; 17728 } 17729 try { 17730 proc.thread.profilerControl(false, null, profileType); 17731 } catch (RemoteException e) { 17732 throw new IllegalStateException("Process disappeared"); 17733 } 17734 } 17735 17736 private void clearProfilerLocked() { 17737 if (mProfileFd != null) { 17738 try { 17739 mProfileFd.close(); 17740 } catch (IOException e) { 17741 } 17742 } 17743 mProfileApp = null; 17744 mProfileProc = null; 17745 mProfileFile = null; 17746 mProfileType = 0; 17747 mAutoStopProfiler = false; 17748 mSamplingInterval = 0; 17749 } 17750 17751 public boolean profileControl(String process, int userId, boolean start, 17752 ProfilerInfo profilerInfo, int profileType) throws RemoteException { 17753 17754 try { 17755 synchronized (this) { 17756 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 17757 // its own permission. 17758 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 17759 != PackageManager.PERMISSION_GRANTED) { 17760 throw new SecurityException("Requires permission " 17761 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 17762 } 17763 17764 if (start && (profilerInfo == null || profilerInfo.profileFd == null)) { 17765 throw new IllegalArgumentException("null profile info or fd"); 17766 } 17767 17768 ProcessRecord proc = null; 17769 if (process != null) { 17770 proc = findProcessLocked(process, userId, "profileControl"); 17771 } 17772 17773 if (start && (proc == null || proc.thread == null)) { 17774 throw new IllegalArgumentException("Unknown process: " + process); 17775 } 17776 17777 if (start) { 17778 stopProfilerLocked(null, 0); 17779 setProfileApp(proc.info, proc.processName, profilerInfo); 17780 mProfileProc = proc; 17781 mProfileType = profileType; 17782 ParcelFileDescriptor fd = profilerInfo.profileFd; 17783 try { 17784 fd = fd.dup(); 17785 } catch (IOException e) { 17786 fd = null; 17787 } 17788 profilerInfo.profileFd = fd; 17789 proc.thread.profilerControl(start, profilerInfo, profileType); 17790 fd = null; 17791 mProfileFd = null; 17792 } else { 17793 stopProfilerLocked(proc, profileType); 17794 if (profilerInfo != null && profilerInfo.profileFd != null) { 17795 try { 17796 profilerInfo.profileFd.close(); 17797 } catch (IOException e) { 17798 } 17799 } 17800 } 17801 17802 return true; 17803 } 17804 } catch (RemoteException e) { 17805 throw new IllegalStateException("Process disappeared"); 17806 } finally { 17807 if (profilerInfo != null && profilerInfo.profileFd != null) { 17808 try { 17809 profilerInfo.profileFd.close(); 17810 } catch (IOException e) { 17811 } 17812 } 17813 } 17814 } 17815 17816 private ProcessRecord findProcessLocked(String process, int userId, String callName) { 17817 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 17818 userId, true, ALLOW_FULL_ONLY, callName, null); 17819 ProcessRecord proc = null; 17820 try { 17821 int pid = Integer.parseInt(process); 17822 synchronized (mPidsSelfLocked) { 17823 proc = mPidsSelfLocked.get(pid); 17824 } 17825 } catch (NumberFormatException e) { 17826 } 17827 17828 if (proc == null) { 17829 ArrayMap<String, SparseArray<ProcessRecord>> all 17830 = mProcessNames.getMap(); 17831 SparseArray<ProcessRecord> procs = all.get(process); 17832 if (procs != null && procs.size() > 0) { 17833 proc = procs.valueAt(0); 17834 if (userId != UserHandle.USER_ALL && proc.userId != userId) { 17835 for (int i=1; i<procs.size(); i++) { 17836 ProcessRecord thisProc = procs.valueAt(i); 17837 if (thisProc.userId == userId) { 17838 proc = thisProc; 17839 break; 17840 } 17841 } 17842 } 17843 } 17844 } 17845 17846 return proc; 17847 } 17848 17849 public boolean dumpHeap(String process, int userId, boolean managed, 17850 String path, ParcelFileDescriptor fd) throws RemoteException { 17851 17852 try { 17853 synchronized (this) { 17854 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 17855 // its own permission (same as profileControl). 17856 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 17857 != PackageManager.PERMISSION_GRANTED) { 17858 throw new SecurityException("Requires permission " 17859 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 17860 } 17861 17862 if (fd == null) { 17863 throw new IllegalArgumentException("null fd"); 17864 } 17865 17866 ProcessRecord proc = findProcessLocked(process, userId, "dumpHeap"); 17867 if (proc == null || proc.thread == null) { 17868 throw new IllegalArgumentException("Unknown process: " + process); 17869 } 17870 17871 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 17872 if (!isDebuggable) { 17873 if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 17874 throw new SecurityException("Process not debuggable: " + proc); 17875 } 17876 } 17877 17878 proc.thread.dumpHeap(managed, path, fd); 17879 fd = null; 17880 return true; 17881 } 17882 } catch (RemoteException e) { 17883 throw new IllegalStateException("Process disappeared"); 17884 } finally { 17885 if (fd != null) { 17886 try { 17887 fd.close(); 17888 } catch (IOException e) { 17889 } 17890 } 17891 } 17892 } 17893 17894 /** In this method we try to acquire our lock to make sure that we have not deadlocked */ 17895 public void monitor() { 17896 synchronized (this) { } 17897 } 17898 17899 void onCoreSettingsChange(Bundle settings) { 17900 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 17901 ProcessRecord processRecord = mLruProcesses.get(i); 17902 try { 17903 if (processRecord.thread != null) { 17904 processRecord.thread.setCoreSettings(settings); 17905 } 17906 } catch (RemoteException re) { 17907 /* ignore */ 17908 } 17909 } 17910 } 17911 17912 // Multi-user methods 17913 17914 /** 17915 * Start user, if its not already running, but don't bring it to foreground. 17916 */ 17917 @Override 17918 public boolean startUserInBackground(final int userId) { 17919 return startUser(userId, /* foreground */ false); 17920 } 17921 17922 /** 17923 * Start user, if its not already running, and bring it to foreground. 17924 */ 17925 boolean startUserInForeground(final int userId, Dialog dlg) { 17926 boolean result = startUser(userId, /* foreground */ true); 17927 dlg.dismiss(); 17928 return result; 17929 } 17930 17931 /** 17932 * Refreshes the list of users related to the current user when either a 17933 * user switch happens or when a new related user is started in the 17934 * background. 17935 */ 17936 private void updateCurrentProfileIdsLocked() { 17937 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17938 mCurrentUserId, false /* enabledOnly */); 17939 int[] currentProfileIds = new int[profiles.size()]; // profiles will not be null 17940 for (int i = 0; i < currentProfileIds.length; i++) { 17941 currentProfileIds[i] = profiles.get(i).id; 17942 } 17943 mCurrentProfileIds = currentProfileIds; 17944 17945 synchronized (mUserProfileGroupIdsSelfLocked) { 17946 mUserProfileGroupIdsSelfLocked.clear(); 17947 final List<UserInfo> users = getUserManagerLocked().getUsers(false); 17948 for (int i = 0; i < users.size(); i++) { 17949 UserInfo user = users.get(i); 17950 if (user.profileGroupId != UserInfo.NO_PROFILE_GROUP_ID) { 17951 mUserProfileGroupIdsSelfLocked.put(user.id, user.profileGroupId); 17952 } 17953 } 17954 } 17955 } 17956 17957 private Set getProfileIdsLocked(int userId) { 17958 Set userIds = new HashSet<Integer>(); 17959 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17960 userId, false /* enabledOnly */); 17961 for (UserInfo user : profiles) { 17962 userIds.add(Integer.valueOf(user.id)); 17963 } 17964 return userIds; 17965 } 17966 17967 @Override 17968 public boolean switchUser(final int userId) { 17969 String userName; 17970 synchronized (this) { 17971 UserInfo userInfo = getUserManagerLocked().getUserInfo(userId); 17972 if (userInfo == null) { 17973 Slog.w(TAG, "No user info for user #" + userId); 17974 return false; 17975 } 17976 if (userInfo.isManagedProfile()) { 17977 Slog.w(TAG, "Cannot switch to User #" + userId + ": not a full user"); 17978 return false; 17979 } 17980 userName = userInfo.name; 17981 mTargetUserId = userId; 17982 } 17983 mHandler.removeMessages(START_USER_SWITCH_MSG); 17984 mHandler.sendMessage(mHandler.obtainMessage(START_USER_SWITCH_MSG, userId, 0, userName)); 17985 return true; 17986 } 17987 17988 private void showUserSwitchDialog(int userId, String userName) { 17989 // The dialog will show and then initiate the user switch by calling startUserInForeground 17990 Dialog d = new UserSwitchingDialog(this, mContext, userId, userName, 17991 true /* above system */); 17992 d.show(); 17993 } 17994 17995 private boolean startUser(final int userId, final boolean foreground) { 17996 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17997 != PackageManager.PERMISSION_GRANTED) { 17998 String msg = "Permission Denial: switchUser() from pid=" 17999 + Binder.getCallingPid() 18000 + ", uid=" + Binder.getCallingUid() 18001 + " requires " + INTERACT_ACROSS_USERS_FULL; 18002 Slog.w(TAG, msg); 18003 throw new SecurityException(msg); 18004 } 18005 18006 if (DEBUG_MU) Slog.i(TAG_MU, "starting userid:" + userId + " fore:" + foreground); 18007 18008 final long ident = Binder.clearCallingIdentity(); 18009 try { 18010 synchronized (this) { 18011 final int oldUserId = mCurrentUserId; 18012 if (oldUserId == userId) { 18013 return true; 18014 } 18015 18016 mStackSupervisor.setLockTaskModeLocked(null, false); 18017 18018 final UserInfo userInfo = getUserManagerLocked().getUserInfo(userId); 18019 if (userInfo == null) { 18020 Slog.w(TAG, "No user info for user #" + userId); 18021 return false; 18022 } 18023 if (foreground && userInfo.isManagedProfile()) { 18024 Slog.w(TAG, "Cannot switch to User #" + userId + ": not a full user"); 18025 return false; 18026 } 18027 18028 if (foreground) { 18029 mWindowManager.startFreezingScreen(R.anim.screen_user_exit, 18030 R.anim.screen_user_enter); 18031 } 18032 18033 boolean needStart = false; 18034 18035 // If the user we are switching to is not currently started, then 18036 // we need to start it now. 18037 if (mStartedUsers.get(userId) == null) { 18038 mStartedUsers.put(userId, new UserStartedState(new UserHandle(userId), false)); 18039 updateStartedUserArrayLocked(); 18040 needStart = true; 18041 } 18042 18043 final Integer userIdInt = Integer.valueOf(userId); 18044 mUserLru.remove(userIdInt); 18045 mUserLru.add(userIdInt); 18046 18047 if (foreground) { 18048 mCurrentUserId = userId; 18049 mTargetUserId = UserHandle.USER_NULL; // reset, mCurrentUserId has caught up 18050 updateCurrentProfileIdsLocked(); 18051 mWindowManager.setCurrentUser(userId, mCurrentProfileIds); 18052 // Once the internal notion of the active user has switched, we lock the device 18053 // with the option to show the user switcher on the keyguard. 18054 mWindowManager.lockNow(null); 18055 } else { 18056 final Integer currentUserIdInt = Integer.valueOf(mCurrentUserId); 18057 updateCurrentProfileIdsLocked(); 18058 mWindowManager.setCurrentProfileIds(mCurrentProfileIds); 18059 mUserLru.remove(currentUserIdInt); 18060 mUserLru.add(currentUserIdInt); 18061 } 18062 18063 final UserStartedState uss = mStartedUsers.get(userId); 18064 18065 // Make sure user is in the started state. If it is currently 18066 // stopping, we need to knock that off. 18067 if (uss.mState == UserStartedState.STATE_STOPPING) { 18068 // If we are stopping, we haven't sent ACTION_SHUTDOWN, 18069 // so we can just fairly silently bring the user back from 18070 // the almost-dead. 18071 uss.mState = UserStartedState.STATE_RUNNING; 18072 updateStartedUserArrayLocked(); 18073 needStart = true; 18074 } else if (uss.mState == UserStartedState.STATE_SHUTDOWN) { 18075 // This means ACTION_SHUTDOWN has been sent, so we will 18076 // need to treat this as a new boot of the user. 18077 uss.mState = UserStartedState.STATE_BOOTING; 18078 updateStartedUserArrayLocked(); 18079 needStart = true; 18080 } 18081 18082 if (uss.mState == UserStartedState.STATE_BOOTING) { 18083 // Booting up a new user, need to tell system services about it. 18084 // Note that this is on the same handler as scheduling of broadcasts, 18085 // which is important because it needs to go first. 18086 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_START_MSG, userId, 0)); 18087 } 18088 18089 if (foreground) { 18090 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_CURRENT_MSG, userId, 18091 oldUserId)); 18092 mHandler.removeMessages(REPORT_USER_SWITCH_MSG); 18093 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 18094 mHandler.sendMessage(mHandler.obtainMessage(REPORT_USER_SWITCH_MSG, 18095 oldUserId, userId, uss)); 18096 mHandler.sendMessageDelayed(mHandler.obtainMessage(USER_SWITCH_TIMEOUT_MSG, 18097 oldUserId, userId, uss), USER_SWITCH_TIMEOUT); 18098 } 18099 18100 if (needStart) { 18101 // Send USER_STARTED broadcast 18102 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 18103 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 18104 | Intent.FLAG_RECEIVER_FOREGROUND); 18105 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 18106 broadcastIntentLocked(null, null, intent, 18107 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 18108 false, false, MY_PID, Process.SYSTEM_UID, userId); 18109 } 18110 18111 if ((userInfo.flags&UserInfo.FLAG_INITIALIZED) == 0) { 18112 if (userId != UserHandle.USER_OWNER) { 18113 Intent intent = new Intent(Intent.ACTION_USER_INITIALIZE); 18114 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 18115 broadcastIntentLocked(null, null, intent, null, 18116 new IIntentReceiver.Stub() { 18117 public void performReceive(Intent intent, int resultCode, 18118 String data, Bundle extras, boolean ordered, 18119 boolean sticky, int sendingUser) { 18120 onUserInitialized(uss, foreground, oldUserId, userId); 18121 } 18122 }, 0, null, null, null, AppOpsManager.OP_NONE, 18123 true, false, MY_PID, Process.SYSTEM_UID, 18124 userId); 18125 uss.initializing = true; 18126 } else { 18127 getUserManagerLocked().makeInitialized(userInfo.id); 18128 } 18129 } 18130 18131 if (foreground) { 18132 if (!uss.initializing) { 18133 moveUserToForeground(uss, oldUserId, userId); 18134 } 18135 } else { 18136 mStackSupervisor.startBackgroundUserLocked(userId, uss); 18137 } 18138 18139 if (needStart) { 18140 Intent intent = new Intent(Intent.ACTION_USER_STARTING); 18141 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 18142 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 18143 broadcastIntentLocked(null, null, intent, 18144 null, new IIntentReceiver.Stub() { 18145 @Override 18146 public void performReceive(Intent intent, int resultCode, String data, 18147 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 18148 throws RemoteException { 18149 } 18150 }, 0, null, null, 18151 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 18152 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 18153 } 18154 } 18155 } finally { 18156 Binder.restoreCallingIdentity(ident); 18157 } 18158 18159 return true; 18160 } 18161 18162 void sendUserSwitchBroadcastsLocked(int oldUserId, int newUserId) { 18163 long ident = Binder.clearCallingIdentity(); 18164 try { 18165 Intent intent; 18166 if (oldUserId >= 0) { 18167 // Send USER_BACKGROUND broadcast to all profiles of the outgoing user 18168 List<UserInfo> profiles = mUserManager.getProfiles(oldUserId, false); 18169 int count = profiles.size(); 18170 for (int i = 0; i < count; i++) { 18171 int profileUserId = profiles.get(i).id; 18172 intent = new Intent(Intent.ACTION_USER_BACKGROUND); 18173 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 18174 | Intent.FLAG_RECEIVER_FOREGROUND); 18175 intent.putExtra(Intent.EXTRA_USER_HANDLE, profileUserId); 18176 broadcastIntentLocked(null, null, intent, 18177 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 18178 false, false, MY_PID, Process.SYSTEM_UID, profileUserId); 18179 } 18180 } 18181 if (newUserId >= 0) { 18182 // Send USER_FOREGROUND broadcast to all profiles of the incoming user 18183 List<UserInfo> profiles = mUserManager.getProfiles(newUserId, false); 18184 int count = profiles.size(); 18185 for (int i = 0; i < count; i++) { 18186 int profileUserId = profiles.get(i).id; 18187 intent = new Intent(Intent.ACTION_USER_FOREGROUND); 18188 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 18189 | Intent.FLAG_RECEIVER_FOREGROUND); 18190 intent.putExtra(Intent.EXTRA_USER_HANDLE, profileUserId); 18191 broadcastIntentLocked(null, null, intent, 18192 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 18193 false, false, MY_PID, Process.SYSTEM_UID, profileUserId); 18194 } 18195 intent = new Intent(Intent.ACTION_USER_SWITCHED); 18196 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 18197 | Intent.FLAG_RECEIVER_FOREGROUND); 18198 intent.putExtra(Intent.EXTRA_USER_HANDLE, newUserId); 18199 broadcastIntentLocked(null, null, intent, 18200 null, null, 0, null, null, 18201 android.Manifest.permission.MANAGE_USERS, AppOpsManager.OP_NONE, 18202 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 18203 } 18204 } finally { 18205 Binder.restoreCallingIdentity(ident); 18206 } 18207 } 18208 18209 void dispatchUserSwitch(final UserStartedState uss, final int oldUserId, 18210 final int newUserId) { 18211 final int N = mUserSwitchObservers.beginBroadcast(); 18212 if (N > 0) { 18213 final IRemoteCallback callback = new IRemoteCallback.Stub() { 18214 int mCount = 0; 18215 @Override 18216 public void sendResult(Bundle data) throws RemoteException { 18217 synchronized (ActivityManagerService.this) { 18218 if (mCurUserSwitchCallback == this) { 18219 mCount++; 18220 if (mCount == N) { 18221 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 18222 } 18223 } 18224 } 18225 } 18226 }; 18227 synchronized (this) { 18228 uss.switching = true; 18229 mCurUserSwitchCallback = callback; 18230 } 18231 for (int i=0; i<N; i++) { 18232 try { 18233 mUserSwitchObservers.getBroadcastItem(i).onUserSwitching( 18234 newUserId, callback); 18235 } catch (RemoteException e) { 18236 } 18237 } 18238 } else { 18239 synchronized (this) { 18240 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 18241 } 18242 } 18243 mUserSwitchObservers.finishBroadcast(); 18244 } 18245 18246 void timeoutUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 18247 synchronized (this) { 18248 Slog.w(TAG, "User switch timeout: from " + oldUserId + " to " + newUserId); 18249 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 18250 } 18251 } 18252 18253 void sendContinueUserSwitchLocked(UserStartedState uss, int oldUserId, int newUserId) { 18254 mCurUserSwitchCallback = null; 18255 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 18256 mHandler.sendMessage(mHandler.obtainMessage(CONTINUE_USER_SWITCH_MSG, 18257 oldUserId, newUserId, uss)); 18258 } 18259 18260 void onUserInitialized(UserStartedState uss, boolean foreground, int oldUserId, int newUserId) { 18261 synchronized (this) { 18262 if (foreground) { 18263 moveUserToForeground(uss, oldUserId, newUserId); 18264 } 18265 } 18266 18267 completeSwitchAndInitalize(uss, newUserId, true, false); 18268 } 18269 18270 void moveUserToForeground(UserStartedState uss, int oldUserId, int newUserId) { 18271 boolean homeInFront = mStackSupervisor.switchUserLocked(newUserId, uss); 18272 if (homeInFront) { 18273 startHomeActivityLocked(newUserId); 18274 } else { 18275 mStackSupervisor.resumeTopActivitiesLocked(); 18276 } 18277 EventLogTags.writeAmSwitchUser(newUserId); 18278 getUserManagerLocked().userForeground(newUserId); 18279 sendUserSwitchBroadcastsLocked(oldUserId, newUserId); 18280 } 18281 18282 void continueUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 18283 completeSwitchAndInitalize(uss, newUserId, false, true); 18284 } 18285 18286 void completeSwitchAndInitalize(UserStartedState uss, int newUserId, 18287 boolean clearInitializing, boolean clearSwitching) { 18288 boolean unfrozen = false; 18289 synchronized (this) { 18290 if (clearInitializing) { 18291 uss.initializing = false; 18292 getUserManagerLocked().makeInitialized(uss.mHandle.getIdentifier()); 18293 } 18294 if (clearSwitching) { 18295 uss.switching = false; 18296 } 18297 if (!uss.switching && !uss.initializing) { 18298 mWindowManager.stopFreezingScreen(); 18299 unfrozen = true; 18300 } 18301 } 18302 if (unfrozen) { 18303 final int N = mUserSwitchObservers.beginBroadcast(); 18304 for (int i=0; i<N; i++) { 18305 try { 18306 mUserSwitchObservers.getBroadcastItem(i).onUserSwitchComplete(newUserId); 18307 } catch (RemoteException e) { 18308 } 18309 } 18310 mUserSwitchObservers.finishBroadcast(); 18311 } 18312 } 18313 18314 void scheduleStartProfilesLocked() { 18315 if (!mHandler.hasMessages(START_PROFILES_MSG)) { 18316 mHandler.sendMessageDelayed(mHandler.obtainMessage(START_PROFILES_MSG), 18317 DateUtils.SECOND_IN_MILLIS); 18318 } 18319 } 18320 18321 void startProfilesLocked() { 18322 if (DEBUG_MU) Slog.i(TAG_MU, "startProfilesLocked"); 18323 List<UserInfo> profiles = getUserManagerLocked().getProfiles( 18324 mCurrentUserId, false /* enabledOnly */); 18325 List<UserInfo> toStart = new ArrayList<UserInfo>(profiles.size()); 18326 for (UserInfo user : profiles) { 18327 if ((user.flags & UserInfo.FLAG_INITIALIZED) == UserInfo.FLAG_INITIALIZED 18328 && user.id != mCurrentUserId) { 18329 toStart.add(user); 18330 } 18331 } 18332 final int n = toStart.size(); 18333 int i = 0; 18334 for (; i < n && i < (MAX_RUNNING_USERS - 1); ++i) { 18335 startUserInBackground(toStart.get(i).id); 18336 } 18337 if (i < n) { 18338 Slog.w(TAG_MU, "More profiles than MAX_RUNNING_USERS"); 18339 } 18340 } 18341 18342 void finishUserBoot(UserStartedState uss) { 18343 synchronized (this) { 18344 if (uss.mState == UserStartedState.STATE_BOOTING 18345 && mStartedUsers.get(uss.mHandle.getIdentifier()) == uss) { 18346 uss.mState = UserStartedState.STATE_RUNNING; 18347 final int userId = uss.mHandle.getIdentifier(); 18348 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 18349 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 18350 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 18351 broadcastIntentLocked(null, null, intent, 18352 null, null, 0, null, null, 18353 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, AppOpsManager.OP_NONE, 18354 true, false, MY_PID, Process.SYSTEM_UID, userId); 18355 } 18356 } 18357 } 18358 18359 void finishUserSwitch(UserStartedState uss) { 18360 synchronized (this) { 18361 finishUserBoot(uss); 18362 18363 startProfilesLocked(); 18364 18365 int num = mUserLru.size(); 18366 int i = 0; 18367 while (num > MAX_RUNNING_USERS && i < mUserLru.size()) { 18368 Integer oldUserId = mUserLru.get(i); 18369 UserStartedState oldUss = mStartedUsers.get(oldUserId); 18370 if (oldUss == null) { 18371 // Shouldn't happen, but be sane if it does. 18372 mUserLru.remove(i); 18373 num--; 18374 continue; 18375 } 18376 if (oldUss.mState == UserStartedState.STATE_STOPPING 18377 || oldUss.mState == UserStartedState.STATE_SHUTDOWN) { 18378 // This user is already stopping, doesn't count. 18379 num--; 18380 i++; 18381 continue; 18382 } 18383 if (oldUserId == UserHandle.USER_OWNER || oldUserId == mCurrentUserId) { 18384 // Owner and current can't be stopped, but count as running. 18385 i++; 18386 continue; 18387 } 18388 // This is a user to be stopped. 18389 stopUserLocked(oldUserId, null); 18390 num--; 18391 i++; 18392 } 18393 } 18394 } 18395 18396 @Override 18397 public int stopUser(final int userId, final IStopUserCallback callback) { 18398 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 18399 != PackageManager.PERMISSION_GRANTED) { 18400 String msg = "Permission Denial: switchUser() from pid=" 18401 + Binder.getCallingPid() 18402 + ", uid=" + Binder.getCallingUid() 18403 + " requires " + INTERACT_ACROSS_USERS_FULL; 18404 Slog.w(TAG, msg); 18405 throw new SecurityException(msg); 18406 } 18407 if (userId <= 0) { 18408 throw new IllegalArgumentException("Can't stop primary user " + userId); 18409 } 18410 synchronized (this) { 18411 return stopUserLocked(userId, callback); 18412 } 18413 } 18414 18415 private int stopUserLocked(final int userId, final IStopUserCallback callback) { 18416 if (DEBUG_MU) Slog.i(TAG_MU, "stopUserLocked userId=" + userId); 18417 if (mCurrentUserId == userId && mTargetUserId == UserHandle.USER_NULL) { 18418 return ActivityManager.USER_OP_IS_CURRENT; 18419 } 18420 18421 final UserStartedState uss = mStartedUsers.get(userId); 18422 if (uss == null) { 18423 // User is not started, nothing to do... but we do need to 18424 // callback if requested. 18425 if (callback != null) { 18426 mHandler.post(new Runnable() { 18427 @Override 18428 public void run() { 18429 try { 18430 callback.userStopped(userId); 18431 } catch (RemoteException e) { 18432 } 18433 } 18434 }); 18435 } 18436 return ActivityManager.USER_OP_SUCCESS; 18437 } 18438 18439 if (callback != null) { 18440 uss.mStopCallbacks.add(callback); 18441 } 18442 18443 if (uss.mState != UserStartedState.STATE_STOPPING 18444 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 18445 uss.mState = UserStartedState.STATE_STOPPING; 18446 updateStartedUserArrayLocked(); 18447 18448 long ident = Binder.clearCallingIdentity(); 18449 try { 18450 // We are going to broadcast ACTION_USER_STOPPING and then 18451 // once that is done send a final ACTION_SHUTDOWN and then 18452 // stop the user. 18453 final Intent stoppingIntent = new Intent(Intent.ACTION_USER_STOPPING); 18454 stoppingIntent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 18455 stoppingIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 18456 stoppingIntent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 18457 final Intent shutdownIntent = new Intent(Intent.ACTION_SHUTDOWN); 18458 // This is the result receiver for the final shutdown broadcast. 18459 final IIntentReceiver shutdownReceiver = new IIntentReceiver.Stub() { 18460 @Override 18461 public void performReceive(Intent intent, int resultCode, String data, 18462 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 18463 finishUserStop(uss); 18464 } 18465 }; 18466 // This is the result receiver for the initial stopping broadcast. 18467 final IIntentReceiver stoppingReceiver = new IIntentReceiver.Stub() { 18468 @Override 18469 public void performReceive(Intent intent, int resultCode, String data, 18470 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 18471 // On to the next. 18472 synchronized (ActivityManagerService.this) { 18473 if (uss.mState != UserStartedState.STATE_STOPPING) { 18474 // Whoops, we are being started back up. Abort, abort! 18475 return; 18476 } 18477 uss.mState = UserStartedState.STATE_SHUTDOWN; 18478 } 18479 mBatteryStatsService.noteEvent( 18480 BatteryStats.HistoryItem.EVENT_USER_RUNNING_FINISH, 18481 Integer.toString(userId), userId); 18482 mSystemServiceManager.stopUser(userId); 18483 broadcastIntentLocked(null, null, shutdownIntent, 18484 null, shutdownReceiver, 0, null, null, null, AppOpsManager.OP_NONE, 18485 true, false, MY_PID, Process.SYSTEM_UID, userId); 18486 } 18487 }; 18488 // Kick things off. 18489 broadcastIntentLocked(null, null, stoppingIntent, 18490 null, stoppingReceiver, 0, null, null, 18491 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 18492 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 18493 } finally { 18494 Binder.restoreCallingIdentity(ident); 18495 } 18496 } 18497 18498 return ActivityManager.USER_OP_SUCCESS; 18499 } 18500 18501 void finishUserStop(UserStartedState uss) { 18502 final int userId = uss.mHandle.getIdentifier(); 18503 boolean stopped; 18504 ArrayList<IStopUserCallback> callbacks; 18505 synchronized (this) { 18506 callbacks = new ArrayList<IStopUserCallback>(uss.mStopCallbacks); 18507 if (mStartedUsers.get(userId) != uss) { 18508 stopped = false; 18509 } else if (uss.mState != UserStartedState.STATE_SHUTDOWN) { 18510 stopped = false; 18511 } else { 18512 stopped = true; 18513 // User can no longer run. 18514 mStartedUsers.remove(userId); 18515 mUserLru.remove(Integer.valueOf(userId)); 18516 updateStartedUserArrayLocked(); 18517 18518 // Clean up all state and processes associated with the user. 18519 // Kill all the processes for the user. 18520 forceStopUserLocked(userId, "finish user"); 18521 } 18522 18523 // Explicitly remove the old information in mRecentTasks. 18524 removeRecentTasksForUserLocked(userId); 18525 } 18526 18527 for (int i=0; i<callbacks.size(); i++) { 18528 try { 18529 if (stopped) callbacks.get(i).userStopped(userId); 18530 else callbacks.get(i).userStopAborted(userId); 18531 } catch (RemoteException e) { 18532 } 18533 } 18534 18535 if (stopped) { 18536 mSystemServiceManager.cleanupUser(userId); 18537 synchronized (this) { 18538 mStackSupervisor.removeUserLocked(userId); 18539 } 18540 } 18541 } 18542 18543 @Override 18544 public UserInfo getCurrentUser() { 18545 if ((checkCallingPermission(INTERACT_ACROSS_USERS) 18546 != PackageManager.PERMISSION_GRANTED) && ( 18547 checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 18548 != PackageManager.PERMISSION_GRANTED)) { 18549 String msg = "Permission Denial: getCurrentUser() from pid=" 18550 + Binder.getCallingPid() 18551 + ", uid=" + Binder.getCallingUid() 18552 + " requires " + INTERACT_ACROSS_USERS; 18553 Slog.w(TAG, msg); 18554 throw new SecurityException(msg); 18555 } 18556 synchronized (this) { 18557 int userId = mTargetUserId != UserHandle.USER_NULL ? mTargetUserId : mCurrentUserId; 18558 return getUserManagerLocked().getUserInfo(userId); 18559 } 18560 } 18561 18562 int getCurrentUserIdLocked() { 18563 return mTargetUserId != UserHandle.USER_NULL ? mTargetUserId : mCurrentUserId; 18564 } 18565 18566 @Override 18567 public boolean isUserRunning(int userId, boolean orStopped) { 18568 if (checkCallingPermission(INTERACT_ACROSS_USERS) 18569 != PackageManager.PERMISSION_GRANTED) { 18570 String msg = "Permission Denial: isUserRunning() from pid=" 18571 + Binder.getCallingPid() 18572 + ", uid=" + Binder.getCallingUid() 18573 + " requires " + INTERACT_ACROSS_USERS; 18574 Slog.w(TAG, msg); 18575 throw new SecurityException(msg); 18576 } 18577 synchronized (this) { 18578 return isUserRunningLocked(userId, orStopped); 18579 } 18580 } 18581 18582 boolean isUserRunningLocked(int userId, boolean orStopped) { 18583 UserStartedState state = mStartedUsers.get(userId); 18584 if (state == null) { 18585 return false; 18586 } 18587 if (orStopped) { 18588 return true; 18589 } 18590 return state.mState != UserStartedState.STATE_STOPPING 18591 && state.mState != UserStartedState.STATE_SHUTDOWN; 18592 } 18593 18594 @Override 18595 public int[] getRunningUserIds() { 18596 if (checkCallingPermission(INTERACT_ACROSS_USERS) 18597 != PackageManager.PERMISSION_GRANTED) { 18598 String msg = "Permission Denial: isUserRunning() from pid=" 18599 + Binder.getCallingPid() 18600 + ", uid=" + Binder.getCallingUid() 18601 + " requires " + INTERACT_ACROSS_USERS; 18602 Slog.w(TAG, msg); 18603 throw new SecurityException(msg); 18604 } 18605 synchronized (this) { 18606 return mStartedUserArray; 18607 } 18608 } 18609 18610 private void updateStartedUserArrayLocked() { 18611 int num = 0; 18612 for (int i=0; i<mStartedUsers.size(); i++) { 18613 UserStartedState uss = mStartedUsers.valueAt(i); 18614 // This list does not include stopping users. 18615 if (uss.mState != UserStartedState.STATE_STOPPING 18616 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 18617 num++; 18618 } 18619 } 18620 mStartedUserArray = new int[num]; 18621 num = 0; 18622 for (int i=0; i<mStartedUsers.size(); i++) { 18623 UserStartedState uss = mStartedUsers.valueAt(i); 18624 if (uss.mState != UserStartedState.STATE_STOPPING 18625 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 18626 mStartedUserArray[num] = mStartedUsers.keyAt(i); 18627 num++; 18628 } 18629 } 18630 } 18631 18632 @Override 18633 public void registerUserSwitchObserver(IUserSwitchObserver observer) { 18634 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 18635 != PackageManager.PERMISSION_GRANTED) { 18636 String msg = "Permission Denial: registerUserSwitchObserver() from pid=" 18637 + Binder.getCallingPid() 18638 + ", uid=" + Binder.getCallingUid() 18639 + " requires " + INTERACT_ACROSS_USERS_FULL; 18640 Slog.w(TAG, msg); 18641 throw new SecurityException(msg); 18642 } 18643 18644 mUserSwitchObservers.register(observer); 18645 } 18646 18647 @Override 18648 public void unregisterUserSwitchObserver(IUserSwitchObserver observer) { 18649 mUserSwitchObservers.unregister(observer); 18650 } 18651 18652 private boolean userExists(int userId) { 18653 if (userId == 0) { 18654 return true; 18655 } 18656 UserManagerService ums = getUserManagerLocked(); 18657 return ums != null ? (ums.getUserInfo(userId) != null) : false; 18658 } 18659 18660 int[] getUsersLocked() { 18661 UserManagerService ums = getUserManagerLocked(); 18662 return ums != null ? ums.getUserIds() : new int[] { 0 }; 18663 } 18664 18665 UserManagerService getUserManagerLocked() { 18666 if (mUserManager == null) { 18667 IBinder b = ServiceManager.getService(Context.USER_SERVICE); 18668 mUserManager = (UserManagerService)IUserManager.Stub.asInterface(b); 18669 } 18670 return mUserManager; 18671 } 18672 18673 private int applyUserId(int uid, int userId) { 18674 return UserHandle.getUid(userId, uid); 18675 } 18676 18677 ApplicationInfo getAppInfoForUser(ApplicationInfo info, int userId) { 18678 if (info == null) return null; 18679 ApplicationInfo newInfo = new ApplicationInfo(info); 18680 newInfo.uid = applyUserId(info.uid, userId); 18681 newInfo.dataDir = USER_DATA_DIR + userId + "/" 18682 + info.packageName; 18683 return newInfo; 18684 } 18685 18686 ActivityInfo getActivityInfoForUser(ActivityInfo aInfo, int userId) { 18687 if (aInfo == null 18688 || (userId < 1 && aInfo.applicationInfo.uid < UserHandle.PER_USER_RANGE)) { 18689 return aInfo; 18690 } 18691 18692 ActivityInfo info = new ActivityInfo(aInfo); 18693 info.applicationInfo = getAppInfoForUser(info.applicationInfo, userId); 18694 return info; 18695 } 18696 18697 private final class LocalService extends ActivityManagerInternal { 18698 @Override 18699 public void goingToSleep() { 18700 ActivityManagerService.this.goingToSleep(); 18701 } 18702 18703 @Override 18704 public void wakingUp() { 18705 ActivityManagerService.this.wakingUp(); 18706 } 18707 18708 @Override 18709 public int startIsolatedProcess(String entryPoint, String[] entryPointArgs, 18710 String processName, String abiOverride, int uid, Runnable crashHandler) { 18711 return ActivityManagerService.this.startIsolatedProcess(entryPoint, entryPointArgs, 18712 processName, abiOverride, uid, crashHandler); 18713 } 18714 } 18715 18716 /** 18717 * An implementation of IAppTask, that allows an app to manage its own tasks via 18718 * {@link android.app.ActivityManager.AppTask}. We keep track of the callingUid to ensure that 18719 * only the process that calls getAppTasks() can call the AppTask methods. 18720 */ 18721 class AppTaskImpl extends IAppTask.Stub { 18722 private int mTaskId; 18723 private int mCallingUid; 18724 18725 public AppTaskImpl(int taskId, int callingUid) { 18726 mTaskId = taskId; 18727 mCallingUid = callingUid; 18728 } 18729 18730 private void checkCaller() { 18731 if (mCallingUid != Binder.getCallingUid()) { 18732 throw new SecurityException("Caller " + mCallingUid 18733 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 18734 } 18735 } 18736 18737 @Override 18738 public void finishAndRemoveTask() { 18739 checkCaller(); 18740 18741 synchronized (ActivityManagerService.this) { 18742 long origId = Binder.clearCallingIdentity(); 18743 try { 18744 TaskRecord tr = recentTaskForIdLocked(mTaskId); 18745 if (tr == null) { 18746 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 18747 } 18748 // Only kill the process if we are not a new document 18749 int flags = tr.getBaseIntent().getFlags(); 18750 boolean isDocument = (flags & Intent.FLAG_ACTIVITY_NEW_DOCUMENT) == 18751 Intent.FLAG_ACTIVITY_NEW_DOCUMENT; 18752 removeTaskByIdLocked(mTaskId, 18753 !isDocument ? ActivityManager.REMOVE_TASK_KILL_PROCESS : 0); 18754 } finally { 18755 Binder.restoreCallingIdentity(origId); 18756 } 18757 } 18758 } 18759 18760 @Override 18761 public ActivityManager.RecentTaskInfo getTaskInfo() { 18762 checkCaller(); 18763 18764 synchronized (ActivityManagerService.this) { 18765 long origId = Binder.clearCallingIdentity(); 18766 try { 18767 TaskRecord tr = recentTaskForIdLocked(mTaskId); 18768 if (tr == null) { 18769 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 18770 } 18771 return createRecentTaskInfoFromTaskRecord(tr); 18772 } finally { 18773 Binder.restoreCallingIdentity(origId); 18774 } 18775 } 18776 } 18777 18778 @Override 18779 public void moveToFront() { 18780 checkCaller(); 18781 18782 final TaskRecord tr; 18783 synchronized (ActivityManagerService.this) { 18784 tr = recentTaskForIdLocked(mTaskId); 18785 if (tr == null) { 18786 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 18787 } 18788 if (tr.getRootActivity() != null) { 18789 long origId = Binder.clearCallingIdentity(); 18790 try { 18791 moveTaskToFrontLocked(tr.taskId, 0, null); 18792 return; 18793 } finally { 18794 Binder.restoreCallingIdentity(origId); 18795 } 18796 } 18797 } 18798 18799 startActivityFromRecentsInner(tr.taskId, null); 18800 } 18801 18802 @Override 18803 public int startActivity(IBinder whoThread, String callingPackage, 18804 Intent intent, String resolvedType, Bundle options) { 18805 checkCaller(); 18806 18807 int callingUser = UserHandle.getCallingUserId(); 18808 TaskRecord tr; 18809 IApplicationThread appThread; 18810 synchronized (ActivityManagerService.this) { 18811 tr = recentTaskForIdLocked(mTaskId); 18812 if (tr == null) { 18813 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 18814 } 18815 appThread = ApplicationThreadNative.asInterface(whoThread); 18816 if (appThread == null) { 18817 throw new IllegalArgumentException("Bad app thread " + appThread); 18818 } 18819 } 18820 return mStackSupervisor.startActivityMayWait(appThread, -1, callingPackage, intent, 18821 resolvedType, null, null, null, null, 0, 0, null, null, 18822 null, options, callingUser, null, tr); 18823 } 18824 18825 @Override 18826 public void setExcludeFromRecents(boolean exclude) { 18827 checkCaller(); 18828 18829 synchronized (ActivityManagerService.this) { 18830 long origId = Binder.clearCallingIdentity(); 18831 try { 18832 TaskRecord tr = recentTaskForIdLocked(mTaskId); 18833 if (tr == null) { 18834 throw new IllegalArgumentException("Unable to find task ID " + mTaskId); 18835 } 18836 Intent intent = tr.getBaseIntent(); 18837 if (exclude) { 18838 intent.addFlags(Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 18839 } else { 18840 intent.setFlags(intent.getFlags() 18841 & ~Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS); 18842 } 18843 } finally { 18844 Binder.restoreCallingIdentity(origId); 18845 } 18846 } 18847 } 18848 } 18849} 18850