ActivityManagerService.java revision 2053168eb4506e2f8795afdbe9731c6451e1589c
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.content.pm.PackageManager.PERMISSION_GRANTED; 22import static com.android.internal.util.XmlUtils.readBooleanAttribute; 23import static com.android.internal.util.XmlUtils.readIntAttribute; 24import static com.android.internal.util.XmlUtils.readLongAttribute; 25import static com.android.internal.util.XmlUtils.writeBooleanAttribute; 26import static com.android.internal.util.XmlUtils.writeIntAttribute; 27import static com.android.internal.util.XmlUtils.writeLongAttribute; 28import static com.android.server.Watchdog.NATIVE_STACKS_OF_INTEREST; 29import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT; 30import static org.xmlpull.v1.XmlPullParser.START_TAG; 31import static com.android.server.am.ActivityStackSupervisor.HOME_STACK_ID; 32 33import android.Manifest; 34import android.app.AppOpsManager; 35import android.app.IActivityContainer; 36import android.app.IActivityContainerCallback; 37import android.app.IAppTask; 38import android.app.admin.DevicePolicyManager; 39import android.appwidget.AppWidgetManager; 40import android.graphics.Rect; 41import android.os.BatteryStats; 42import android.os.PersistableBundle; 43import android.service.voice.IVoiceInteractionSession; 44import android.util.ArrayMap; 45import android.util.ArraySet; 46 47import android.util.SparseIntArray; 48import com.android.internal.R; 49import com.android.internal.annotations.GuardedBy; 50import com.android.internal.app.IAppOpsService; 51import com.android.internal.app.IVoiceInteractor; 52import com.android.internal.app.ProcessMap; 53import com.android.internal.app.ProcessStats; 54import com.android.internal.content.PackageMonitor; 55import com.android.internal.os.BackgroundThread; 56import com.android.internal.os.BatteryStatsImpl; 57import com.android.internal.os.ProcessCpuTracker; 58import com.android.internal.os.TransferPipe; 59import com.android.internal.os.Zygote; 60import com.android.internal.util.FastPrintWriter; 61import com.android.internal.util.FastXmlSerializer; 62import com.android.internal.util.MemInfoReader; 63import com.android.internal.util.Preconditions; 64import com.android.server.AppOpsService; 65import com.android.server.AttributeCache; 66import com.android.server.IntentResolver; 67import com.android.server.LocalServices; 68import com.android.server.ServiceThread; 69import com.android.server.SystemService; 70import com.android.server.SystemServiceManager; 71import com.android.server.Watchdog; 72import com.android.server.am.ActivityStack.ActivityState; 73import com.android.server.firewall.IntentFirewall; 74import com.android.server.pm.UserManagerService; 75import com.android.server.wm.AppTransition; 76import com.android.server.wm.WindowManagerService; 77import com.google.android.collect.Lists; 78import com.google.android.collect.Maps; 79 80import libcore.io.IoUtils; 81 82import org.xmlpull.v1.XmlPullParser; 83import org.xmlpull.v1.XmlPullParserException; 84import org.xmlpull.v1.XmlSerializer; 85 86import android.app.Activity; 87import android.app.ActivityManager; 88import android.app.ActivityManager.RunningTaskInfo; 89import android.app.ActivityManager.StackInfo; 90import android.app.ActivityManagerInternal; 91import android.app.ActivityManagerNative; 92import android.app.ActivityOptions; 93import android.app.ActivityThread; 94import android.app.AlertDialog; 95import android.app.AppGlobals; 96import android.app.ApplicationErrorReport; 97import android.app.Dialog; 98import android.app.IActivityController; 99import android.app.IApplicationThread; 100import android.app.IInstrumentationWatcher; 101import android.app.INotificationManager; 102import android.app.IProcessObserver; 103import android.app.IServiceConnection; 104import android.app.IStopUserCallback; 105import android.app.IUiAutomationConnection; 106import android.app.IUserSwitchObserver; 107import android.app.Instrumentation; 108import android.app.Notification; 109import android.app.NotificationManager; 110import android.app.PendingIntent; 111import android.app.backup.IBackupManager; 112import android.content.ActivityNotFoundException; 113import android.content.BroadcastReceiver; 114import android.content.ClipData; 115import android.content.ComponentCallbacks2; 116import android.content.ComponentName; 117import android.content.ContentProvider; 118import android.content.ContentResolver; 119import android.content.Context; 120import android.content.DialogInterface; 121import android.content.IContentProvider; 122import android.content.IIntentReceiver; 123import android.content.IIntentSender; 124import android.content.Intent; 125import android.content.IntentFilter; 126import android.content.IntentSender; 127import android.content.pm.ActivityInfo; 128import android.content.pm.ApplicationInfo; 129import android.content.pm.ConfigurationInfo; 130import android.content.pm.IPackageDataObserver; 131import android.content.pm.IPackageManager; 132import android.content.pm.InstrumentationInfo; 133import android.content.pm.PackageInfo; 134import android.content.pm.PackageManager; 135import android.content.pm.ParceledListSlice; 136import android.content.pm.UserInfo; 137import android.content.pm.PackageManager.NameNotFoundException; 138import android.content.pm.PathPermission; 139import android.content.pm.ProviderInfo; 140import android.content.pm.ResolveInfo; 141import android.content.pm.ServiceInfo; 142import android.content.res.CompatibilityInfo; 143import android.content.res.Configuration; 144import android.net.Proxy; 145import android.net.ProxyInfo; 146import android.net.Uri; 147import android.os.Binder; 148import android.os.Build; 149import android.os.Bundle; 150import android.os.Debug; 151import android.os.DropBoxManager; 152import android.os.Environment; 153import android.os.FactoryTest; 154import android.os.FileObserver; 155import android.os.FileUtils; 156import android.os.Handler; 157import android.os.IBinder; 158import android.os.IPermissionController; 159import android.os.IRemoteCallback; 160import android.os.IUserManager; 161import android.os.Looper; 162import android.os.Message; 163import android.os.Parcel; 164import android.os.ParcelFileDescriptor; 165import android.os.Process; 166import android.os.RemoteCallbackList; 167import android.os.RemoteException; 168import android.os.SELinux; 169import android.os.ServiceManager; 170import android.os.StrictMode; 171import android.os.SystemClock; 172import android.os.SystemProperties; 173import android.os.UpdateLock; 174import android.os.UserHandle; 175import android.provider.Settings; 176import android.text.format.DateUtils; 177import android.text.format.Time; 178import android.util.AtomicFile; 179import android.util.EventLog; 180import android.util.Log; 181import android.util.Pair; 182import android.util.PrintWriterPrinter; 183import android.util.Slog; 184import android.util.SparseArray; 185import android.util.TimeUtils; 186import android.util.Xml; 187import android.view.Gravity; 188import android.view.LayoutInflater; 189import android.view.View; 190import android.view.WindowManager; 191 192import java.io.BufferedInputStream; 193import java.io.BufferedOutputStream; 194import java.io.DataInputStream; 195import java.io.DataOutputStream; 196import java.io.File; 197import java.io.FileDescriptor; 198import java.io.FileInputStream; 199import java.io.FileNotFoundException; 200import java.io.FileOutputStream; 201import java.io.IOException; 202import java.io.InputStreamReader; 203import java.io.PrintWriter; 204import java.io.StringWriter; 205import java.lang.ref.WeakReference; 206import java.util.ArrayList; 207import java.util.Arrays; 208import java.util.Collections; 209import java.util.Comparator; 210import java.util.HashMap; 211import java.util.HashSet; 212import java.util.Iterator; 213import java.util.List; 214import java.util.Locale; 215import java.util.Map; 216import java.util.Set; 217import java.util.concurrent.atomic.AtomicBoolean; 218import java.util.concurrent.atomic.AtomicLong; 219 220public final class ActivityManagerService extends ActivityManagerNative 221 implements Watchdog.Monitor, BatteryStatsImpl.BatteryCallback { 222 private static final String USER_DATA_DIR = "/data/user/"; 223 static final String TAG = "ActivityManager"; 224 static final String TAG_MU = "ActivityManagerServiceMU"; 225 static final boolean DEBUG = false; 226 static final boolean localLOGV = DEBUG; 227 static final boolean DEBUG_BACKUP = localLOGV || false; 228 static final boolean DEBUG_BROADCAST = localLOGV || false; 229 static final boolean DEBUG_BROADCAST_LIGHT = DEBUG_BROADCAST || false; 230 static final boolean DEBUG_BACKGROUND_BROADCAST = DEBUG_BROADCAST || false; 231 static final boolean DEBUG_CLEANUP = localLOGV || false; 232 static final boolean DEBUG_CONFIGURATION = localLOGV || false; 233 static final boolean DEBUG_FOCUS = false; 234 static final boolean DEBUG_IMMERSIVE = localLOGV || false; 235 static final boolean DEBUG_MU = localLOGV || false; 236 static final boolean DEBUG_OOM_ADJ = localLOGV || false; 237 static final boolean DEBUG_LRU = localLOGV || false; 238 static final boolean DEBUG_PAUSE = localLOGV || false; 239 static final boolean DEBUG_POWER = localLOGV || false; 240 static final boolean DEBUG_POWER_QUICK = DEBUG_POWER || false; 241 static final boolean DEBUG_PROCESS_OBSERVERS = localLOGV || false; 242 static final boolean DEBUG_PROCESSES = localLOGV || false; 243 static final boolean DEBUG_PROVIDER = localLOGV || false; 244 static final boolean DEBUG_RESULTS = localLOGV || false; 245 static final boolean DEBUG_SERVICE = localLOGV || false; 246 static final boolean DEBUG_SERVICE_EXECUTING = localLOGV || false; 247 static final boolean DEBUG_STACK = localLOGV || false; 248 static final boolean DEBUG_SWITCH = localLOGV || false; 249 static final boolean DEBUG_TASKS = localLOGV || false; 250 static final boolean DEBUG_THUMBNAILS = localLOGV || false; 251 static final boolean DEBUG_TRANSITION = localLOGV || false; 252 static final boolean DEBUG_URI_PERMISSION = localLOGV || false; 253 static final boolean DEBUG_USER_LEAVING = localLOGV || false; 254 static final boolean DEBUG_VISBILITY = localLOGV || false; 255 static final boolean DEBUG_PSS = localLOGV || false; 256 static final boolean DEBUG_LOCKSCREEN = localLOGV || false; 257 static final boolean VALIDATE_TOKENS = false; 258 static final boolean SHOW_ACTIVITY_START_TIME = true; 259 260 // Control over CPU and battery monitoring. 261 static final long BATTERY_STATS_TIME = 30*60*1000; // write battery stats every 30 minutes. 262 static final boolean MONITOR_CPU_USAGE = true; 263 static final long MONITOR_CPU_MIN_TIME = 5*1000; // don't sample cpu less than every 5 seconds. 264 static final long MONITOR_CPU_MAX_TIME = 0x0fffffff; // wait possibly forever for next cpu sample. 265 static final boolean MONITOR_THREAD_CPU_USAGE = false; 266 267 // The flags that are set for all calls we make to the package manager. 268 static final int STOCK_PM_FLAGS = PackageManager.GET_SHARED_LIBRARY_FILES; 269 270 private static final String SYSTEM_DEBUGGABLE = "ro.debuggable"; 271 272 static final boolean IS_USER_BUILD = "user".equals(Build.TYPE); 273 274 // Maximum number of recent tasks that we can remember. 275 static final int MAX_RECENT_TASKS = ActivityManager.isLowRamDeviceStatic() ? 100 : 200; 276 277 // Maximum number recent bitmaps to keep in memory. 278 static final int MAX_RECENT_BITMAPS = 5; 279 280 // Amount of time after a call to stopAppSwitches() during which we will 281 // prevent further untrusted switches from happening. 282 static final long APP_SWITCH_DELAY_TIME = 5*1000; 283 284 // How long we wait for a launched process to attach to the activity manager 285 // before we decide it's never going to come up for real. 286 static final int PROC_START_TIMEOUT = 10*1000; 287 288 // How long we wait for a launched process to attach to the activity manager 289 // before we decide it's never going to come up for real, when the process was 290 // started with a wrapper for instrumentation (such as Valgrind) because it 291 // could take much longer than usual. 292 static final int PROC_START_TIMEOUT_WITH_WRAPPER = 1200*1000; 293 294 // How long to wait after going idle before forcing apps to GC. 295 static final int GC_TIMEOUT = 5*1000; 296 297 // The minimum amount of time between successive GC requests for a process. 298 static final int GC_MIN_INTERVAL = 60*1000; 299 300 // The minimum amount of time between successive PSS requests for a process. 301 static final int FULL_PSS_MIN_INTERVAL = 10*60*1000; 302 303 // The minimum amount of time between successive PSS requests for a process 304 // when the request is due to the memory state being lowered. 305 static final int FULL_PSS_LOWERED_INTERVAL = 2*60*1000; 306 307 // The rate at which we check for apps using excessive power -- 15 mins. 308 static final int POWER_CHECK_DELAY = (DEBUG_POWER_QUICK ? 2 : 15) * 60*1000; 309 310 // The minimum sample duration we will allow before deciding we have 311 // enough data on wake locks to start killing things. 312 static final int WAKE_LOCK_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 313 314 // The minimum sample duration we will allow before deciding we have 315 // enough data on CPU usage to start killing things. 316 static final int CPU_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 317 318 // How long we allow a receiver to run before giving up on it. 319 static final int BROADCAST_FG_TIMEOUT = 10*1000; 320 static final int BROADCAST_BG_TIMEOUT = 60*1000; 321 322 // How long we wait until we timeout on key dispatching. 323 static final int KEY_DISPATCHING_TIMEOUT = 5*1000; 324 325 // How long we wait until we timeout on key dispatching during instrumentation. 326 static final int INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT = 60*1000; 327 328 // Amount of time we wait for observers to handle a user switch before 329 // giving up on them and unfreezing the screen. 330 static final int USER_SWITCH_TIMEOUT = 2*1000; 331 332 // Maximum number of users we allow to be running at a time. 333 static final int MAX_RUNNING_USERS = 3; 334 335 // How long to wait in getAssistContextExtras for the activity and foreground services 336 // to respond with the result. 337 static final int PENDING_ASSIST_EXTRAS_TIMEOUT = 500; 338 339 // Maximum number of persisted Uri grants a package is allowed 340 static final int MAX_PERSISTED_URI_GRANTS = 128; 341 342 static final int MY_PID = Process.myPid(); 343 344 static final String[] EMPTY_STRING_ARRAY = new String[0]; 345 346 // How many bytes to write into the dropbox log before truncating 347 static final int DROPBOX_MAX_SIZE = 256 * 1024; 348 349 // Access modes for handleIncomingUser. 350 static final int ALLOW_NON_FULL = 0; 351 static final int ALLOW_NON_FULL_IN_PROFILE = 1; 352 static final int ALLOW_FULL_ONLY = 2; 353 354 /** All system services */ 355 SystemServiceManager mSystemServiceManager; 356 357 /** Run all ActivityStacks through this */ 358 ActivityStackSupervisor mStackSupervisor; 359 360 public IntentFirewall mIntentFirewall; 361 362 // Whether we should show our dialogs (ANR, crash, etc) or just perform their 363 // default actuion automatically. Important for devices without direct input 364 // devices. 365 private boolean mShowDialogs = true; 366 367 /** 368 * Description of a request to start a new activity, which has been held 369 * due to app switches being disabled. 370 */ 371 static class PendingActivityLaunch { 372 final ActivityRecord r; 373 final ActivityRecord sourceRecord; 374 final int startFlags; 375 final ActivityStack stack; 376 377 PendingActivityLaunch(ActivityRecord _r, ActivityRecord _sourceRecord, 378 int _startFlags, ActivityStack _stack) { 379 r = _r; 380 sourceRecord = _sourceRecord; 381 startFlags = _startFlags; 382 stack = _stack; 383 } 384 } 385 386 final ArrayList<PendingActivityLaunch> mPendingActivityLaunches 387 = new ArrayList<PendingActivityLaunch>(); 388 389 BroadcastQueue mFgBroadcastQueue; 390 BroadcastQueue mBgBroadcastQueue; 391 // Convenient for easy iteration over the queues. Foreground is first 392 // so that dispatch of foreground broadcasts gets precedence. 393 final BroadcastQueue[] mBroadcastQueues = new BroadcastQueue[2]; 394 395 BroadcastQueue broadcastQueueForIntent(Intent intent) { 396 final boolean isFg = (intent.getFlags() & Intent.FLAG_RECEIVER_FOREGROUND) != 0; 397 if (DEBUG_BACKGROUND_BROADCAST) { 398 Slog.i(TAG, "Broadcast intent " + intent + " on " 399 + (isFg ? "foreground" : "background") 400 + " queue"); 401 } 402 return (isFg) ? mFgBroadcastQueue : mBgBroadcastQueue; 403 } 404 405 BroadcastRecord broadcastRecordForReceiverLocked(IBinder receiver) { 406 for (BroadcastQueue queue : mBroadcastQueues) { 407 BroadcastRecord r = queue.getMatchingOrderedReceiver(receiver); 408 if (r != null) { 409 return r; 410 } 411 } 412 return null; 413 } 414 415 /** 416 * Activity we have told the window manager to have key focus. 417 */ 418 ActivityRecord mFocusedActivity = null; 419 420 /** 421 * List of intents that were used to start the most recent tasks. 422 */ 423 ArrayList<TaskRecord> mRecentTasks; 424 ArraySet<TaskRecord> mTmpRecents = new ArraySet<TaskRecord>(); 425 426 public class PendingAssistExtras extends Binder implements Runnable { 427 public final ActivityRecord activity; 428 public boolean haveResult = false; 429 public Bundle result = null; 430 public PendingAssistExtras(ActivityRecord _activity) { 431 activity = _activity; 432 } 433 @Override 434 public void run() { 435 Slog.w(TAG, "getAssistContextExtras failed: timeout retrieving from " + activity); 436 synchronized (this) { 437 haveResult = true; 438 notifyAll(); 439 } 440 } 441 } 442 443 final ArrayList<PendingAssistExtras> mPendingAssistExtras 444 = new ArrayList<PendingAssistExtras>(); 445 446 /** 447 * Process management. 448 */ 449 final ProcessList mProcessList = new ProcessList(); 450 451 /** 452 * All of the applications we currently have running organized by name. 453 * The keys are strings of the application package name (as 454 * returned by the package manager), and the keys are ApplicationRecord 455 * objects. 456 */ 457 final ProcessMap<ProcessRecord> mProcessNames = new ProcessMap<ProcessRecord>(); 458 459 /** 460 * Tracking long-term execution of processes to look for abuse and other 461 * bad app behavior. 462 */ 463 final ProcessStatsService mProcessStats; 464 465 /** 466 * The currently running isolated processes. 467 */ 468 final SparseArray<ProcessRecord> mIsolatedProcesses = new SparseArray<ProcessRecord>(); 469 470 /** 471 * Counter for assigning isolated process uids, to avoid frequently reusing the 472 * same ones. 473 */ 474 int mNextIsolatedProcessUid = 0; 475 476 /** 477 * The currently running heavy-weight process, if any. 478 */ 479 ProcessRecord mHeavyWeightProcess = null; 480 481 /** 482 * The last time that various processes have crashed. 483 */ 484 final ProcessMap<Long> mProcessCrashTimes = new ProcessMap<Long>(); 485 486 /** 487 * Information about a process that is currently marked as bad. 488 */ 489 static final class BadProcessInfo { 490 BadProcessInfo(long time, String shortMsg, String longMsg, String stack) { 491 this.time = time; 492 this.shortMsg = shortMsg; 493 this.longMsg = longMsg; 494 this.stack = stack; 495 } 496 497 final long time; 498 final String shortMsg; 499 final String longMsg; 500 final String stack; 501 } 502 503 /** 504 * Set of applications that we consider to be bad, and will reject 505 * incoming broadcasts from (which the user has no control over). 506 * Processes are added to this set when they have crashed twice within 507 * a minimum amount of time; they are removed from it when they are 508 * later restarted (hopefully due to some user action). The value is the 509 * time it was added to the list. 510 */ 511 final ProcessMap<BadProcessInfo> mBadProcesses = new ProcessMap<BadProcessInfo>(); 512 513 /** 514 * All of the processes we currently have running organized by pid. 515 * The keys are the pid running the application. 516 * 517 * <p>NOTE: This object is protected by its own lock, NOT the global 518 * activity manager lock! 519 */ 520 final SparseArray<ProcessRecord> mPidsSelfLocked = new SparseArray<ProcessRecord>(); 521 522 /** 523 * All of the processes that have been forced to be foreground. The key 524 * is the pid of the caller who requested it (we hold a death 525 * link on it). 526 */ 527 abstract class ForegroundToken implements IBinder.DeathRecipient { 528 int pid; 529 IBinder token; 530 } 531 final SparseArray<ForegroundToken> mForegroundProcesses = new SparseArray<ForegroundToken>(); 532 533 /** 534 * List of records for processes that someone had tried to start before the 535 * system was ready. We don't start them at that point, but ensure they 536 * are started by the time booting is complete. 537 */ 538 final ArrayList<ProcessRecord> mProcessesOnHold = new ArrayList<ProcessRecord>(); 539 540 /** 541 * List of persistent applications that are in the process 542 * of being started. 543 */ 544 final ArrayList<ProcessRecord> mPersistentStartingProcesses = new ArrayList<ProcessRecord>(); 545 546 /** 547 * Processes that are being forcibly torn down. 548 */ 549 final ArrayList<ProcessRecord> mRemovedProcesses = new ArrayList<ProcessRecord>(); 550 551 /** 552 * List of running applications, sorted by recent usage. 553 * The first entry in the list is the least recently used. 554 */ 555 final ArrayList<ProcessRecord> mLruProcesses = new ArrayList<ProcessRecord>(); 556 557 /** 558 * Where in mLruProcesses that the processes hosting activities start. 559 */ 560 int mLruProcessActivityStart = 0; 561 562 /** 563 * Where in mLruProcesses that the processes hosting services start. 564 * This is after (lower index) than mLruProcessesActivityStart. 565 */ 566 int mLruProcessServiceStart = 0; 567 568 /** 569 * List of processes that should gc as soon as things are idle. 570 */ 571 final ArrayList<ProcessRecord> mProcessesToGc = new ArrayList<ProcessRecord>(); 572 573 /** 574 * Processes we want to collect PSS data from. 575 */ 576 final ArrayList<ProcessRecord> mPendingPssProcesses = new ArrayList<ProcessRecord>(); 577 578 /** 579 * Last time we requested PSS data of all processes. 580 */ 581 long mLastFullPssTime = SystemClock.uptimeMillis(); 582 583 /** 584 * If set, the next time we collect PSS data we should do a full collection 585 * with data from native processes and the kernel. 586 */ 587 boolean mFullPssPending = false; 588 589 /** 590 * This is the process holding what we currently consider to be 591 * the "home" activity. 592 */ 593 ProcessRecord mHomeProcess; 594 595 /** 596 * This is the process holding the activity the user last visited that 597 * is in a different process from the one they are currently in. 598 */ 599 ProcessRecord mPreviousProcess; 600 601 /** 602 * The time at which the previous process was last visible. 603 */ 604 long mPreviousProcessVisibleTime; 605 606 /** 607 * Which uses have been started, so are allowed to run code. 608 */ 609 final SparseArray<UserStartedState> mStartedUsers = new SparseArray<UserStartedState>(); 610 611 /** 612 * LRU list of history of current users. Most recently current is at the end. 613 */ 614 final ArrayList<Integer> mUserLru = new ArrayList<Integer>(); 615 616 /** 617 * Constant array of the users that are currently started. 618 */ 619 int[] mStartedUserArray = new int[] { 0 }; 620 621 /** 622 * Registered observers of the user switching mechanics. 623 */ 624 final RemoteCallbackList<IUserSwitchObserver> mUserSwitchObservers 625 = new RemoteCallbackList<IUserSwitchObserver>(); 626 627 /** 628 * Currently active user switch. 629 */ 630 Object mCurUserSwitchCallback; 631 632 /** 633 * Packages that the user has asked to have run in screen size 634 * compatibility mode instead of filling the screen. 635 */ 636 final CompatModePackages mCompatModePackages; 637 638 /** 639 * Set of IntentSenderRecord objects that are currently active. 640 */ 641 final HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>> mIntentSenderRecords 642 = new HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>>(); 643 644 /** 645 * Fingerprints (hashCode()) of stack traces that we've 646 * already logged DropBox entries for. Guarded by itself. If 647 * something (rogue user app) forces this over 648 * MAX_DUP_SUPPRESSED_STACKS entries, the contents are cleared. 649 */ 650 private final HashSet<Integer> mAlreadyLoggedViolatedStacks = new HashSet<Integer>(); 651 private static final int MAX_DUP_SUPPRESSED_STACKS = 5000; 652 653 /** 654 * Strict Mode background batched logging state. 655 * 656 * The string buffer is guarded by itself, and its lock is also 657 * used to determine if another batched write is already 658 * in-flight. 659 */ 660 private final StringBuilder mStrictModeBuffer = new StringBuilder(); 661 662 /** 663 * Keeps track of all IIntentReceivers that have been registered for 664 * broadcasts. Hash keys are the receiver IBinder, hash value is 665 * a ReceiverList. 666 */ 667 final HashMap<IBinder, ReceiverList> mRegisteredReceivers = 668 new HashMap<IBinder, ReceiverList>(); 669 670 /** 671 * Resolver for broadcast intents to registered receivers. 672 * Holds BroadcastFilter (subclass of IntentFilter). 673 */ 674 final IntentResolver<BroadcastFilter, BroadcastFilter> mReceiverResolver 675 = new IntentResolver<BroadcastFilter, BroadcastFilter>() { 676 @Override 677 protected boolean allowFilterResult( 678 BroadcastFilter filter, List<BroadcastFilter> dest) { 679 IBinder target = filter.receiverList.receiver.asBinder(); 680 for (int i=dest.size()-1; i>=0; i--) { 681 if (dest.get(i).receiverList.receiver.asBinder() == target) { 682 return false; 683 } 684 } 685 return true; 686 } 687 688 @Override 689 protected BroadcastFilter newResult(BroadcastFilter filter, int match, int userId) { 690 if (userId == UserHandle.USER_ALL || filter.owningUserId == UserHandle.USER_ALL 691 || userId == filter.owningUserId) { 692 return super.newResult(filter, match, userId); 693 } 694 return null; 695 } 696 697 @Override 698 protected BroadcastFilter[] newArray(int size) { 699 return new BroadcastFilter[size]; 700 } 701 702 @Override 703 protected boolean isPackageForFilter(String packageName, BroadcastFilter filter) { 704 return packageName.equals(filter.packageName); 705 } 706 }; 707 708 /** 709 * State of all active sticky broadcasts per user. Keys are the action of the 710 * sticky Intent, values are an ArrayList of all broadcasted intents with 711 * that action (which should usually be one). The SparseArray is keyed 712 * by the user ID the sticky is for, and can include UserHandle.USER_ALL 713 * for stickies that are sent to all users. 714 */ 715 final SparseArray<ArrayMap<String, ArrayList<Intent>>> mStickyBroadcasts = 716 new SparseArray<ArrayMap<String, ArrayList<Intent>>>(); 717 718 final ActiveServices mServices; 719 720 /** 721 * Backup/restore process management 722 */ 723 String mBackupAppName = null; 724 BackupRecord mBackupTarget = null; 725 726 final ProviderMap mProviderMap; 727 728 /** 729 * List of content providers who have clients waiting for them. The 730 * application is currently being launched and the provider will be 731 * removed from this list once it is published. 732 */ 733 final ArrayList<ContentProviderRecord> mLaunchingProviders 734 = new ArrayList<ContentProviderRecord>(); 735 736 /** 737 * File storing persisted {@link #mGrantedUriPermissions}. 738 */ 739 private final AtomicFile mGrantFile; 740 741 /** XML constants used in {@link #mGrantFile} */ 742 private static final String TAG_URI_GRANTS = "uri-grants"; 743 private static final String TAG_URI_GRANT = "uri-grant"; 744 private static final String ATTR_USER_HANDLE = "userHandle"; 745 private static final String ATTR_SOURCE_USER_ID = "sourceUserId"; 746 private static final String ATTR_TARGET_USER_ID = "targetUserId"; 747 private static final String ATTR_SOURCE_PKG = "sourcePkg"; 748 private static final String ATTR_TARGET_PKG = "targetPkg"; 749 private static final String ATTR_URI = "uri"; 750 private static final String ATTR_MODE_FLAGS = "modeFlags"; 751 private static final String ATTR_CREATED_TIME = "createdTime"; 752 private static final String ATTR_PREFIX = "prefix"; 753 754 /** 755 * Global set of specific {@link Uri} permissions that have been granted. 756 * This optimized lookup structure maps from {@link UriPermission#targetUid} 757 * to {@link UriPermission#uri} to {@link UriPermission}. 758 */ 759 @GuardedBy("this") 760 private final SparseArray<ArrayMap<GrantUri, UriPermission>> 761 mGrantedUriPermissions = new SparseArray<ArrayMap<GrantUri, UriPermission>>(); 762 763 public static class GrantUri { 764 public final int sourceUserId; 765 public final Uri uri; 766 public boolean prefix; 767 768 public GrantUri(int sourceUserId, Uri uri, boolean prefix) { 769 this.sourceUserId = sourceUserId; 770 this.uri = uri; 771 this.prefix = prefix; 772 } 773 774 @Override 775 public int hashCode() { 776 return toString().hashCode(); 777 } 778 779 @Override 780 public boolean equals(Object o) { 781 if (o instanceof GrantUri) { 782 GrantUri other = (GrantUri) o; 783 return uri.equals(other.uri) && (sourceUserId == other.sourceUserId) 784 && prefix == other.prefix; 785 } 786 return false; 787 } 788 789 @Override 790 public String toString() { 791 String result = Integer.toString(sourceUserId) + " @ " + uri.toString(); 792 if (prefix) result += " [prefix]"; 793 return result; 794 } 795 796 public String toSafeString() { 797 String result = Integer.toString(sourceUserId) + " @ " + uri.toSafeString(); 798 if (prefix) result += " [prefix]"; 799 return result; 800 } 801 802 public static GrantUri resolve(int defaultSourceUserHandle, Uri uri) { 803 return new GrantUri(ContentProvider.getUserIdFromUri(uri, defaultSourceUserHandle), 804 ContentProvider.getUriWithoutUserId(uri), false); 805 } 806 } 807 808 CoreSettingsObserver mCoreSettingsObserver; 809 810 /** 811 * Thread-local storage used to carry caller permissions over through 812 * indirect content-provider access. 813 */ 814 private class Identity { 815 public int pid; 816 public int uid; 817 818 Identity(int _pid, int _uid) { 819 pid = _pid; 820 uid = _uid; 821 } 822 } 823 824 private static final ThreadLocal<Identity> sCallerIdentity = new ThreadLocal<Identity>(); 825 826 /** 827 * All information we have collected about the runtime performance of 828 * any user id that can impact battery performance. 829 */ 830 final BatteryStatsService mBatteryStatsService; 831 832 /** 833 * Information about component usage 834 */ 835 final UsageStatsService mUsageStatsService; 836 837 /** 838 * Information about and control over application operations 839 */ 840 final AppOpsService mAppOpsService; 841 842 /** 843 * Save recent tasks information across reboots. 844 */ 845 final TaskPersister mTaskPersister; 846 847 /** 848 * Current configuration information. HistoryRecord objects are given 849 * a reference to this object to indicate which configuration they are 850 * currently running in, so this object must be kept immutable. 851 */ 852 Configuration mConfiguration = new Configuration(); 853 854 /** 855 * Current sequencing integer of the configuration, for skipping old 856 * configurations. 857 */ 858 int mConfigurationSeq = 0; 859 860 /** 861 * Hardware-reported OpenGLES version. 862 */ 863 final int GL_ES_VERSION; 864 865 /** 866 * List of initialization arguments to pass to all processes when binding applications to them. 867 * For example, references to the commonly used services. 868 */ 869 HashMap<String, IBinder> mAppBindArgs; 870 871 /** 872 * Temporary to avoid allocations. Protected by main lock. 873 */ 874 final StringBuilder mStringBuilder = new StringBuilder(256); 875 876 /** 877 * Used to control how we initialize the service. 878 */ 879 ComponentName mTopComponent; 880 String mTopAction = Intent.ACTION_MAIN; 881 String mTopData; 882 boolean mProcessesReady = false; 883 boolean mSystemReady = false; 884 boolean mBooting = false; 885 boolean mWaitingUpdate = false; 886 boolean mDidUpdate = false; 887 boolean mOnBattery = false; 888 boolean mLaunchWarningShown = false; 889 890 Context mContext; 891 892 int mFactoryTest; 893 894 boolean mCheckedForSetup; 895 896 /** 897 * The time at which we will allow normal application switches again, 898 * after a call to {@link #stopAppSwitches()}. 899 */ 900 long mAppSwitchesAllowedTime; 901 902 /** 903 * This is set to true after the first switch after mAppSwitchesAllowedTime 904 * is set; any switches after that will clear the time. 905 */ 906 boolean mDidAppSwitch; 907 908 /** 909 * Last time (in realtime) at which we checked for power usage. 910 */ 911 long mLastPowerCheckRealtime; 912 913 /** 914 * Last time (in uptime) at which we checked for power usage. 915 */ 916 long mLastPowerCheckUptime; 917 918 /** 919 * Set while we are wanting to sleep, to prevent any 920 * activities from being started/resumed. 921 */ 922 private boolean mSleeping = false; 923 924 /** 925 * Set while we are running a voice interaction. This overrides 926 * sleeping while it is active. 927 */ 928 private boolean mRunningVoice = false; 929 930 /** 931 * State of external calls telling us if the device is asleep. 932 */ 933 private boolean mWentToSleep = false; 934 935 /** 936 * State of external call telling us if the lock screen is shown. 937 */ 938 private boolean mLockScreenShown = false; 939 940 /** 941 * Set if we are shutting down the system, similar to sleeping. 942 */ 943 boolean mShuttingDown = false; 944 945 /** 946 * Current sequence id for oom_adj computation traversal. 947 */ 948 int mAdjSeq = 0; 949 950 /** 951 * Current sequence id for process LRU updating. 952 */ 953 int mLruSeq = 0; 954 955 /** 956 * Keep track of the non-cached/empty process we last found, to help 957 * determine how to distribute cached/empty processes next time. 958 */ 959 int mNumNonCachedProcs = 0; 960 961 /** 962 * Keep track of the number of cached hidden procs, to balance oom adj 963 * distribution between those and empty procs. 964 */ 965 int mNumCachedHiddenProcs = 0; 966 967 /** 968 * Keep track of the number of service processes we last found, to 969 * determine on the next iteration which should be B services. 970 */ 971 int mNumServiceProcs = 0; 972 int mNewNumAServiceProcs = 0; 973 int mNewNumServiceProcs = 0; 974 975 /** 976 * Allow the current computed overall memory level of the system to go down? 977 * This is set to false when we are killing processes for reasons other than 978 * memory management, so that the now smaller process list will not be taken as 979 * an indication that memory is tighter. 980 */ 981 boolean mAllowLowerMemLevel = false; 982 983 /** 984 * The last computed memory level, for holding when we are in a state that 985 * processes are going away for other reasons. 986 */ 987 int mLastMemoryLevel = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 988 989 /** 990 * The last total number of process we have, to determine if changes actually look 991 * like a shrinking number of process due to lower RAM. 992 */ 993 int mLastNumProcesses; 994 995 /** 996 * The uptime of the last time we performed idle maintenance. 997 */ 998 long mLastIdleTime = SystemClock.uptimeMillis(); 999 1000 /** 1001 * Total time spent with RAM that has been added in the past since the last idle time. 1002 */ 1003 long mLowRamTimeSinceLastIdle = 0; 1004 1005 /** 1006 * If RAM is currently low, when that horrible situation started. 1007 */ 1008 long mLowRamStartTime = 0; 1009 1010 /** 1011 * For reporting to battery stats the current top application. 1012 */ 1013 private String mCurResumedPackage = null; 1014 private int mCurResumedUid = -1; 1015 1016 /** 1017 * For reporting to battery stats the apps currently running foreground 1018 * service. The ProcessMap is package/uid tuples; each of these contain 1019 * an array of the currently foreground processes. 1020 */ 1021 final ProcessMap<ArrayList<ProcessRecord>> mForegroundPackages 1022 = new ProcessMap<ArrayList<ProcessRecord>>(); 1023 1024 /** 1025 * This is set if we had to do a delayed dexopt of an app before launching 1026 * it, to increase the ANR timeouts in that case. 1027 */ 1028 boolean mDidDexOpt; 1029 1030 /** 1031 * Set if the systemServer made a call to enterSafeMode. 1032 */ 1033 boolean mSafeMode; 1034 1035 String mDebugApp = null; 1036 boolean mWaitForDebugger = false; 1037 boolean mDebugTransient = false; 1038 String mOrigDebugApp = null; 1039 boolean mOrigWaitForDebugger = false; 1040 boolean mAlwaysFinishActivities = false; 1041 IActivityController mController = null; 1042 String mProfileApp = null; 1043 ProcessRecord mProfileProc = null; 1044 String mProfileFile; 1045 ParcelFileDescriptor mProfileFd; 1046 int mProfileType = 0; 1047 boolean mAutoStopProfiler = false; 1048 String mOpenGlTraceApp = null; 1049 1050 static class ProcessChangeItem { 1051 static final int CHANGE_ACTIVITIES = 1<<0; 1052 static final int CHANGE_PROCESS_STATE = 1<<1; 1053 int changes; 1054 int uid; 1055 int pid; 1056 int processState; 1057 boolean foregroundActivities; 1058 } 1059 1060 final RemoteCallbackList<IProcessObserver> mProcessObservers 1061 = new RemoteCallbackList<IProcessObserver>(); 1062 ProcessChangeItem[] mActiveProcessChanges = new ProcessChangeItem[5]; 1063 1064 final ArrayList<ProcessChangeItem> mPendingProcessChanges 1065 = new ArrayList<ProcessChangeItem>(); 1066 final ArrayList<ProcessChangeItem> mAvailProcessChanges 1067 = new ArrayList<ProcessChangeItem>(); 1068 1069 /** 1070 * Runtime CPU use collection thread. This object's lock is used to 1071 * protect all related state. 1072 */ 1073 final Thread mProcessCpuThread; 1074 1075 /** 1076 * Used to collect process stats when showing not responding dialog. 1077 * Protected by mProcessCpuThread. 1078 */ 1079 final ProcessCpuTracker mProcessCpuTracker = new ProcessCpuTracker( 1080 MONITOR_THREAD_CPU_USAGE); 1081 final AtomicLong mLastCpuTime = new AtomicLong(0); 1082 final AtomicBoolean mProcessCpuMutexFree = new AtomicBoolean(true); 1083 1084 long mLastWriteTime = 0; 1085 1086 /** 1087 * Used to retain an update lock when the foreground activity is in 1088 * immersive mode. 1089 */ 1090 final UpdateLock mUpdateLock = new UpdateLock("immersive"); 1091 1092 /** 1093 * Set to true after the system has finished booting. 1094 */ 1095 boolean mBooted = false; 1096 1097 int mProcessLimit = ProcessList.MAX_CACHED_APPS; 1098 int mProcessLimitOverride = -1; 1099 1100 WindowManagerService mWindowManager; 1101 1102 final ActivityThread mSystemThread; 1103 1104 int mCurrentUserId = 0; 1105 int[] mCurrentProfileIds = new int[] {UserHandle.USER_OWNER}; // Accessed by ActivityStack 1106 1107 /** 1108 * Mapping from each known user ID to the profile group ID it is associated with. 1109 */ 1110 SparseIntArray mUserProfileGroupIdsSelfLocked = new SparseIntArray(); 1111 1112 private UserManagerService mUserManager; 1113 1114 private final class AppDeathRecipient implements IBinder.DeathRecipient { 1115 final ProcessRecord mApp; 1116 final int mPid; 1117 final IApplicationThread mAppThread; 1118 1119 AppDeathRecipient(ProcessRecord app, int pid, 1120 IApplicationThread thread) { 1121 if (localLOGV) Slog.v( 1122 TAG, "New death recipient " + this 1123 + " for thread " + thread.asBinder()); 1124 mApp = app; 1125 mPid = pid; 1126 mAppThread = thread; 1127 } 1128 1129 @Override 1130 public void binderDied() { 1131 if (localLOGV) Slog.v( 1132 TAG, "Death received in " + this 1133 + " for thread " + mAppThread.asBinder()); 1134 synchronized(ActivityManagerService.this) { 1135 appDiedLocked(mApp, mPid, mAppThread); 1136 } 1137 } 1138 } 1139 1140 static final int SHOW_ERROR_MSG = 1; 1141 static final int SHOW_NOT_RESPONDING_MSG = 2; 1142 static final int SHOW_FACTORY_ERROR_MSG = 3; 1143 static final int UPDATE_CONFIGURATION_MSG = 4; 1144 static final int GC_BACKGROUND_PROCESSES_MSG = 5; 1145 static final int WAIT_FOR_DEBUGGER_MSG = 6; 1146 static final int SERVICE_TIMEOUT_MSG = 12; 1147 static final int UPDATE_TIME_ZONE = 13; 1148 static final int SHOW_UID_ERROR_MSG = 14; 1149 static final int IM_FEELING_LUCKY_MSG = 15; 1150 static final int PROC_START_TIMEOUT_MSG = 20; 1151 static final int DO_PENDING_ACTIVITY_LAUNCHES_MSG = 21; 1152 static final int KILL_APPLICATION_MSG = 22; 1153 static final int FINALIZE_PENDING_INTENT_MSG = 23; 1154 static final int POST_HEAVY_NOTIFICATION_MSG = 24; 1155 static final int CANCEL_HEAVY_NOTIFICATION_MSG = 25; 1156 static final int SHOW_STRICT_MODE_VIOLATION_MSG = 26; 1157 static final int CHECK_EXCESSIVE_WAKE_LOCKS_MSG = 27; 1158 static final int CLEAR_DNS_CACHE_MSG = 28; 1159 static final int UPDATE_HTTP_PROXY_MSG = 29; 1160 static final int SHOW_COMPAT_MODE_DIALOG_MSG = 30; 1161 static final int DISPATCH_PROCESSES_CHANGED = 31; 1162 static final int DISPATCH_PROCESS_DIED = 32; 1163 static final int REPORT_MEM_USAGE_MSG = 33; 1164 static final int REPORT_USER_SWITCH_MSG = 34; 1165 static final int CONTINUE_USER_SWITCH_MSG = 35; 1166 static final int USER_SWITCH_TIMEOUT_MSG = 36; 1167 static final int IMMERSIVE_MODE_LOCK_MSG = 37; 1168 static final int PERSIST_URI_GRANTS_MSG = 38; 1169 static final int REQUEST_ALL_PSS_MSG = 39; 1170 static final int START_PROFILES_MSG = 40; 1171 static final int UPDATE_TIME = 41; 1172 static final int SYSTEM_USER_START_MSG = 42; 1173 static final int SYSTEM_USER_CURRENT_MSG = 43; 1174 1175 static final int FIRST_ACTIVITY_STACK_MSG = 100; 1176 static final int FIRST_BROADCAST_QUEUE_MSG = 200; 1177 static final int FIRST_COMPAT_MODE_MSG = 300; 1178 static final int FIRST_SUPERVISOR_STACK_MSG = 100; 1179 1180 AlertDialog mUidAlert; 1181 CompatModeDialog mCompatModeDialog; 1182 long mLastMemUsageReportTime = 0; 1183 1184 private LockToAppRequestDialog mLockToAppRequest; 1185 1186 /** 1187 * Flag whether the current user is a "monkey", i.e. whether 1188 * the UI is driven by a UI automation tool. 1189 */ 1190 private boolean mUserIsMonkey; 1191 1192 /** Flag whether the device has a recents UI */ 1193 final boolean mHasRecents; 1194 1195 final ServiceThread mHandlerThread; 1196 final MainHandler mHandler; 1197 1198 final class MainHandler extends Handler { 1199 public MainHandler(Looper looper) { 1200 super(looper, null, true); 1201 } 1202 1203 @Override 1204 public void handleMessage(Message msg) { 1205 switch (msg.what) { 1206 case SHOW_ERROR_MSG: { 1207 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1208 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 1209 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 1210 synchronized (ActivityManagerService.this) { 1211 ProcessRecord proc = (ProcessRecord)data.get("app"); 1212 AppErrorResult res = (AppErrorResult) data.get("result"); 1213 if (proc != null && proc.crashDialog != null) { 1214 Slog.e(TAG, "App already has crash dialog: " + proc); 1215 if (res != null) { 1216 res.set(0); 1217 } 1218 return; 1219 } 1220 if (!showBackground && UserHandle.getAppId(proc.uid) 1221 >= Process.FIRST_APPLICATION_UID && proc.userId != mCurrentUserId 1222 && proc.pid != MY_PID) { 1223 Slog.w(TAG, "Skipping crash dialog of " + proc + ": background"); 1224 if (res != null) { 1225 res.set(0); 1226 } 1227 return; 1228 } 1229 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1230 Dialog d = new AppErrorDialog(mContext, 1231 ActivityManagerService.this, res, proc); 1232 d.show(); 1233 proc.crashDialog = d; 1234 } else { 1235 // The device is asleep, so just pretend that the user 1236 // saw a crash dialog and hit "force quit". 1237 if (res != null) { 1238 res.set(0); 1239 } 1240 } 1241 } 1242 1243 ensureBootCompleted(); 1244 } break; 1245 case SHOW_NOT_RESPONDING_MSG: { 1246 synchronized (ActivityManagerService.this) { 1247 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1248 ProcessRecord proc = (ProcessRecord)data.get("app"); 1249 if (proc != null && proc.anrDialog != null) { 1250 Slog.e(TAG, "App already has anr dialog: " + proc); 1251 return; 1252 } 1253 1254 Intent intent = new Intent("android.intent.action.ANR"); 1255 if (!mProcessesReady) { 1256 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 1257 | Intent.FLAG_RECEIVER_FOREGROUND); 1258 } 1259 broadcastIntentLocked(null, null, intent, 1260 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 1261 false, false, MY_PID, Process.SYSTEM_UID, 0 /* TODO: Verify */); 1262 1263 if (mShowDialogs) { 1264 Dialog d = new AppNotRespondingDialog(ActivityManagerService.this, 1265 mContext, proc, (ActivityRecord)data.get("activity"), 1266 msg.arg1 != 0); 1267 d.show(); 1268 proc.anrDialog = d; 1269 } else { 1270 // Just kill the app if there is no dialog to be shown. 1271 killAppAtUsersRequest(proc, null); 1272 } 1273 } 1274 1275 ensureBootCompleted(); 1276 } break; 1277 case SHOW_STRICT_MODE_VIOLATION_MSG: { 1278 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1279 synchronized (ActivityManagerService.this) { 1280 ProcessRecord proc = (ProcessRecord) data.get("app"); 1281 if (proc == null) { 1282 Slog.e(TAG, "App not found when showing strict mode dialog."); 1283 break; 1284 } 1285 if (proc.crashDialog != null) { 1286 Slog.e(TAG, "App already has strict mode dialog: " + proc); 1287 return; 1288 } 1289 AppErrorResult res = (AppErrorResult) data.get("result"); 1290 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1291 Dialog d = new StrictModeViolationDialog(mContext, 1292 ActivityManagerService.this, res, proc); 1293 d.show(); 1294 proc.crashDialog = d; 1295 } else { 1296 // The device is asleep, so just pretend that the user 1297 // saw a crash dialog and hit "force quit". 1298 res.set(0); 1299 } 1300 } 1301 ensureBootCompleted(); 1302 } break; 1303 case SHOW_FACTORY_ERROR_MSG: { 1304 Dialog d = new FactoryErrorDialog( 1305 mContext, msg.getData().getCharSequence("msg")); 1306 d.show(); 1307 ensureBootCompleted(); 1308 } break; 1309 case UPDATE_CONFIGURATION_MSG: { 1310 final ContentResolver resolver = mContext.getContentResolver(); 1311 Settings.System.putConfiguration(resolver, (Configuration)msg.obj); 1312 } break; 1313 case GC_BACKGROUND_PROCESSES_MSG: { 1314 synchronized (ActivityManagerService.this) { 1315 performAppGcsIfAppropriateLocked(); 1316 } 1317 } break; 1318 case WAIT_FOR_DEBUGGER_MSG: { 1319 synchronized (ActivityManagerService.this) { 1320 ProcessRecord app = (ProcessRecord)msg.obj; 1321 if (msg.arg1 != 0) { 1322 if (!app.waitedForDebugger) { 1323 Dialog d = new AppWaitingForDebuggerDialog( 1324 ActivityManagerService.this, 1325 mContext, app); 1326 app.waitDialog = d; 1327 app.waitedForDebugger = true; 1328 d.show(); 1329 } 1330 } else { 1331 if (app.waitDialog != null) { 1332 app.waitDialog.dismiss(); 1333 app.waitDialog = null; 1334 } 1335 } 1336 } 1337 } break; 1338 case SERVICE_TIMEOUT_MSG: { 1339 if (mDidDexOpt) { 1340 mDidDexOpt = false; 1341 Message nmsg = mHandler.obtainMessage(SERVICE_TIMEOUT_MSG); 1342 nmsg.obj = msg.obj; 1343 mHandler.sendMessageDelayed(nmsg, ActiveServices.SERVICE_TIMEOUT); 1344 return; 1345 } 1346 mServices.serviceTimeout((ProcessRecord)msg.obj); 1347 } break; 1348 case UPDATE_TIME_ZONE: { 1349 synchronized (ActivityManagerService.this) { 1350 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1351 ProcessRecord r = mLruProcesses.get(i); 1352 if (r.thread != null) { 1353 try { 1354 r.thread.updateTimeZone(); 1355 } catch (RemoteException ex) { 1356 Slog.w(TAG, "Failed to update time zone for: " + r.info.processName); 1357 } 1358 } 1359 } 1360 } 1361 } break; 1362 case CLEAR_DNS_CACHE_MSG: { 1363 synchronized (ActivityManagerService.this) { 1364 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1365 ProcessRecord r = mLruProcesses.get(i); 1366 if (r.thread != null) { 1367 try { 1368 r.thread.clearDnsCache(); 1369 } catch (RemoteException ex) { 1370 Slog.w(TAG, "Failed to clear dns cache for: " + r.info.processName); 1371 } 1372 } 1373 } 1374 } 1375 } break; 1376 case UPDATE_HTTP_PROXY_MSG: { 1377 ProxyInfo proxy = (ProxyInfo)msg.obj; 1378 String host = ""; 1379 String port = ""; 1380 String exclList = ""; 1381 Uri pacFileUrl = Uri.EMPTY; 1382 if (proxy != null) { 1383 host = proxy.getHost(); 1384 port = Integer.toString(proxy.getPort()); 1385 exclList = proxy.getExclusionListAsString(); 1386 pacFileUrl = proxy.getPacFileUrl(); 1387 } 1388 synchronized (ActivityManagerService.this) { 1389 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1390 ProcessRecord r = mLruProcesses.get(i); 1391 if (r.thread != null) { 1392 try { 1393 r.thread.setHttpProxy(host, port, exclList, pacFileUrl); 1394 } catch (RemoteException ex) { 1395 Slog.w(TAG, "Failed to update http proxy for: " + 1396 r.info.processName); 1397 } 1398 } 1399 } 1400 } 1401 } break; 1402 case SHOW_UID_ERROR_MSG: { 1403 String title = "System UIDs Inconsistent"; 1404 String text = "UIDs on the system are inconsistent, you need to wipe your" 1405 + " data partition or your device will be unstable."; 1406 Log.e(TAG, title + ": " + text); 1407 if (mShowDialogs) { 1408 // XXX This is a temporary dialog, no need to localize. 1409 AlertDialog d = new BaseErrorDialog(mContext); 1410 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 1411 d.setCancelable(false); 1412 d.setTitle(title); 1413 d.setMessage(text); 1414 d.setButton(DialogInterface.BUTTON_POSITIVE, "I'm Feeling Lucky", 1415 mHandler.obtainMessage(IM_FEELING_LUCKY_MSG)); 1416 mUidAlert = d; 1417 d.show(); 1418 } 1419 } break; 1420 case IM_FEELING_LUCKY_MSG: { 1421 if (mUidAlert != null) { 1422 mUidAlert.dismiss(); 1423 mUidAlert = null; 1424 } 1425 } break; 1426 case PROC_START_TIMEOUT_MSG: { 1427 if (mDidDexOpt) { 1428 mDidDexOpt = false; 1429 Message nmsg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 1430 nmsg.obj = msg.obj; 1431 mHandler.sendMessageDelayed(nmsg, PROC_START_TIMEOUT); 1432 return; 1433 } 1434 ProcessRecord app = (ProcessRecord)msg.obj; 1435 synchronized (ActivityManagerService.this) { 1436 processStartTimedOutLocked(app); 1437 } 1438 } break; 1439 case DO_PENDING_ACTIVITY_LAUNCHES_MSG: { 1440 synchronized (ActivityManagerService.this) { 1441 doPendingActivityLaunchesLocked(true); 1442 } 1443 } break; 1444 case KILL_APPLICATION_MSG: { 1445 synchronized (ActivityManagerService.this) { 1446 int appid = msg.arg1; 1447 boolean restart = (msg.arg2 == 1); 1448 Bundle bundle = (Bundle)msg.obj; 1449 String pkg = bundle.getString("pkg"); 1450 String reason = bundle.getString("reason"); 1451 forceStopPackageLocked(pkg, appid, restart, false, true, false, 1452 false, UserHandle.USER_ALL, reason); 1453 } 1454 } break; 1455 case FINALIZE_PENDING_INTENT_MSG: { 1456 ((PendingIntentRecord)msg.obj).completeFinalize(); 1457 } break; 1458 case POST_HEAVY_NOTIFICATION_MSG: { 1459 INotificationManager inm = NotificationManager.getService(); 1460 if (inm == null) { 1461 return; 1462 } 1463 1464 ActivityRecord root = (ActivityRecord)msg.obj; 1465 ProcessRecord process = root.app; 1466 if (process == null) { 1467 return; 1468 } 1469 1470 try { 1471 Context context = mContext.createPackageContext(process.info.packageName, 0); 1472 String text = mContext.getString(R.string.heavy_weight_notification, 1473 context.getApplicationInfo().loadLabel(context.getPackageManager())); 1474 Notification notification = new Notification(); 1475 notification.icon = com.android.internal.R.drawable.stat_sys_adb; //context.getApplicationInfo().icon; 1476 notification.when = 0; 1477 notification.flags = Notification.FLAG_ONGOING_EVENT; 1478 notification.tickerText = text; 1479 notification.defaults = 0; // please be quiet 1480 notification.sound = null; 1481 notification.vibrate = null; 1482 notification.setLatestEventInfo(context, text, 1483 mContext.getText(R.string.heavy_weight_notification_detail), 1484 PendingIntent.getActivityAsUser(mContext, 0, root.intent, 1485 PendingIntent.FLAG_CANCEL_CURRENT, null, 1486 new UserHandle(root.userId))); 1487 1488 try { 1489 int[] outId = new int[1]; 1490 inm.enqueueNotificationWithTag("android", "android", null, 1491 R.string.heavy_weight_notification, 1492 notification, outId, root.userId); 1493 } catch (RuntimeException e) { 1494 Slog.w(ActivityManagerService.TAG, 1495 "Error showing notification for heavy-weight app", e); 1496 } catch (RemoteException e) { 1497 } 1498 } catch (NameNotFoundException e) { 1499 Slog.w(TAG, "Unable to create context for heavy notification", e); 1500 } 1501 } break; 1502 case CANCEL_HEAVY_NOTIFICATION_MSG: { 1503 INotificationManager inm = NotificationManager.getService(); 1504 if (inm == null) { 1505 return; 1506 } 1507 try { 1508 inm.cancelNotificationWithTag("android", null, 1509 R.string.heavy_weight_notification, msg.arg1); 1510 } catch (RuntimeException e) { 1511 Slog.w(ActivityManagerService.TAG, 1512 "Error canceling notification for service", e); 1513 } catch (RemoteException e) { 1514 } 1515 } break; 1516 case CHECK_EXCESSIVE_WAKE_LOCKS_MSG: { 1517 synchronized (ActivityManagerService.this) { 1518 checkExcessivePowerUsageLocked(true); 1519 removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1520 Message nmsg = obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1521 sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 1522 } 1523 } break; 1524 case SHOW_COMPAT_MODE_DIALOG_MSG: { 1525 synchronized (ActivityManagerService.this) { 1526 ActivityRecord ar = (ActivityRecord)msg.obj; 1527 if (mCompatModeDialog != null) { 1528 if (mCompatModeDialog.mAppInfo.packageName.equals( 1529 ar.info.applicationInfo.packageName)) { 1530 return; 1531 } 1532 mCompatModeDialog.dismiss(); 1533 mCompatModeDialog = null; 1534 } 1535 if (ar != null && false) { 1536 if (mCompatModePackages.getPackageAskCompatModeLocked( 1537 ar.packageName)) { 1538 int mode = mCompatModePackages.computeCompatModeLocked( 1539 ar.info.applicationInfo); 1540 if (mode == ActivityManager.COMPAT_MODE_DISABLED 1541 || mode == ActivityManager.COMPAT_MODE_ENABLED) { 1542 mCompatModeDialog = new CompatModeDialog( 1543 ActivityManagerService.this, mContext, 1544 ar.info.applicationInfo); 1545 mCompatModeDialog.show(); 1546 } 1547 } 1548 } 1549 } 1550 break; 1551 } 1552 case DISPATCH_PROCESSES_CHANGED: { 1553 dispatchProcessesChanged(); 1554 break; 1555 } 1556 case DISPATCH_PROCESS_DIED: { 1557 final int pid = msg.arg1; 1558 final int uid = msg.arg2; 1559 dispatchProcessDied(pid, uid); 1560 break; 1561 } 1562 case REPORT_MEM_USAGE_MSG: { 1563 final ArrayList<ProcessMemInfo> memInfos = (ArrayList<ProcessMemInfo>)msg.obj; 1564 Thread thread = new Thread() { 1565 @Override public void run() { 1566 final SparseArray<ProcessMemInfo> infoMap 1567 = new SparseArray<ProcessMemInfo>(memInfos.size()); 1568 for (int i=0, N=memInfos.size(); i<N; i++) { 1569 ProcessMemInfo mi = memInfos.get(i); 1570 infoMap.put(mi.pid, mi); 1571 } 1572 updateCpuStatsNow(); 1573 synchronized (mProcessCpuThread) { 1574 final int N = mProcessCpuTracker.countStats(); 1575 for (int i=0; i<N; i++) { 1576 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 1577 if (st.vsize > 0) { 1578 long pss = Debug.getPss(st.pid, null); 1579 if (pss > 0) { 1580 if (infoMap.indexOfKey(st.pid) < 0) { 1581 ProcessMemInfo mi = new ProcessMemInfo(st.name, st.pid, 1582 ProcessList.NATIVE_ADJ, -1, "native", null); 1583 mi.pss = pss; 1584 memInfos.add(mi); 1585 } 1586 } 1587 } 1588 } 1589 } 1590 1591 long totalPss = 0; 1592 for (int i=0, N=memInfos.size(); i<N; i++) { 1593 ProcessMemInfo mi = memInfos.get(i); 1594 if (mi.pss == 0) { 1595 mi.pss = Debug.getPss(mi.pid, null); 1596 } 1597 totalPss += mi.pss; 1598 } 1599 Collections.sort(memInfos, new Comparator<ProcessMemInfo>() { 1600 @Override public int compare(ProcessMemInfo lhs, ProcessMemInfo rhs) { 1601 if (lhs.oomAdj != rhs.oomAdj) { 1602 return lhs.oomAdj < rhs.oomAdj ? -1 : 1; 1603 } 1604 if (lhs.pss != rhs.pss) { 1605 return lhs.pss < rhs.pss ? 1 : -1; 1606 } 1607 return 0; 1608 } 1609 }); 1610 1611 StringBuilder tag = new StringBuilder(128); 1612 StringBuilder stack = new StringBuilder(128); 1613 tag.append("Low on memory -- "); 1614 appendMemBucket(tag, totalPss, "total", false); 1615 appendMemBucket(stack, totalPss, "total", true); 1616 1617 StringBuilder logBuilder = new StringBuilder(1024); 1618 logBuilder.append("Low on memory:\n"); 1619 1620 boolean firstLine = true; 1621 int lastOomAdj = Integer.MIN_VALUE; 1622 for (int i=0, N=memInfos.size(); i<N; i++) { 1623 ProcessMemInfo mi = memInfos.get(i); 1624 1625 if (mi.oomAdj != ProcessList.NATIVE_ADJ 1626 && (mi.oomAdj < ProcessList.SERVICE_ADJ 1627 || mi.oomAdj == ProcessList.HOME_APP_ADJ 1628 || mi.oomAdj == ProcessList.PREVIOUS_APP_ADJ)) { 1629 if (lastOomAdj != mi.oomAdj) { 1630 lastOomAdj = mi.oomAdj; 1631 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1632 tag.append(" / "); 1633 } 1634 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ) { 1635 if (firstLine) { 1636 stack.append(":"); 1637 firstLine = false; 1638 } 1639 stack.append("\n\t at "); 1640 } else { 1641 stack.append("$"); 1642 } 1643 } else { 1644 tag.append(" "); 1645 stack.append("$"); 1646 } 1647 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1648 appendMemBucket(tag, mi.pss, mi.name, false); 1649 } 1650 appendMemBucket(stack, mi.pss, mi.name, true); 1651 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ 1652 && ((i+1) >= N || memInfos.get(i+1).oomAdj != lastOomAdj)) { 1653 stack.append("("); 1654 for (int k=0; k<DUMP_MEM_OOM_ADJ.length; k++) { 1655 if (DUMP_MEM_OOM_ADJ[k] == mi.oomAdj) { 1656 stack.append(DUMP_MEM_OOM_LABEL[k]); 1657 stack.append(":"); 1658 stack.append(DUMP_MEM_OOM_ADJ[k]); 1659 } 1660 } 1661 stack.append(")"); 1662 } 1663 } 1664 1665 logBuilder.append(" "); 1666 logBuilder.append(ProcessList.makeOomAdjString(mi.oomAdj)); 1667 logBuilder.append(' '); 1668 logBuilder.append(ProcessList.makeProcStateString(mi.procState)); 1669 logBuilder.append(' '); 1670 ProcessList.appendRamKb(logBuilder, mi.pss); 1671 logBuilder.append(" kB: "); 1672 logBuilder.append(mi.name); 1673 logBuilder.append(" ("); 1674 logBuilder.append(mi.pid); 1675 logBuilder.append(") "); 1676 logBuilder.append(mi.adjType); 1677 logBuilder.append('\n'); 1678 if (mi.adjReason != null) { 1679 logBuilder.append(" "); 1680 logBuilder.append(mi.adjReason); 1681 logBuilder.append('\n'); 1682 } 1683 } 1684 1685 logBuilder.append(" "); 1686 ProcessList.appendRamKb(logBuilder, totalPss); 1687 logBuilder.append(" kB: TOTAL\n"); 1688 1689 long[] infos = new long[Debug.MEMINFO_COUNT]; 1690 Debug.getMemInfo(infos); 1691 logBuilder.append(" MemInfo: "); 1692 logBuilder.append(infos[Debug.MEMINFO_SLAB]).append(" kB slab, "); 1693 logBuilder.append(infos[Debug.MEMINFO_SHMEM]).append(" kB shmem, "); 1694 logBuilder.append(infos[Debug.MEMINFO_BUFFERS]).append(" kB buffers, "); 1695 logBuilder.append(infos[Debug.MEMINFO_CACHED]).append(" kB cached, "); 1696 logBuilder.append(infos[Debug.MEMINFO_FREE]).append(" kB free\n"); 1697 if (infos[Debug.MEMINFO_ZRAM_TOTAL] != 0) { 1698 logBuilder.append(" ZRAM: "); 1699 logBuilder.append(infos[Debug.MEMINFO_ZRAM_TOTAL]); 1700 logBuilder.append(" kB RAM, "); 1701 logBuilder.append(infos[Debug.MEMINFO_SWAP_TOTAL]); 1702 logBuilder.append(" kB swap total, "); 1703 logBuilder.append(infos[Debug.MEMINFO_SWAP_FREE]); 1704 logBuilder.append(" kB swap free\n"); 1705 } 1706 Slog.i(TAG, logBuilder.toString()); 1707 1708 StringBuilder dropBuilder = new StringBuilder(1024); 1709 /* 1710 StringWriter oomSw = new StringWriter(); 1711 PrintWriter oomPw = new FastPrintWriter(oomSw, false, 256); 1712 StringWriter catSw = new StringWriter(); 1713 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1714 String[] emptyArgs = new String[] { }; 1715 dumpApplicationMemoryUsage(null, oomPw, " ", emptyArgs, true, catPw); 1716 oomPw.flush(); 1717 String oomString = oomSw.toString(); 1718 */ 1719 dropBuilder.append(stack); 1720 dropBuilder.append('\n'); 1721 dropBuilder.append('\n'); 1722 dropBuilder.append(logBuilder); 1723 dropBuilder.append('\n'); 1724 /* 1725 dropBuilder.append(oomString); 1726 dropBuilder.append('\n'); 1727 */ 1728 StringWriter catSw = new StringWriter(); 1729 synchronized (ActivityManagerService.this) { 1730 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1731 String[] emptyArgs = new String[] { }; 1732 catPw.println(); 1733 dumpProcessesLocked(null, catPw, emptyArgs, 0, false, null); 1734 catPw.println(); 1735 mServices.dumpServicesLocked(null, catPw, emptyArgs, 0, 1736 false, false, null); 1737 catPw.println(); 1738 dumpActivitiesLocked(null, catPw, emptyArgs, 0, false, false, null); 1739 catPw.flush(); 1740 } 1741 dropBuilder.append(catSw.toString()); 1742 addErrorToDropBox("lowmem", null, "system_server", null, 1743 null, tag.toString(), dropBuilder.toString(), null, null); 1744 //Slog.i(TAG, "Sent to dropbox:"); 1745 //Slog.i(TAG, dropBuilder.toString()); 1746 synchronized (ActivityManagerService.this) { 1747 long now = SystemClock.uptimeMillis(); 1748 if (mLastMemUsageReportTime < now) { 1749 mLastMemUsageReportTime = now; 1750 } 1751 } 1752 } 1753 }; 1754 thread.start(); 1755 break; 1756 } 1757 case REPORT_USER_SWITCH_MSG: { 1758 dispatchUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1759 break; 1760 } 1761 case CONTINUE_USER_SWITCH_MSG: { 1762 continueUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1763 break; 1764 } 1765 case USER_SWITCH_TIMEOUT_MSG: { 1766 timeoutUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1767 break; 1768 } 1769 case IMMERSIVE_MODE_LOCK_MSG: { 1770 final boolean nextState = (msg.arg1 != 0); 1771 if (mUpdateLock.isHeld() != nextState) { 1772 if (DEBUG_IMMERSIVE) { 1773 final ActivityRecord r = (ActivityRecord) msg.obj; 1774 Slog.d(TAG, "Applying new update lock state '" + nextState + "' for " + r); 1775 } 1776 if (nextState) { 1777 mUpdateLock.acquire(); 1778 } else { 1779 mUpdateLock.release(); 1780 } 1781 } 1782 break; 1783 } 1784 case PERSIST_URI_GRANTS_MSG: { 1785 writeGrantedUriPermissions(); 1786 break; 1787 } 1788 case REQUEST_ALL_PSS_MSG: { 1789 requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, false); 1790 break; 1791 } 1792 case START_PROFILES_MSG: { 1793 synchronized (ActivityManagerService.this) { 1794 startProfilesLocked(); 1795 } 1796 break; 1797 } 1798 case UPDATE_TIME: { 1799 synchronized (ActivityManagerService.this) { 1800 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1801 ProcessRecord r = mLruProcesses.get(i); 1802 if (r.thread != null) { 1803 try { 1804 r.thread.updateTimePrefs(msg.arg1 == 0 ? false : true); 1805 } catch (RemoteException ex) { 1806 Slog.w(TAG, "Failed to update preferences for: " + r.info.processName); 1807 } 1808 } 1809 } 1810 } 1811 break; 1812 } 1813 case SYSTEM_USER_START_MSG: { 1814 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 1815 Integer.toString(msg.arg1), msg.arg1); 1816 mSystemServiceManager.startUser(msg.arg1); 1817 break; 1818 } 1819 case SYSTEM_USER_CURRENT_MSG: { 1820 mBatteryStatsService.noteEvent( 1821 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_FINISH, 1822 Integer.toString(msg.arg2), msg.arg2); 1823 mBatteryStatsService.noteEvent( 1824 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 1825 Integer.toString(msg.arg1), msg.arg1); 1826 mSystemServiceManager.switchUser(msg.arg1); 1827 break; 1828 } 1829 } 1830 } 1831 }; 1832 1833 static final int COLLECT_PSS_BG_MSG = 1; 1834 1835 final Handler mBgHandler = new Handler(BackgroundThread.getHandler().getLooper()) { 1836 @Override 1837 public void handleMessage(Message msg) { 1838 switch (msg.what) { 1839 case COLLECT_PSS_BG_MSG: { 1840 long start = SystemClock.uptimeMillis(); 1841 MemInfoReader memInfo = null; 1842 synchronized (ActivityManagerService.this) { 1843 if (mFullPssPending) { 1844 mFullPssPending = false; 1845 memInfo = new MemInfoReader(); 1846 } 1847 } 1848 if (memInfo != null) { 1849 updateCpuStatsNow(); 1850 long nativeTotalPss = 0; 1851 synchronized (mProcessCpuThread) { 1852 final int N = mProcessCpuTracker.countStats(); 1853 for (int j=0; j<N; j++) { 1854 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(j); 1855 if (st.vsize <= 0 || st.uid >= Process.FIRST_APPLICATION_UID) { 1856 // This is definitely an application process; skip it. 1857 continue; 1858 } 1859 synchronized (mPidsSelfLocked) { 1860 if (mPidsSelfLocked.indexOfKey(st.pid) >= 0) { 1861 // This is one of our own processes; skip it. 1862 continue; 1863 } 1864 } 1865 nativeTotalPss += Debug.getPss(st.pid, null); 1866 } 1867 } 1868 memInfo.readMemInfo(); 1869 synchronized (this) { 1870 if (DEBUG_PSS) Slog.d(TAG, "Collected native and kernel memory in " 1871 + (SystemClock.uptimeMillis()-start) + "ms"); 1872 mProcessStats.addSysMemUsageLocked(memInfo.getCachedSizeKb(), 1873 memInfo.getFreeSizeKb(), memInfo.getZramTotalSizeKb(), 1874 memInfo.getBuffersSizeKb()+memInfo.getShmemSizeKb() 1875 +memInfo.getSlabSizeKb(), 1876 nativeTotalPss); 1877 } 1878 } 1879 1880 int i=0, num=0; 1881 long[] tmp = new long[1]; 1882 do { 1883 ProcessRecord proc; 1884 int procState; 1885 int pid; 1886 synchronized (ActivityManagerService.this) { 1887 if (i >= mPendingPssProcesses.size()) { 1888 if (DEBUG_PSS) Slog.d(TAG, "Collected PSS of " + num + " of " + i 1889 + " processes in " + (SystemClock.uptimeMillis()-start) + "ms"); 1890 mPendingPssProcesses.clear(); 1891 return; 1892 } 1893 proc = mPendingPssProcesses.get(i); 1894 procState = proc.pssProcState; 1895 if (proc.thread != null && procState == proc.setProcState) { 1896 pid = proc.pid; 1897 } else { 1898 proc = null; 1899 pid = 0; 1900 } 1901 i++; 1902 } 1903 if (proc != null) { 1904 long pss = Debug.getPss(pid, tmp); 1905 synchronized (ActivityManagerService.this) { 1906 if (proc.thread != null && proc.setProcState == procState 1907 && proc.pid == pid) { 1908 num++; 1909 proc.lastPssTime = SystemClock.uptimeMillis(); 1910 proc.baseProcessTracker.addPss(pss, tmp[0], true, proc.pkgList); 1911 if (DEBUG_PSS) Slog.d(TAG, "PSS of " + proc.toShortString() 1912 + ": " + pss + " lastPss=" + proc.lastPss 1913 + " state=" + ProcessList.makeProcStateString(procState)); 1914 if (proc.initialIdlePss == 0) { 1915 proc.initialIdlePss = pss; 1916 } 1917 proc.lastPss = pss; 1918 if (procState >= ActivityManager.PROCESS_STATE_HOME) { 1919 proc.lastCachedPss = pss; 1920 } 1921 } 1922 } 1923 } 1924 } while (true); 1925 } 1926 } 1927 } 1928 }; 1929 1930 /** 1931 * Monitor for package changes and update our internal state. 1932 */ 1933 private final PackageMonitor mPackageMonitor = new PackageMonitor() { 1934 @Override 1935 public void onPackageRemoved(String packageName, int uid) { 1936 // Remove all tasks with activities in the specified package from the list of recent tasks 1937 synchronized (ActivityManagerService.this) { 1938 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 1939 TaskRecord tr = mRecentTasks.get(i); 1940 ComponentName cn = tr.intent.getComponent(); 1941 if (cn != null && cn.getPackageName().equals(packageName)) { 1942 // If the package name matches, remove the task and kill the process 1943 removeTaskByIdLocked(tr.taskId, ActivityManager.REMOVE_TASK_KILL_PROCESS); 1944 } 1945 } 1946 } 1947 } 1948 1949 @Override 1950 public boolean onPackageChanged(String packageName, int uid, String[] components) { 1951 onPackageModified(packageName); 1952 return true; 1953 } 1954 1955 @Override 1956 public void onPackageModified(String packageName) { 1957 final PackageManager pm = mContext.getPackageManager(); 1958 final ArrayList<Pair<Intent, Integer>> recentTaskIntents = 1959 new ArrayList<Pair<Intent, Integer>>(); 1960 final ArrayList<Integer> tasksToRemove = new ArrayList<Integer>(); 1961 // Copy the list of recent tasks so that we don't hold onto the lock on 1962 // ActivityManagerService for long periods while checking if components exist. 1963 synchronized (ActivityManagerService.this) { 1964 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 1965 TaskRecord tr = mRecentTasks.get(i); 1966 recentTaskIntents.add(new Pair<Intent, Integer>(tr.intent, tr.taskId)); 1967 } 1968 } 1969 // Check the recent tasks and filter out all tasks with components that no longer exist. 1970 Intent tmpI = new Intent(); 1971 for (int i = recentTaskIntents.size() - 1; i >= 0; i--) { 1972 Pair<Intent, Integer> p = recentTaskIntents.get(i); 1973 ComponentName cn = p.first.getComponent(); 1974 if (cn != null && cn.getPackageName().equals(packageName)) { 1975 try { 1976 // Add the task to the list to remove if the component no longer exists 1977 tmpI.setComponent(cn); 1978 if (pm.queryIntentActivities(tmpI, PackageManager.MATCH_DEFAULT_ONLY).isEmpty()) { 1979 tasksToRemove.add(p.second); 1980 } 1981 } catch (Exception e) {} 1982 } 1983 } 1984 // Prune all the tasks with removed components from the list of recent tasks 1985 synchronized (ActivityManagerService.this) { 1986 for (int i = tasksToRemove.size() - 1; i >= 0; i--) { 1987 // Remove the task but don't kill the process (since other components in that 1988 // package may still be running and in the background) 1989 removeTaskByIdLocked(tasksToRemove.get(i), 0); 1990 } 1991 } 1992 } 1993 1994 @Override 1995 public boolean onHandleForceStop(Intent intent, String[] packages, int uid, boolean doit) { 1996 // Force stop the specified packages 1997 if (packages != null) { 1998 for (String pkg : packages) { 1999 synchronized (ActivityManagerService.this) { 2000 if (forceStopPackageLocked(pkg, -1, false, false, false, false, false, 0, 2001 "finished booting")) { 2002 return true; 2003 } 2004 } 2005 } 2006 } 2007 return false; 2008 } 2009 }; 2010 2011 public void setSystemProcess() { 2012 try { 2013 ServiceManager.addService(Context.ACTIVITY_SERVICE, this, true); 2014 ServiceManager.addService(ProcessStats.SERVICE_NAME, mProcessStats); 2015 ServiceManager.addService("meminfo", new MemBinder(this)); 2016 ServiceManager.addService("gfxinfo", new GraphicsBinder(this)); 2017 ServiceManager.addService("dbinfo", new DbBinder(this)); 2018 if (MONITOR_CPU_USAGE) { 2019 ServiceManager.addService("cpuinfo", new CpuBinder(this)); 2020 } 2021 ServiceManager.addService("permission", new PermissionController(this)); 2022 2023 ApplicationInfo info = mContext.getPackageManager().getApplicationInfo( 2024 "android", STOCK_PM_FLAGS); 2025 mSystemThread.installSystemApplicationInfo(info); 2026 2027 synchronized (this) { 2028 ProcessRecord app = newProcessRecordLocked(info, info.processName, false); 2029 app.persistent = true; 2030 app.pid = MY_PID; 2031 app.maxAdj = ProcessList.SYSTEM_ADJ; 2032 app.makeActive(mSystemThread.getApplicationThread(), mProcessStats); 2033 mProcessNames.put(app.processName, app.uid, app); 2034 synchronized (mPidsSelfLocked) { 2035 mPidsSelfLocked.put(app.pid, app); 2036 } 2037 updateLruProcessLocked(app, false, null); 2038 updateOomAdjLocked(); 2039 } 2040 } catch (PackageManager.NameNotFoundException e) { 2041 throw new RuntimeException( 2042 "Unable to find android system package", e); 2043 } 2044 } 2045 2046 public void setWindowManager(WindowManagerService wm) { 2047 mWindowManager = wm; 2048 mStackSupervisor.setWindowManager(wm); 2049 } 2050 2051 public void startObservingNativeCrashes() { 2052 final NativeCrashListener ncl = new NativeCrashListener(this); 2053 ncl.start(); 2054 } 2055 2056 public IAppOpsService getAppOpsService() { 2057 return mAppOpsService; 2058 } 2059 2060 static class MemBinder extends Binder { 2061 ActivityManagerService mActivityManagerService; 2062 MemBinder(ActivityManagerService activityManagerService) { 2063 mActivityManagerService = activityManagerService; 2064 } 2065 2066 @Override 2067 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2068 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2069 != PackageManager.PERMISSION_GRANTED) { 2070 pw.println("Permission Denial: can't dump meminfo from from pid=" 2071 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2072 + " without permission " + android.Manifest.permission.DUMP); 2073 return; 2074 } 2075 2076 mActivityManagerService.dumpApplicationMemoryUsage(fd, pw, " ", args, false, null); 2077 } 2078 } 2079 2080 static class GraphicsBinder extends Binder { 2081 ActivityManagerService mActivityManagerService; 2082 GraphicsBinder(ActivityManagerService activityManagerService) { 2083 mActivityManagerService = activityManagerService; 2084 } 2085 2086 @Override 2087 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2088 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2089 != PackageManager.PERMISSION_GRANTED) { 2090 pw.println("Permission Denial: can't dump gfxinfo from from pid=" 2091 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2092 + " without permission " + android.Manifest.permission.DUMP); 2093 return; 2094 } 2095 2096 mActivityManagerService.dumpGraphicsHardwareUsage(fd, pw, args); 2097 } 2098 } 2099 2100 static class DbBinder extends Binder { 2101 ActivityManagerService mActivityManagerService; 2102 DbBinder(ActivityManagerService activityManagerService) { 2103 mActivityManagerService = activityManagerService; 2104 } 2105 2106 @Override 2107 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2108 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2109 != PackageManager.PERMISSION_GRANTED) { 2110 pw.println("Permission Denial: can't dump dbinfo from from pid=" 2111 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2112 + " without permission " + android.Manifest.permission.DUMP); 2113 return; 2114 } 2115 2116 mActivityManagerService.dumpDbInfo(fd, pw, args); 2117 } 2118 } 2119 2120 static class CpuBinder extends Binder { 2121 ActivityManagerService mActivityManagerService; 2122 CpuBinder(ActivityManagerService activityManagerService) { 2123 mActivityManagerService = activityManagerService; 2124 } 2125 2126 @Override 2127 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2128 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2129 != PackageManager.PERMISSION_GRANTED) { 2130 pw.println("Permission Denial: can't dump cpuinfo from from pid=" 2131 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2132 + " without permission " + android.Manifest.permission.DUMP); 2133 return; 2134 } 2135 2136 synchronized (mActivityManagerService.mProcessCpuThread) { 2137 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentLoad()); 2138 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentState( 2139 SystemClock.uptimeMillis())); 2140 } 2141 } 2142 } 2143 2144 public static final class Lifecycle extends SystemService { 2145 private final ActivityManagerService mService; 2146 2147 public Lifecycle(Context context) { 2148 super(context); 2149 mService = new ActivityManagerService(context); 2150 } 2151 2152 @Override 2153 public void onStart() { 2154 mService.start(); 2155 } 2156 2157 public ActivityManagerService getService() { 2158 return mService; 2159 } 2160 } 2161 2162 // Note: This method is invoked on the main thread but may need to attach various 2163 // handlers to other threads. So take care to be explicit about the looper. 2164 public ActivityManagerService(Context systemContext) { 2165 mContext = systemContext; 2166 mFactoryTest = FactoryTest.getMode(); 2167 mSystemThread = ActivityThread.currentActivityThread(); 2168 2169 Slog.i(TAG, "Memory class: " + ActivityManager.staticGetMemoryClass()); 2170 2171 mHandlerThread = new ServiceThread(TAG, 2172 android.os.Process.THREAD_PRIORITY_FOREGROUND, false /*allowIo*/); 2173 mHandlerThread.start(); 2174 mHandler = new MainHandler(mHandlerThread.getLooper()); 2175 2176 mFgBroadcastQueue = new BroadcastQueue(this, mHandler, 2177 "foreground", BROADCAST_FG_TIMEOUT, false); 2178 mBgBroadcastQueue = new BroadcastQueue(this, mHandler, 2179 "background", BROADCAST_BG_TIMEOUT, true); 2180 mBroadcastQueues[0] = mFgBroadcastQueue; 2181 mBroadcastQueues[1] = mBgBroadcastQueue; 2182 2183 mServices = new ActiveServices(this); 2184 mProviderMap = new ProviderMap(this); 2185 2186 // TODO: Move creation of battery stats service outside of activity manager service. 2187 File dataDir = Environment.getDataDirectory(); 2188 File systemDir = new File(dataDir, "system"); 2189 systemDir.mkdirs(); 2190 mBatteryStatsService = new BatteryStatsService(new File( 2191 systemDir, "batterystats.bin").toString(), mHandler); 2192 mBatteryStatsService.getActiveStatistics().readLocked(); 2193 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2194 mOnBattery = DEBUG_POWER ? true 2195 : mBatteryStatsService.getActiveStatistics().getIsOnBattery(); 2196 mBatteryStatsService.getActiveStatistics().setCallback(this); 2197 2198 mProcessStats = new ProcessStatsService(this, new File(systemDir, "procstats")); 2199 2200 mUsageStatsService = new UsageStatsService(new File(systemDir, "usagestats").toString()); 2201 mAppOpsService = new AppOpsService(new File(systemDir, "appops.xml"), mHandler); 2202 2203 mGrantFile = new AtomicFile(new File(systemDir, "urigrants.xml")); 2204 2205 // User 0 is the first and only user that runs at boot. 2206 mStartedUsers.put(0, new UserStartedState(new UserHandle(0), true)); 2207 mUserLru.add(Integer.valueOf(0)); 2208 updateStartedUserArrayLocked(); 2209 2210 GL_ES_VERSION = SystemProperties.getInt("ro.opengles.version", 2211 ConfigurationInfo.GL_ES_VERSION_UNDEFINED); 2212 2213 mConfiguration.setToDefaults(); 2214 mConfiguration.setLocale(Locale.getDefault()); 2215 2216 mConfigurationSeq = mConfiguration.seq = 1; 2217 mProcessCpuTracker.init(); 2218 2219 mHasRecents = mContext.getResources().getBoolean( 2220 com.android.internal.R.bool.config_hasRecents); 2221 2222 mCompatModePackages = new CompatModePackages(this, systemDir, mHandler); 2223 mIntentFirewall = new IntentFirewall(new IntentFirewallInterface(), mHandler); 2224 mStackSupervisor = new ActivityStackSupervisor(this); 2225 mTaskPersister = new TaskPersister(systemDir, mStackSupervisor); 2226 2227 mProcessCpuThread = new Thread("CpuTracker") { 2228 @Override 2229 public void run() { 2230 while (true) { 2231 try { 2232 try { 2233 synchronized(this) { 2234 final long now = SystemClock.uptimeMillis(); 2235 long nextCpuDelay = (mLastCpuTime.get()+MONITOR_CPU_MAX_TIME)-now; 2236 long nextWriteDelay = (mLastWriteTime+BATTERY_STATS_TIME)-now; 2237 //Slog.i(TAG, "Cpu delay=" + nextCpuDelay 2238 // + ", write delay=" + nextWriteDelay); 2239 if (nextWriteDelay < nextCpuDelay) { 2240 nextCpuDelay = nextWriteDelay; 2241 } 2242 if (nextCpuDelay > 0) { 2243 mProcessCpuMutexFree.set(true); 2244 this.wait(nextCpuDelay); 2245 } 2246 } 2247 } catch (InterruptedException e) { 2248 } 2249 updateCpuStatsNow(); 2250 } catch (Exception e) { 2251 Slog.e(TAG, "Unexpected exception collecting process stats", e); 2252 } 2253 } 2254 } 2255 }; 2256 2257 mLockToAppRequest = new LockToAppRequestDialog(mContext, this); 2258 2259 Watchdog.getInstance().addMonitor(this); 2260 Watchdog.getInstance().addThread(mHandler); 2261 } 2262 2263 public void setSystemServiceManager(SystemServiceManager mgr) { 2264 mSystemServiceManager = mgr; 2265 } 2266 2267 private void start() { 2268 Process.removeAllProcessGroups(); 2269 mProcessCpuThread.start(); 2270 2271 mBatteryStatsService.publish(mContext); 2272 mUsageStatsService.publish(mContext); 2273 mAppOpsService.publish(mContext); 2274 Slog.d("AppOps", "AppOpsService published"); 2275 LocalServices.addService(ActivityManagerInternal.class, new LocalService()); 2276 } 2277 2278 public void initPowerManagement() { 2279 mStackSupervisor.initPowerManagement(); 2280 mBatteryStatsService.initPowerManagement(); 2281 } 2282 2283 @Override 2284 public boolean onTransact(int code, Parcel data, Parcel reply, int flags) 2285 throws RemoteException { 2286 if (code == SYSPROPS_TRANSACTION) { 2287 // We need to tell all apps about the system property change. 2288 ArrayList<IBinder> procs = new ArrayList<IBinder>(); 2289 synchronized(this) { 2290 final int NP = mProcessNames.getMap().size(); 2291 for (int ip=0; ip<NP; ip++) { 2292 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 2293 final int NA = apps.size(); 2294 for (int ia=0; ia<NA; ia++) { 2295 ProcessRecord app = apps.valueAt(ia); 2296 if (app.thread != null) { 2297 procs.add(app.thread.asBinder()); 2298 } 2299 } 2300 } 2301 } 2302 2303 int N = procs.size(); 2304 for (int i=0; i<N; i++) { 2305 Parcel data2 = Parcel.obtain(); 2306 try { 2307 procs.get(i).transact(IBinder.SYSPROPS_TRANSACTION, data2, null, 0); 2308 } catch (RemoteException e) { 2309 } 2310 data2.recycle(); 2311 } 2312 } 2313 try { 2314 return super.onTransact(code, data, reply, flags); 2315 } catch (RuntimeException e) { 2316 // The activity manager only throws security exceptions, so let's 2317 // log all others. 2318 if (!(e instanceof SecurityException)) { 2319 Slog.wtf(TAG, "Activity Manager Crash", e); 2320 } 2321 throw e; 2322 } 2323 } 2324 2325 void updateCpuStats() { 2326 final long now = SystemClock.uptimeMillis(); 2327 if (mLastCpuTime.get() >= now - MONITOR_CPU_MIN_TIME) { 2328 return; 2329 } 2330 if (mProcessCpuMutexFree.compareAndSet(true, false)) { 2331 synchronized (mProcessCpuThread) { 2332 mProcessCpuThread.notify(); 2333 } 2334 } 2335 } 2336 2337 void updateCpuStatsNow() { 2338 synchronized (mProcessCpuThread) { 2339 mProcessCpuMutexFree.set(false); 2340 final long now = SystemClock.uptimeMillis(); 2341 boolean haveNewCpuStats = false; 2342 2343 if (MONITOR_CPU_USAGE && 2344 mLastCpuTime.get() < (now-MONITOR_CPU_MIN_TIME)) { 2345 mLastCpuTime.set(now); 2346 haveNewCpuStats = true; 2347 mProcessCpuTracker.update(); 2348 //Slog.i(TAG, mProcessCpu.printCurrentState()); 2349 //Slog.i(TAG, "Total CPU usage: " 2350 // + mProcessCpu.getTotalCpuPercent() + "%"); 2351 2352 // Slog the cpu usage if the property is set. 2353 if ("true".equals(SystemProperties.get("events.cpu"))) { 2354 int user = mProcessCpuTracker.getLastUserTime(); 2355 int system = mProcessCpuTracker.getLastSystemTime(); 2356 int iowait = mProcessCpuTracker.getLastIoWaitTime(); 2357 int irq = mProcessCpuTracker.getLastIrqTime(); 2358 int softIrq = mProcessCpuTracker.getLastSoftIrqTime(); 2359 int idle = mProcessCpuTracker.getLastIdleTime(); 2360 2361 int total = user + system + iowait + irq + softIrq + idle; 2362 if (total == 0) total = 1; 2363 2364 EventLog.writeEvent(EventLogTags.CPU, 2365 ((user+system+iowait+irq+softIrq) * 100) / total, 2366 (user * 100) / total, 2367 (system * 100) / total, 2368 (iowait * 100) / total, 2369 (irq * 100) / total, 2370 (softIrq * 100) / total); 2371 } 2372 } 2373 2374 long[] cpuSpeedTimes = mProcessCpuTracker.getLastCpuSpeedTimes(); 2375 final BatteryStatsImpl bstats = mBatteryStatsService.getActiveStatistics(); 2376 synchronized(bstats) { 2377 synchronized(mPidsSelfLocked) { 2378 if (haveNewCpuStats) { 2379 if (mOnBattery) { 2380 int perc = bstats.startAddingCpuLocked(); 2381 int totalUTime = 0; 2382 int totalSTime = 0; 2383 final int N = mProcessCpuTracker.countStats(); 2384 for (int i=0; i<N; i++) { 2385 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 2386 if (!st.working) { 2387 continue; 2388 } 2389 ProcessRecord pr = mPidsSelfLocked.get(st.pid); 2390 int otherUTime = (st.rel_utime*perc)/100; 2391 int otherSTime = (st.rel_stime*perc)/100; 2392 totalUTime += otherUTime; 2393 totalSTime += otherSTime; 2394 if (pr != null) { 2395 BatteryStatsImpl.Uid.Proc ps = pr.curProcBatteryStats; 2396 if (ps == null || !ps.isActive()) { 2397 pr.curProcBatteryStats = ps = bstats.getProcessStatsLocked( 2398 pr.info.uid, pr.processName); 2399 } 2400 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2401 st.rel_stime-otherSTime); 2402 ps.addSpeedStepTimes(cpuSpeedTimes); 2403 pr.curCpuTime += (st.rel_utime+st.rel_stime) * 10; 2404 } else { 2405 BatteryStatsImpl.Uid.Proc ps = st.batteryStats; 2406 if (ps == null || !ps.isActive()) { 2407 st.batteryStats = ps = bstats.getProcessStatsLocked( 2408 bstats.mapUid(st.uid), st.name); 2409 } 2410 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2411 st.rel_stime-otherSTime); 2412 ps.addSpeedStepTimes(cpuSpeedTimes); 2413 } 2414 } 2415 bstats.finishAddingCpuLocked(perc, totalUTime, 2416 totalSTime, cpuSpeedTimes); 2417 } 2418 } 2419 } 2420 2421 if (mLastWriteTime < (now-BATTERY_STATS_TIME)) { 2422 mLastWriteTime = now; 2423 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2424 } 2425 } 2426 } 2427 } 2428 2429 @Override 2430 public void batteryNeedsCpuUpdate() { 2431 updateCpuStatsNow(); 2432 } 2433 2434 @Override 2435 public void batteryPowerChanged(boolean onBattery) { 2436 // When plugging in, update the CPU stats first before changing 2437 // the plug state. 2438 updateCpuStatsNow(); 2439 synchronized (this) { 2440 synchronized(mPidsSelfLocked) { 2441 mOnBattery = DEBUG_POWER ? true : onBattery; 2442 } 2443 } 2444 } 2445 2446 /** 2447 * Initialize the application bind args. These are passed to each 2448 * process when the bindApplication() IPC is sent to the process. They're 2449 * lazily setup to make sure the services are running when they're asked for. 2450 */ 2451 private HashMap<String, IBinder> getCommonServicesLocked() { 2452 if (mAppBindArgs == null) { 2453 mAppBindArgs = new HashMap<String, IBinder>(); 2454 2455 // Setup the application init args 2456 mAppBindArgs.put("package", ServiceManager.getService("package")); 2457 mAppBindArgs.put("window", ServiceManager.getService("window")); 2458 mAppBindArgs.put(Context.ALARM_SERVICE, 2459 ServiceManager.getService(Context.ALARM_SERVICE)); 2460 } 2461 return mAppBindArgs; 2462 } 2463 2464 final void setFocusedActivityLocked(ActivityRecord r) { 2465 if (mFocusedActivity != r) { 2466 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedActivityLocked: r=" + r); 2467 mFocusedActivity = r; 2468 if (r.task != null && r.task.voiceInteractor != null) { 2469 startRunningVoiceLocked(); 2470 } else { 2471 finishRunningVoiceLocked(); 2472 } 2473 mStackSupervisor.setFocusedStack(r); 2474 if (r != null) { 2475 mWindowManager.setFocusedApp(r.appToken, true); 2476 } 2477 applyUpdateLockStateLocked(r); 2478 } 2479 } 2480 2481 final void clearFocusedActivity(ActivityRecord r) { 2482 if (mFocusedActivity == r) { 2483 mFocusedActivity = null; 2484 } 2485 } 2486 2487 @Override 2488 public void setFocusedStack(int stackId) { 2489 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedStack: stackId=" + stackId); 2490 synchronized (ActivityManagerService.this) { 2491 ActivityStack stack = mStackSupervisor.getStack(stackId); 2492 if (stack != null) { 2493 ActivityRecord r = stack.topRunningActivityLocked(null); 2494 if (r != null) { 2495 setFocusedActivityLocked(r); 2496 } 2497 } 2498 } 2499 } 2500 2501 @Override 2502 public void notifyActivityDrawn(IBinder token) { 2503 if (DEBUG_VISBILITY) Slog.d(TAG, "notifyActivityDrawn: token=" + token); 2504 synchronized (this) { 2505 ActivityRecord r= mStackSupervisor.isInAnyStackLocked(token); 2506 if (r != null) { 2507 r.task.stack.notifyActivityDrawnLocked(r); 2508 } 2509 } 2510 } 2511 2512 final void applyUpdateLockStateLocked(ActivityRecord r) { 2513 // Modifications to the UpdateLock state are done on our handler, outside 2514 // the activity manager's locks. The new state is determined based on the 2515 // state *now* of the relevant activity record. The object is passed to 2516 // the handler solely for logging detail, not to be consulted/modified. 2517 final boolean nextState = r != null && r.immersive; 2518 mHandler.sendMessage( 2519 mHandler.obtainMessage(IMMERSIVE_MODE_LOCK_MSG, (nextState) ? 1 : 0, 0, r)); 2520 } 2521 2522 final void showAskCompatModeDialogLocked(ActivityRecord r) { 2523 Message msg = Message.obtain(); 2524 msg.what = SHOW_COMPAT_MODE_DIALOG_MSG; 2525 msg.obj = r.task.askedCompatMode ? null : r; 2526 mHandler.sendMessage(msg); 2527 } 2528 2529 private final int updateLruProcessInternalLocked(ProcessRecord app, long now, int index, 2530 String what, Object obj, ProcessRecord srcApp) { 2531 app.lastActivityTime = now; 2532 2533 if (app.activities.size() > 0) { 2534 // Don't want to touch dependent processes that are hosting activities. 2535 return index; 2536 } 2537 2538 int lrui = mLruProcesses.lastIndexOf(app); 2539 if (lrui < 0) { 2540 Slog.wtf(TAG, "Adding dependent process " + app + " not on LRU list: " 2541 + what + " " + obj + " from " + srcApp); 2542 return index; 2543 } 2544 2545 if (lrui >= index) { 2546 // Don't want to cause this to move dependent processes *back* in the 2547 // list as if they were less frequently used. 2548 return index; 2549 } 2550 2551 if (lrui >= mLruProcessActivityStart) { 2552 // Don't want to touch dependent processes that are hosting activities. 2553 return index; 2554 } 2555 2556 mLruProcesses.remove(lrui); 2557 if (index > 0) { 2558 index--; 2559 } 2560 if (DEBUG_LRU) Slog.d(TAG, "Moving dep from " + lrui + " to " + index 2561 + " in LRU list: " + app); 2562 mLruProcesses.add(index, app); 2563 return index; 2564 } 2565 2566 final void removeLruProcessLocked(ProcessRecord app) { 2567 int lrui = mLruProcesses.lastIndexOf(app); 2568 if (lrui >= 0) { 2569 if (lrui <= mLruProcessActivityStart) { 2570 mLruProcessActivityStart--; 2571 } 2572 if (lrui <= mLruProcessServiceStart) { 2573 mLruProcessServiceStart--; 2574 } 2575 mLruProcesses.remove(lrui); 2576 } 2577 } 2578 2579 final void updateLruProcessLocked(ProcessRecord app, boolean activityChange, 2580 ProcessRecord client) { 2581 final boolean hasActivity = app.activities.size() > 0 || app.hasClientActivities 2582 || app.treatLikeActivity; 2583 final boolean hasService = false; // not impl yet. app.services.size() > 0; 2584 if (!activityChange && hasActivity) { 2585 // The process has activities, so we are only allowing activity-based adjustments 2586 // to move it. It should be kept in the front of the list with other 2587 // processes that have activities, and we don't want those to change their 2588 // order except due to activity operations. 2589 return; 2590 } 2591 2592 mLruSeq++; 2593 final long now = SystemClock.uptimeMillis(); 2594 app.lastActivityTime = now; 2595 2596 // First a quick reject: if the app is already at the position we will 2597 // put it, then there is nothing to do. 2598 if (hasActivity) { 2599 final int N = mLruProcesses.size(); 2600 if (N > 0 && mLruProcesses.get(N-1) == app) { 2601 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top activity: " + app); 2602 return; 2603 } 2604 } else { 2605 if (mLruProcessServiceStart > 0 2606 && mLruProcesses.get(mLruProcessServiceStart-1) == app) { 2607 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top other: " + app); 2608 return; 2609 } 2610 } 2611 2612 int lrui = mLruProcesses.lastIndexOf(app); 2613 2614 if (app.persistent && lrui >= 0) { 2615 // We don't care about the position of persistent processes, as long as 2616 // they are in the list. 2617 if (DEBUG_LRU) Slog.d(TAG, "Not moving, persistent: " + app); 2618 return; 2619 } 2620 2621 /* In progress: compute new position first, so we can avoid doing work 2622 if the process is not actually going to move. Not yet working. 2623 int addIndex; 2624 int nextIndex; 2625 boolean inActivity = false, inService = false; 2626 if (hasActivity) { 2627 // Process has activities, put it at the very tipsy-top. 2628 addIndex = mLruProcesses.size(); 2629 nextIndex = mLruProcessServiceStart; 2630 inActivity = true; 2631 } else if (hasService) { 2632 // Process has services, put it at the top of the service list. 2633 addIndex = mLruProcessActivityStart; 2634 nextIndex = mLruProcessServiceStart; 2635 inActivity = true; 2636 inService = true; 2637 } else { 2638 // Process not otherwise of interest, it goes to the top of the non-service area. 2639 addIndex = mLruProcessServiceStart; 2640 if (client != null) { 2641 int clientIndex = mLruProcesses.lastIndexOf(client); 2642 if (clientIndex < 0) Slog.d(TAG, "Unknown client " + client + " when updating " 2643 + app); 2644 if (clientIndex >= 0 && addIndex > clientIndex) { 2645 addIndex = clientIndex; 2646 } 2647 } 2648 nextIndex = addIndex > 0 ? addIndex-1 : addIndex; 2649 } 2650 2651 Slog.d(TAG, "Update LRU at " + lrui + " to " + addIndex + " (act=" 2652 + mLruProcessActivityStart + "): " + app); 2653 */ 2654 2655 if (lrui >= 0) { 2656 if (lrui < mLruProcessActivityStart) { 2657 mLruProcessActivityStart--; 2658 } 2659 if (lrui < mLruProcessServiceStart) { 2660 mLruProcessServiceStart--; 2661 } 2662 /* 2663 if (addIndex > lrui) { 2664 addIndex--; 2665 } 2666 if (nextIndex > lrui) { 2667 nextIndex--; 2668 } 2669 */ 2670 mLruProcesses.remove(lrui); 2671 } 2672 2673 /* 2674 mLruProcesses.add(addIndex, app); 2675 if (inActivity) { 2676 mLruProcessActivityStart++; 2677 } 2678 if (inService) { 2679 mLruProcessActivityStart++; 2680 } 2681 */ 2682 2683 int nextIndex; 2684 if (hasActivity) { 2685 final int N = mLruProcesses.size(); 2686 if (app.activities.size() == 0 && mLruProcessActivityStart < (N-1)) { 2687 // Process doesn't have activities, but has clients with 2688 // activities... move it up, but one below the top (the top 2689 // should always have a real activity). 2690 if (DEBUG_LRU) Slog.d(TAG, "Adding to second-top of LRU activity list: " + app); 2691 mLruProcesses.add(N-1, app); 2692 // To keep it from spamming the LRU list (by making a bunch of clients), 2693 // we will push down any other entries owned by the app. 2694 final int uid = app.info.uid; 2695 for (int i=N-2; i>mLruProcessActivityStart; i--) { 2696 ProcessRecord subProc = mLruProcesses.get(i); 2697 if (subProc.info.uid == uid) { 2698 // We want to push this one down the list. If the process after 2699 // it is for the same uid, however, don't do so, because we don't 2700 // want them internally to be re-ordered. 2701 if (mLruProcesses.get(i-1).info.uid != uid) { 2702 if (DEBUG_LRU) Slog.d(TAG, "Pushing uid " + uid + " swapping at " + i 2703 + ": " + mLruProcesses.get(i) + " : " + mLruProcesses.get(i-1)); 2704 ProcessRecord tmp = mLruProcesses.get(i); 2705 mLruProcesses.set(i, mLruProcesses.get(i-1)); 2706 mLruProcesses.set(i-1, tmp); 2707 i--; 2708 } 2709 } else { 2710 // A gap, we can stop here. 2711 break; 2712 } 2713 } 2714 } else { 2715 // Process has activities, put it at the very tipsy-top. 2716 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU activity list: " + app); 2717 mLruProcesses.add(app); 2718 } 2719 nextIndex = mLruProcessServiceStart; 2720 } else if (hasService) { 2721 // Process has services, put it at the top of the service list. 2722 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU service list: " + app); 2723 mLruProcesses.add(mLruProcessActivityStart, app); 2724 nextIndex = mLruProcessServiceStart; 2725 mLruProcessActivityStart++; 2726 } else { 2727 // Process not otherwise of interest, it goes to the top of the non-service area. 2728 int index = mLruProcessServiceStart; 2729 if (client != null) { 2730 // If there is a client, don't allow the process to be moved up higher 2731 // in the list than that client. 2732 int clientIndex = mLruProcesses.lastIndexOf(client); 2733 if (DEBUG_LRU && clientIndex < 0) Slog.d(TAG, "Unknown client " + client 2734 + " when updating " + app); 2735 if (clientIndex <= lrui) { 2736 // Don't allow the client index restriction to push it down farther in the 2737 // list than it already is. 2738 clientIndex = lrui; 2739 } 2740 if (clientIndex >= 0 && index > clientIndex) { 2741 index = clientIndex; 2742 } 2743 } 2744 if (DEBUG_LRU) Slog.d(TAG, "Adding at " + index + " of LRU list: " + app); 2745 mLruProcesses.add(index, app); 2746 nextIndex = index-1; 2747 mLruProcessActivityStart++; 2748 mLruProcessServiceStart++; 2749 } 2750 2751 // If the app is currently using a content provider or service, 2752 // bump those processes as well. 2753 for (int j=app.connections.size()-1; j>=0; j--) { 2754 ConnectionRecord cr = app.connections.valueAt(j); 2755 if (cr.binding != null && !cr.serviceDead && cr.binding.service != null 2756 && cr.binding.service.app != null 2757 && cr.binding.service.app.lruSeq != mLruSeq 2758 && !cr.binding.service.app.persistent) { 2759 nextIndex = updateLruProcessInternalLocked(cr.binding.service.app, now, nextIndex, 2760 "service connection", cr, app); 2761 } 2762 } 2763 for (int j=app.conProviders.size()-1; j>=0; j--) { 2764 ContentProviderRecord cpr = app.conProviders.get(j).provider; 2765 if (cpr.proc != null && cpr.proc.lruSeq != mLruSeq && !cpr.proc.persistent) { 2766 nextIndex = updateLruProcessInternalLocked(cpr.proc, now, nextIndex, 2767 "provider reference", cpr, app); 2768 } 2769 } 2770 } 2771 2772 final ProcessRecord getProcessRecordLocked(String processName, int uid, boolean keepIfLarge) { 2773 if (uid == Process.SYSTEM_UID) { 2774 // The system gets to run in any process. If there are multiple 2775 // processes with the same uid, just pick the first (this 2776 // should never happen). 2777 SparseArray<ProcessRecord> procs = mProcessNames.getMap().get(processName); 2778 if (procs == null) return null; 2779 final int N = procs.size(); 2780 for (int i = 0; i < N; i++) { 2781 if (UserHandle.isSameUser(procs.keyAt(i), uid)) return procs.valueAt(i); 2782 } 2783 } 2784 ProcessRecord proc = mProcessNames.get(processName, uid); 2785 if (false && proc != null && !keepIfLarge 2786 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY 2787 && proc.lastCachedPss >= 4000) { 2788 // Turn this condition on to cause killing to happen regularly, for testing. 2789 if (proc.baseProcessTracker != null) { 2790 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2791 } 2792 killUnneededProcessLocked(proc, Long.toString(proc.lastCachedPss) 2793 + "k from cached"); 2794 } else if (proc != null && !keepIfLarge 2795 && mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 2796 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 2797 if (DEBUG_PSS) Slog.d(TAG, "May not keep " + proc + ": pss=" + proc.lastCachedPss); 2798 if (proc.lastCachedPss >= mProcessList.getCachedRestoreThresholdKb()) { 2799 if (proc.baseProcessTracker != null) { 2800 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2801 } 2802 killUnneededProcessLocked(proc, Long.toString(proc.lastCachedPss) 2803 + "k from cached"); 2804 } 2805 } 2806 return proc; 2807 } 2808 2809 void ensurePackageDexOpt(String packageName) { 2810 IPackageManager pm = AppGlobals.getPackageManager(); 2811 try { 2812 if (pm.performDexOptIfNeeded(packageName, null /* instruction set */)) { 2813 mDidDexOpt = true; 2814 } 2815 } catch (RemoteException e) { 2816 } 2817 } 2818 2819 boolean isNextTransitionForward() { 2820 int transit = mWindowManager.getPendingAppTransition(); 2821 return transit == AppTransition.TRANSIT_ACTIVITY_OPEN 2822 || transit == AppTransition.TRANSIT_TASK_OPEN 2823 || transit == AppTransition.TRANSIT_TASK_TO_FRONT; 2824 } 2825 2826 final ProcessRecord startProcessLocked(String processName, 2827 ApplicationInfo info, boolean knownToBeDead, int intentFlags, 2828 String hostingType, ComponentName hostingName, boolean allowWhileBooting, 2829 boolean isolated, boolean keepIfLarge) { 2830 ProcessRecord app; 2831 if (!isolated) { 2832 app = getProcessRecordLocked(processName, info.uid, keepIfLarge); 2833 } else { 2834 // If this is an isolated process, it can't re-use an existing process. 2835 app = null; 2836 } 2837 // We don't have to do anything more if: 2838 // (1) There is an existing application record; and 2839 // (2) The caller doesn't think it is dead, OR there is no thread 2840 // object attached to it so we know it couldn't have crashed; and 2841 // (3) There is a pid assigned to it, so it is either starting or 2842 // already running. 2843 if (DEBUG_PROCESSES) Slog.v(TAG, "startProcess: name=" + processName 2844 + " app=" + app + " knownToBeDead=" + knownToBeDead 2845 + " thread=" + (app != null ? app.thread : null) 2846 + " pid=" + (app != null ? app.pid : -1)); 2847 if (app != null && app.pid > 0) { 2848 if (!knownToBeDead || app.thread == null) { 2849 // We already have the app running, or are waiting for it to 2850 // come up (we have a pid but not yet its thread), so keep it. 2851 if (DEBUG_PROCESSES) Slog.v(TAG, "App already running: " + app); 2852 // If this is a new package in the process, add the package to the list 2853 app.addPackage(info.packageName, info.versionCode, mProcessStats); 2854 return app; 2855 } 2856 2857 // An application record is attached to a previous process, 2858 // clean it up now. 2859 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, "App died: " + app); 2860 Process.killProcessGroup(app.info.uid, app.pid); 2861 handleAppDiedLocked(app, true, true); 2862 } 2863 2864 String hostingNameStr = hostingName != null 2865 ? hostingName.flattenToShortString() : null; 2866 2867 if (!isolated) { 2868 if ((intentFlags&Intent.FLAG_FROM_BACKGROUND) != 0) { 2869 // If we are in the background, then check to see if this process 2870 // is bad. If so, we will just silently fail. 2871 if (mBadProcesses.get(info.processName, info.uid) != null) { 2872 if (DEBUG_PROCESSES) Slog.v(TAG, "Bad process: " + info.uid 2873 + "/" + info.processName); 2874 return null; 2875 } 2876 } else { 2877 // When the user is explicitly starting a process, then clear its 2878 // crash count so that we won't make it bad until they see at 2879 // least one crash dialog again, and make the process good again 2880 // if it had been bad. 2881 if (DEBUG_PROCESSES) Slog.v(TAG, "Clearing bad process: " + info.uid 2882 + "/" + info.processName); 2883 mProcessCrashTimes.remove(info.processName, info.uid); 2884 if (mBadProcesses.get(info.processName, info.uid) != null) { 2885 EventLog.writeEvent(EventLogTags.AM_PROC_GOOD, 2886 UserHandle.getUserId(info.uid), info.uid, 2887 info.processName); 2888 mBadProcesses.remove(info.processName, info.uid); 2889 if (app != null) { 2890 app.bad = false; 2891 } 2892 } 2893 } 2894 } 2895 2896 if (app == null) { 2897 app = newProcessRecordLocked(info, processName, isolated); 2898 if (app == null) { 2899 Slog.w(TAG, "Failed making new process record for " 2900 + processName + "/" + info.uid + " isolated=" + isolated); 2901 return null; 2902 } 2903 mProcessNames.put(processName, app.uid, app); 2904 if (isolated) { 2905 mIsolatedProcesses.put(app.uid, app); 2906 } 2907 } else { 2908 // If this is a new package in the process, add the package to the list 2909 app.addPackage(info.packageName, info.versionCode, mProcessStats); 2910 } 2911 2912 // If the system is not ready yet, then hold off on starting this 2913 // process until it is. 2914 if (!mProcessesReady 2915 && !isAllowedWhileBooting(info) 2916 && !allowWhileBooting) { 2917 if (!mProcessesOnHold.contains(app)) { 2918 mProcessesOnHold.add(app); 2919 } 2920 if (DEBUG_PROCESSES) Slog.v(TAG, "System not ready, putting on hold: " + app); 2921 return app; 2922 } 2923 2924 startProcessLocked(app, hostingType, hostingNameStr, null /* ABI override */); 2925 return (app.pid != 0) ? app : null; 2926 } 2927 2928 boolean isAllowedWhileBooting(ApplicationInfo ai) { 2929 return (ai.flags&ApplicationInfo.FLAG_PERSISTENT) != 0; 2930 } 2931 2932 private final void startProcessLocked(ProcessRecord app, 2933 String hostingType, String hostingNameStr, String abiOverride) { 2934 if (app.pid > 0 && app.pid != MY_PID) { 2935 synchronized (mPidsSelfLocked) { 2936 mPidsSelfLocked.remove(app.pid); 2937 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 2938 } 2939 app.setPid(0); 2940 } 2941 2942 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 2943 "startProcessLocked removing on hold: " + app); 2944 mProcessesOnHold.remove(app); 2945 2946 updateCpuStats(); 2947 2948 try { 2949 int uid = app.uid; 2950 2951 int[] gids = null; 2952 int mountExternal = Zygote.MOUNT_EXTERNAL_NONE; 2953 if (!app.isolated) { 2954 int[] permGids = null; 2955 try { 2956 final PackageManager pm = mContext.getPackageManager(); 2957 permGids = pm.getPackageGids(app.info.packageName); 2958 2959 if (Environment.isExternalStorageEmulated()) { 2960 if (pm.checkPermission( 2961 android.Manifest.permission.ACCESS_ALL_EXTERNAL_STORAGE, 2962 app.info.packageName) == PERMISSION_GRANTED) { 2963 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER_ALL; 2964 } else { 2965 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER; 2966 } 2967 } 2968 } catch (PackageManager.NameNotFoundException e) { 2969 Slog.w(TAG, "Unable to retrieve gids", e); 2970 } 2971 2972 /* 2973 * Add shared application and profile GIDs so applications can share some 2974 * resources like shared libraries and access user-wide resources 2975 */ 2976 if (permGids == null) { 2977 gids = new int[2]; 2978 } else { 2979 gids = new int[permGids.length + 2]; 2980 System.arraycopy(permGids, 0, gids, 2, permGids.length); 2981 } 2982 gids[0] = UserHandle.getSharedAppGid(UserHandle.getAppId(uid)); 2983 gids[1] = UserHandle.getUserGid(UserHandle.getUserId(uid)); 2984 } 2985 if (mFactoryTest != FactoryTest.FACTORY_TEST_OFF) { 2986 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 2987 && mTopComponent != null 2988 && app.processName.equals(mTopComponent.getPackageName())) { 2989 uid = 0; 2990 } 2991 if (mFactoryTest == FactoryTest.FACTORY_TEST_HIGH_LEVEL 2992 && (app.info.flags&ApplicationInfo.FLAG_FACTORY_TEST) != 0) { 2993 uid = 0; 2994 } 2995 } 2996 int debugFlags = 0; 2997 if ((app.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 2998 debugFlags |= Zygote.DEBUG_ENABLE_DEBUGGER; 2999 // Also turn on CheckJNI for debuggable apps. It's quite 3000 // awkward to turn on otherwise. 3001 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 3002 } 3003 // Run the app in safe mode if its manifest requests so or the 3004 // system is booted in safe mode. 3005 if ((app.info.flags & ApplicationInfo.FLAG_VM_SAFE_MODE) != 0 || 3006 mSafeMode == true) { 3007 debugFlags |= Zygote.DEBUG_ENABLE_SAFEMODE; 3008 } 3009 if ("1".equals(SystemProperties.get("debug.checkjni"))) { 3010 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 3011 } 3012 if ("1".equals(SystemProperties.get("debug.jni.logging"))) { 3013 debugFlags |= Zygote.DEBUG_ENABLE_JNI_LOGGING; 3014 } 3015 if ("1".equals(SystemProperties.get("debug.assert"))) { 3016 debugFlags |= Zygote.DEBUG_ENABLE_ASSERT; 3017 } 3018 3019 String requiredAbi = (abiOverride != null) ? abiOverride : app.info.primaryCpuAbi; 3020 if (requiredAbi == null) { 3021 requiredAbi = Build.SUPPORTED_ABIS[0]; 3022 } 3023 3024 // Start the process. It will either succeed and return a result containing 3025 // the PID of the new process, or else throw a RuntimeException. 3026 Process.ProcessStartResult startResult = Process.start("android.app.ActivityThread", 3027 app.processName, uid, uid, gids, debugFlags, mountExternal, 3028 app.info.targetSdkVersion, app.info.seinfo, requiredAbi, null); 3029 3030 if (app.isolated) { 3031 mBatteryStatsService.addIsolatedUid(app.uid, app.info.uid); 3032 } 3033 mBatteryStatsService.noteProcessStart(app.processName, app.info.uid); 3034 3035 EventLog.writeEvent(EventLogTags.AM_PROC_START, 3036 UserHandle.getUserId(uid), startResult.pid, uid, 3037 app.processName, hostingType, 3038 hostingNameStr != null ? hostingNameStr : ""); 3039 3040 if (app.persistent) { 3041 Watchdog.getInstance().processStarted(app.processName, startResult.pid); 3042 } 3043 3044 StringBuilder buf = mStringBuilder; 3045 buf.setLength(0); 3046 buf.append("Start proc "); 3047 buf.append(app.processName); 3048 buf.append(" for "); 3049 buf.append(hostingType); 3050 if (hostingNameStr != null) { 3051 buf.append(" "); 3052 buf.append(hostingNameStr); 3053 } 3054 buf.append(": pid="); 3055 buf.append(startResult.pid); 3056 buf.append(" uid="); 3057 buf.append(uid); 3058 buf.append(" gids={"); 3059 if (gids != null) { 3060 for (int gi=0; gi<gids.length; gi++) { 3061 if (gi != 0) buf.append(", "); 3062 buf.append(gids[gi]); 3063 3064 } 3065 } 3066 buf.append("}"); 3067 if (requiredAbi != null) { 3068 buf.append(" abi="); 3069 buf.append(requiredAbi); 3070 } 3071 Slog.i(TAG, buf.toString()); 3072 app.setPid(startResult.pid); 3073 app.usingWrapper = startResult.usingWrapper; 3074 app.removed = false; 3075 app.killedByAm = false; 3076 synchronized (mPidsSelfLocked) { 3077 this.mPidsSelfLocked.put(startResult.pid, app); 3078 Message msg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 3079 msg.obj = app; 3080 mHandler.sendMessageDelayed(msg, startResult.usingWrapper 3081 ? PROC_START_TIMEOUT_WITH_WRAPPER : PROC_START_TIMEOUT); 3082 } 3083 } catch (RuntimeException e) { 3084 // XXX do better error recovery. 3085 app.setPid(0); 3086 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 3087 if (app.isolated) { 3088 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 3089 } 3090 Slog.e(TAG, "Failure starting process " + app.processName, e); 3091 } 3092 } 3093 3094 void updateUsageStats(ActivityRecord component, boolean resumed) { 3095 if (DEBUG_SWITCH) Slog.d(TAG, "updateUsageStats: comp=" + component + "res=" + resumed); 3096 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 3097 if (resumed) { 3098 mUsageStatsService.noteResumeComponent(component.realActivity); 3099 synchronized (stats) { 3100 stats.noteActivityResumedLocked(component.app.uid); 3101 } 3102 } else { 3103 mUsageStatsService.notePauseComponent(component.realActivity); 3104 synchronized (stats) { 3105 stats.noteActivityPausedLocked(component.app.uid); 3106 } 3107 } 3108 } 3109 3110 Intent getHomeIntent() { 3111 Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null); 3112 intent.setComponent(mTopComponent); 3113 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 3114 intent.addCategory(Intent.CATEGORY_HOME); 3115 } 3116 return intent; 3117 } 3118 3119 boolean startHomeActivityLocked(int userId) { 3120 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3121 && mTopAction == null) { 3122 // We are running in factory test mode, but unable to find 3123 // the factory test app, so just sit around displaying the 3124 // error message and don't try to start anything. 3125 return false; 3126 } 3127 Intent intent = getHomeIntent(); 3128 ActivityInfo aInfo = 3129 resolveActivityInfo(intent, STOCK_PM_FLAGS, userId); 3130 if (aInfo != null) { 3131 intent.setComponent(new ComponentName( 3132 aInfo.applicationInfo.packageName, aInfo.name)); 3133 // Don't do this if the home app is currently being 3134 // instrumented. 3135 aInfo = new ActivityInfo(aInfo); 3136 aInfo.applicationInfo = getAppInfoForUser(aInfo.applicationInfo, userId); 3137 ProcessRecord app = getProcessRecordLocked(aInfo.processName, 3138 aInfo.applicationInfo.uid, true); 3139 if (app == null || app.instrumentationClass == null) { 3140 intent.setFlags(intent.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK); 3141 mStackSupervisor.startHomeActivity(intent, aInfo); 3142 } 3143 } 3144 3145 return true; 3146 } 3147 3148 private ActivityInfo resolveActivityInfo(Intent intent, int flags, int userId) { 3149 ActivityInfo ai = null; 3150 ComponentName comp = intent.getComponent(); 3151 try { 3152 if (comp != null) { 3153 ai = AppGlobals.getPackageManager().getActivityInfo(comp, flags, userId); 3154 } else { 3155 ResolveInfo info = AppGlobals.getPackageManager().resolveIntent( 3156 intent, 3157 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 3158 flags, userId); 3159 3160 if (info != null) { 3161 ai = info.activityInfo; 3162 } 3163 } 3164 } catch (RemoteException e) { 3165 // ignore 3166 } 3167 3168 return ai; 3169 } 3170 3171 /** 3172 * Starts the "new version setup screen" if appropriate. 3173 */ 3174 void startSetupActivityLocked() { 3175 // Only do this once per boot. 3176 if (mCheckedForSetup) { 3177 return; 3178 } 3179 3180 // We will show this screen if the current one is a different 3181 // version than the last one shown, and we are not running in 3182 // low-level factory test mode. 3183 final ContentResolver resolver = mContext.getContentResolver(); 3184 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL && 3185 Settings.Global.getInt(resolver, 3186 Settings.Global.DEVICE_PROVISIONED, 0) != 0) { 3187 mCheckedForSetup = true; 3188 3189 // See if we should be showing the platform update setup UI. 3190 Intent intent = new Intent(Intent.ACTION_UPGRADE_SETUP); 3191 List<ResolveInfo> ris = mContext.getPackageManager() 3192 .queryIntentActivities(intent, PackageManager.GET_META_DATA); 3193 3194 // We don't allow third party apps to replace this. 3195 ResolveInfo ri = null; 3196 for (int i=0; ris != null && i<ris.size(); i++) { 3197 if ((ris.get(i).activityInfo.applicationInfo.flags 3198 & ApplicationInfo.FLAG_SYSTEM) != 0) { 3199 ri = ris.get(i); 3200 break; 3201 } 3202 } 3203 3204 if (ri != null) { 3205 String vers = ri.activityInfo.metaData != null 3206 ? ri.activityInfo.metaData.getString(Intent.METADATA_SETUP_VERSION) 3207 : null; 3208 if (vers == null && ri.activityInfo.applicationInfo.metaData != null) { 3209 vers = ri.activityInfo.applicationInfo.metaData.getString( 3210 Intent.METADATA_SETUP_VERSION); 3211 } 3212 String lastVers = Settings.Secure.getString( 3213 resolver, Settings.Secure.LAST_SETUP_SHOWN); 3214 if (vers != null && !vers.equals(lastVers)) { 3215 intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 3216 intent.setComponent(new ComponentName( 3217 ri.activityInfo.packageName, ri.activityInfo.name)); 3218 mStackSupervisor.startActivityLocked(null, intent, null, ri.activityInfo, 3219 null, null, null, null, 0, 0, 0, null, 0, null, false, null, null); 3220 } 3221 } 3222 } 3223 } 3224 3225 CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) { 3226 return mCompatModePackages.compatibilityInfoForPackageLocked(ai); 3227 } 3228 3229 void enforceNotIsolatedCaller(String caller) { 3230 if (UserHandle.isIsolated(Binder.getCallingUid())) { 3231 throw new SecurityException("Isolated process not allowed to call " + caller); 3232 } 3233 } 3234 3235 @Override 3236 public int getFrontActivityScreenCompatMode() { 3237 enforceNotIsolatedCaller("getFrontActivityScreenCompatMode"); 3238 synchronized (this) { 3239 return mCompatModePackages.getFrontActivityScreenCompatModeLocked(); 3240 } 3241 } 3242 3243 @Override 3244 public void setFrontActivityScreenCompatMode(int mode) { 3245 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3246 "setFrontActivityScreenCompatMode"); 3247 synchronized (this) { 3248 mCompatModePackages.setFrontActivityScreenCompatModeLocked(mode); 3249 } 3250 } 3251 3252 @Override 3253 public int getPackageScreenCompatMode(String packageName) { 3254 enforceNotIsolatedCaller("getPackageScreenCompatMode"); 3255 synchronized (this) { 3256 return mCompatModePackages.getPackageScreenCompatModeLocked(packageName); 3257 } 3258 } 3259 3260 @Override 3261 public void setPackageScreenCompatMode(String packageName, int mode) { 3262 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3263 "setPackageScreenCompatMode"); 3264 synchronized (this) { 3265 mCompatModePackages.setPackageScreenCompatModeLocked(packageName, mode); 3266 } 3267 } 3268 3269 @Override 3270 public boolean getPackageAskScreenCompat(String packageName) { 3271 enforceNotIsolatedCaller("getPackageAskScreenCompat"); 3272 synchronized (this) { 3273 return mCompatModePackages.getPackageAskCompatModeLocked(packageName); 3274 } 3275 } 3276 3277 @Override 3278 public void setPackageAskScreenCompat(String packageName, boolean ask) { 3279 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3280 "setPackageAskScreenCompat"); 3281 synchronized (this) { 3282 mCompatModePackages.setPackageAskCompatModeLocked(packageName, ask); 3283 } 3284 } 3285 3286 private void dispatchProcessesChanged() { 3287 int N; 3288 synchronized (this) { 3289 N = mPendingProcessChanges.size(); 3290 if (mActiveProcessChanges.length < N) { 3291 mActiveProcessChanges = new ProcessChangeItem[N]; 3292 } 3293 mPendingProcessChanges.toArray(mActiveProcessChanges); 3294 mAvailProcessChanges.addAll(mPendingProcessChanges); 3295 mPendingProcessChanges.clear(); 3296 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "*** Delivering " + N + " process changes"); 3297 } 3298 3299 int i = mProcessObservers.beginBroadcast(); 3300 while (i > 0) { 3301 i--; 3302 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3303 if (observer != null) { 3304 try { 3305 for (int j=0; j<N; j++) { 3306 ProcessChangeItem item = mActiveProcessChanges[j]; 3307 if ((item.changes&ProcessChangeItem.CHANGE_ACTIVITIES) != 0) { 3308 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "ACTIVITIES CHANGED pid=" 3309 + item.pid + " uid=" + item.uid + ": " 3310 + item.foregroundActivities); 3311 observer.onForegroundActivitiesChanged(item.pid, item.uid, 3312 item.foregroundActivities); 3313 } 3314 if ((item.changes&ProcessChangeItem.CHANGE_PROCESS_STATE) != 0) { 3315 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "PROCSTATE CHANGED pid=" 3316 + item.pid + " uid=" + item.uid + ": " + item.processState); 3317 observer.onProcessStateChanged(item.pid, item.uid, item.processState); 3318 } 3319 } 3320 } catch (RemoteException e) { 3321 } 3322 } 3323 } 3324 mProcessObservers.finishBroadcast(); 3325 } 3326 3327 private void dispatchProcessDied(int pid, int uid) { 3328 int i = mProcessObservers.beginBroadcast(); 3329 while (i > 0) { 3330 i--; 3331 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3332 if (observer != null) { 3333 try { 3334 observer.onProcessDied(pid, uid); 3335 } catch (RemoteException e) { 3336 } 3337 } 3338 } 3339 mProcessObservers.finishBroadcast(); 3340 } 3341 3342 final void doPendingActivityLaunchesLocked(boolean doResume) { 3343 final int N = mPendingActivityLaunches.size(); 3344 if (N <= 0) { 3345 return; 3346 } 3347 for (int i=0; i<N; i++) { 3348 PendingActivityLaunch pal = mPendingActivityLaunches.get(i); 3349 mStackSupervisor.startActivityUncheckedLocked(pal.r, pal.sourceRecord, null, null, pal.startFlags, 3350 doResume && i == (N-1), null); 3351 } 3352 mPendingActivityLaunches.clear(); 3353 } 3354 3355 @Override 3356 public final int startActivity(IApplicationThread caller, String callingPackage, 3357 Intent intent, String resolvedType, IBinder resultTo, 3358 String resultWho, int requestCode, int startFlags, 3359 String profileFile, ParcelFileDescriptor profileFd, Bundle options) { 3360 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo, 3361 resultWho, requestCode, 3362 startFlags, profileFile, profileFd, options, UserHandle.getCallingUserId()); 3363 } 3364 3365 @Override 3366 public final int startActivityAsUser(IApplicationThread caller, String callingPackage, 3367 Intent intent, String resolvedType, IBinder resultTo, 3368 String resultWho, int requestCode, int startFlags, 3369 String profileFile, ParcelFileDescriptor profileFd, Bundle options, int userId) { 3370 enforceNotIsolatedCaller("startActivity"); 3371 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3372 false, ALLOW_FULL_ONLY, "startActivity", null); 3373 // TODO: Switch to user app stacks here. 3374 return mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 3375 null, null, resultTo, resultWho, requestCode, startFlags, profileFile, profileFd, 3376 null, null, options, userId, null); 3377 } 3378 3379 @Override 3380 public final WaitResult startActivityAndWait(IApplicationThread caller, String callingPackage, 3381 Intent intent, String resolvedType, IBinder resultTo, 3382 String resultWho, int requestCode, int startFlags, String profileFile, 3383 ParcelFileDescriptor profileFd, Bundle options, int userId) { 3384 enforceNotIsolatedCaller("startActivityAndWait"); 3385 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3386 false, ALLOW_FULL_ONLY, "startActivityAndWait", null); 3387 WaitResult res = new WaitResult(); 3388 // TODO: Switch to user app stacks here. 3389 mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 3390 null, null, resultTo, resultWho, requestCode, startFlags, profileFile, profileFd, 3391 res, null, options, userId, null); 3392 return res; 3393 } 3394 3395 @Override 3396 public final int startActivityWithConfig(IApplicationThread caller, String callingPackage, 3397 Intent intent, String resolvedType, IBinder resultTo, 3398 String resultWho, int requestCode, int startFlags, Configuration config, 3399 Bundle options, int userId) { 3400 enforceNotIsolatedCaller("startActivityWithConfig"); 3401 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3402 false, ALLOW_FULL_ONLY, "startActivityWithConfig", null); 3403 // TODO: Switch to user app stacks here. 3404 int ret = mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, 3405 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3406 null, null, null, config, options, userId, null); 3407 return ret; 3408 } 3409 3410 @Override 3411 public int startActivityIntentSender(IApplicationThread caller, 3412 IntentSender intent, Intent fillInIntent, String resolvedType, 3413 IBinder resultTo, String resultWho, int requestCode, 3414 int flagsMask, int flagsValues, Bundle options) { 3415 enforceNotIsolatedCaller("startActivityIntentSender"); 3416 // Refuse possible leaked file descriptors 3417 if (fillInIntent != null && fillInIntent.hasFileDescriptors()) { 3418 throw new IllegalArgumentException("File descriptors passed in Intent"); 3419 } 3420 3421 IIntentSender sender = intent.getTarget(); 3422 if (!(sender instanceof PendingIntentRecord)) { 3423 throw new IllegalArgumentException("Bad PendingIntent object"); 3424 } 3425 3426 PendingIntentRecord pir = (PendingIntentRecord)sender; 3427 3428 synchronized (this) { 3429 // If this is coming from the currently resumed activity, it is 3430 // effectively saying that app switches are allowed at this point. 3431 final ActivityStack stack = getFocusedStack(); 3432 if (stack.mResumedActivity != null && 3433 stack.mResumedActivity.info.applicationInfo.uid == Binder.getCallingUid()) { 3434 mAppSwitchesAllowedTime = 0; 3435 } 3436 } 3437 int ret = pir.sendInner(0, fillInIntent, resolvedType, null, null, 3438 resultTo, resultWho, requestCode, flagsMask, flagsValues, options, null); 3439 return ret; 3440 } 3441 3442 @Override 3443 public int startVoiceActivity(String callingPackage, int callingPid, int callingUid, 3444 Intent intent, String resolvedType, IVoiceInteractionSession session, 3445 IVoiceInteractor interactor, int startFlags, String profileFile, 3446 ParcelFileDescriptor profileFd, Bundle options, int userId) { 3447 if (checkCallingPermission(Manifest.permission.BIND_VOICE_INTERACTION) 3448 != PackageManager.PERMISSION_GRANTED) { 3449 String msg = "Permission Denial: startVoiceActivity() from pid=" 3450 + Binder.getCallingPid() 3451 + ", uid=" + Binder.getCallingUid() 3452 + " requires " + android.Manifest.permission.BIND_VOICE_INTERACTION; 3453 Slog.w(TAG, msg); 3454 throw new SecurityException(msg); 3455 } 3456 if (session == null || interactor == null) { 3457 throw new NullPointerException("null session or interactor"); 3458 } 3459 userId = handleIncomingUser(callingPid, callingUid, userId, 3460 false, ALLOW_FULL_ONLY, "startVoiceActivity", null); 3461 // TODO: Switch to user app stacks here. 3462 return mStackSupervisor.startActivityMayWait(null, callingUid, callingPackage, intent, 3463 resolvedType, session, interactor, null, null, 0, startFlags, 3464 profileFile, profileFd, null, null, options, userId, null); 3465 } 3466 3467 @Override 3468 public boolean startNextMatchingActivity(IBinder callingActivity, 3469 Intent intent, Bundle options) { 3470 // Refuse possible leaked file descriptors 3471 if (intent != null && intent.hasFileDescriptors() == true) { 3472 throw new IllegalArgumentException("File descriptors passed in Intent"); 3473 } 3474 3475 synchronized (this) { 3476 final ActivityRecord r = ActivityRecord.isInStackLocked(callingActivity); 3477 if (r == null) { 3478 ActivityOptions.abort(options); 3479 return false; 3480 } 3481 if (r.app == null || r.app.thread == null) { 3482 // The caller is not running... d'oh! 3483 ActivityOptions.abort(options); 3484 return false; 3485 } 3486 intent = new Intent(intent); 3487 // The caller is not allowed to change the data. 3488 intent.setDataAndType(r.intent.getData(), r.intent.getType()); 3489 // And we are resetting to find the next component... 3490 intent.setComponent(null); 3491 3492 final boolean debug = ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0); 3493 3494 ActivityInfo aInfo = null; 3495 try { 3496 List<ResolveInfo> resolves = 3497 AppGlobals.getPackageManager().queryIntentActivities( 3498 intent, r.resolvedType, 3499 PackageManager.MATCH_DEFAULT_ONLY | STOCK_PM_FLAGS, 3500 UserHandle.getCallingUserId()); 3501 3502 // Look for the original activity in the list... 3503 final int N = resolves != null ? resolves.size() : 0; 3504 for (int i=0; i<N; i++) { 3505 ResolveInfo rInfo = resolves.get(i); 3506 if (rInfo.activityInfo.packageName.equals(r.packageName) 3507 && rInfo.activityInfo.name.equals(r.info.name)) { 3508 // We found the current one... the next matching is 3509 // after it. 3510 i++; 3511 if (i<N) { 3512 aInfo = resolves.get(i).activityInfo; 3513 } 3514 if (debug) { 3515 Slog.v(TAG, "Next matching activity: found current " + r.packageName 3516 + "/" + r.info.name); 3517 Slog.v(TAG, "Next matching activity: next is " + aInfo.packageName 3518 + "/" + aInfo.name); 3519 } 3520 break; 3521 } 3522 } 3523 } catch (RemoteException e) { 3524 } 3525 3526 if (aInfo == null) { 3527 // Nobody who is next! 3528 ActivityOptions.abort(options); 3529 if (debug) Slog.d(TAG, "Next matching activity: nothing found"); 3530 return false; 3531 } 3532 3533 intent.setComponent(new ComponentName( 3534 aInfo.applicationInfo.packageName, aInfo.name)); 3535 intent.setFlags(intent.getFlags()&~( 3536 Intent.FLAG_ACTIVITY_FORWARD_RESULT| 3537 Intent.FLAG_ACTIVITY_CLEAR_TOP| 3538 Intent.FLAG_ACTIVITY_MULTIPLE_TASK| 3539 Intent.FLAG_ACTIVITY_NEW_TASK)); 3540 3541 // Okay now we need to start the new activity, replacing the 3542 // currently running activity. This is a little tricky because 3543 // we want to start the new one as if the current one is finished, 3544 // but not finish the current one first so that there is no flicker. 3545 // And thus... 3546 final boolean wasFinishing = r.finishing; 3547 r.finishing = true; 3548 3549 // Propagate reply information over to the new activity. 3550 final ActivityRecord resultTo = r.resultTo; 3551 final String resultWho = r.resultWho; 3552 final int requestCode = r.requestCode; 3553 r.resultTo = null; 3554 if (resultTo != null) { 3555 resultTo.removeResultsLocked(r, resultWho, requestCode); 3556 } 3557 3558 final long origId = Binder.clearCallingIdentity(); 3559 int res = mStackSupervisor.startActivityLocked(r.app.thread, intent, 3560 r.resolvedType, aInfo, null, null, resultTo != null ? resultTo.appToken : null, 3561 resultWho, requestCode, -1, r.launchedFromUid, r.launchedFromPackage, 0, 3562 options, false, null, null); 3563 Binder.restoreCallingIdentity(origId); 3564 3565 r.finishing = wasFinishing; 3566 if (res != ActivityManager.START_SUCCESS) { 3567 return false; 3568 } 3569 return true; 3570 } 3571 } 3572 3573 final int startActivityInPackage(int uid, String callingPackage, 3574 Intent intent, String resolvedType, IBinder resultTo, 3575 String resultWho, int requestCode, int startFlags, Bundle options, int userId, 3576 IActivityContainer container) { 3577 3578 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3579 false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 3580 3581 // TODO: Switch to user app stacks here. 3582 int ret = mStackSupervisor.startActivityMayWait(null, uid, callingPackage, intent, resolvedType, 3583 null, null, resultTo, resultWho, requestCode, startFlags, 3584 null, null, null, null, options, userId, container); 3585 return ret; 3586 } 3587 3588 @Override 3589 public final int startActivities(IApplicationThread caller, String callingPackage, 3590 Intent[] intents, String[] resolvedTypes, IBinder resultTo, Bundle options, 3591 int userId) { 3592 enforceNotIsolatedCaller("startActivities"); 3593 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3594 false, ALLOW_FULL_ONLY, "startActivity", null); 3595 // TODO: Switch to user app stacks here. 3596 int ret = mStackSupervisor.startActivities(caller, -1, callingPackage, intents, 3597 resolvedTypes, resultTo, options, userId); 3598 return ret; 3599 } 3600 3601 final int startActivitiesInPackage(int uid, String callingPackage, 3602 Intent[] intents, String[] resolvedTypes, IBinder resultTo, 3603 Bundle options, int userId) { 3604 3605 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3606 false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 3607 // TODO: Switch to user app stacks here. 3608 int ret = mStackSupervisor.startActivities(null, uid, callingPackage, intents, resolvedTypes, 3609 resultTo, options, userId); 3610 return ret; 3611 } 3612 3613 final void addRecentTaskLocked(TaskRecord task) { 3614 int N = mRecentTasks.size(); 3615 // Quick case: check if the top-most recent task is the same. 3616 if (N > 0 && mRecentTasks.get(0) == task) { 3617 return; 3618 } 3619 // Another quick case: never add voice sessions. 3620 if (task.voiceSession != null) { 3621 return; 3622 } 3623 // Remove any existing entries that are the same kind of task. 3624 final Intent intent = task.intent; 3625 final boolean document = intent != null && intent.isDocument(); 3626 final ComponentName comp = intent.getComponent(); 3627 3628 int maxRecents = task.maxRecents - 1; 3629 for (int i=0; i<N; i++) { 3630 final TaskRecord tr = mRecentTasks.get(i); 3631 if (task != tr) { 3632 if (task.userId != tr.userId) { 3633 continue; 3634 } 3635 if (i > MAX_RECENT_BITMAPS) { 3636 tr.freeLastThumbnail(); 3637 } 3638 final Intent trIntent = tr.intent; 3639 if ((task.affinity == null || !task.affinity.equals(tr.affinity)) && 3640 (intent == null || !intent.filterEquals(trIntent))) { 3641 continue; 3642 } 3643 final boolean trIsDocument = trIntent != null && trIntent.isDocument(); 3644 if (document && trIsDocument) { 3645 // These are the same document activity (not necessarily the same doc). 3646 if (maxRecents > 0) { 3647 --maxRecents; 3648 continue; 3649 } 3650 // Hit the maximum number of documents for this task. Fall through 3651 // and remove this document from recents. 3652 } else if (document || trIsDocument) { 3653 // Only one of these is a document. Not the droid we're looking for. 3654 continue; 3655 } 3656 } 3657 3658 // Either task and tr are the same or, their affinities match or their intents match 3659 // and neither of them is a document, or they are documents using the same activity 3660 // and their maxRecents has been reached. 3661 tr.disposeThumbnail(); 3662 mRecentTasks.remove(i); 3663 if (task != tr) { 3664 tr.closeRecentsChain(); 3665 } 3666 i--; 3667 N--; 3668 if (task.intent == null) { 3669 // If the new recent task we are adding is not fully 3670 // specified, then replace it with the existing recent task. 3671 task = tr; 3672 } 3673 mTaskPersister.notify(tr, false); 3674 } 3675 if (N >= MAX_RECENT_TASKS) { 3676 final TaskRecord tr = mRecentTasks.remove(N - 1); 3677 tr.disposeThumbnail(); 3678 tr.closeRecentsChain(); 3679 } 3680 mRecentTasks.add(0, task); 3681 } 3682 3683 @Override 3684 public void reportActivityFullyDrawn(IBinder token) { 3685 synchronized (this) { 3686 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3687 if (r == null) { 3688 return; 3689 } 3690 r.reportFullyDrawnLocked(); 3691 } 3692 } 3693 3694 @Override 3695 public void setRequestedOrientation(IBinder token, int requestedOrientation) { 3696 synchronized (this) { 3697 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3698 if (r == null) { 3699 return; 3700 } 3701 final long origId = Binder.clearCallingIdentity(); 3702 mWindowManager.setAppOrientation(r.appToken, requestedOrientation); 3703 Configuration config = mWindowManager.updateOrientationFromAppTokens( 3704 mConfiguration, r.mayFreezeScreenLocked(r.app) ? r.appToken : null); 3705 if (config != null) { 3706 r.frozenBeforeDestroy = true; 3707 if (!updateConfigurationLocked(config, r, false, false)) { 3708 mStackSupervisor.resumeTopActivitiesLocked(); 3709 } 3710 } 3711 Binder.restoreCallingIdentity(origId); 3712 } 3713 } 3714 3715 @Override 3716 public int getRequestedOrientation(IBinder token) { 3717 synchronized (this) { 3718 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3719 if (r == null) { 3720 return ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED; 3721 } 3722 return mWindowManager.getAppOrientation(r.appToken); 3723 } 3724 } 3725 3726 /** 3727 * This is the internal entry point for handling Activity.finish(). 3728 * 3729 * @param token The Binder token referencing the Activity we want to finish. 3730 * @param resultCode Result code, if any, from this Activity. 3731 * @param resultData Result data (Intent), if any, from this Activity. 3732 * @param finishTask Whether to finish the task associated with this Activity. Only applies to 3733 * the root Activity in the task. 3734 * 3735 * @return Returns true if the activity successfully finished, or false if it is still running. 3736 */ 3737 @Override 3738 public final boolean finishActivity(IBinder token, int resultCode, Intent resultData, 3739 boolean finishTask) { 3740 // Refuse possible leaked file descriptors 3741 if (resultData != null && resultData.hasFileDescriptors() == true) { 3742 throw new IllegalArgumentException("File descriptors passed in Intent"); 3743 } 3744 3745 synchronized(this) { 3746 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3747 if (r == null) { 3748 return true; 3749 } 3750 // Keep track of the root activity of the task before we finish it 3751 TaskRecord tr = r.task; 3752 ActivityRecord rootR = tr.getRootActivity(); 3753 // Do not allow task to finish in Lock Task mode. 3754 if (tr == mStackSupervisor.mLockTaskModeTask) { 3755 if (rootR == r) { 3756 mStackSupervisor.showLockTaskToast(); 3757 return false; 3758 } 3759 } 3760 if (mController != null) { 3761 // Find the first activity that is not finishing. 3762 ActivityRecord next = r.task.stack.topRunningActivityLocked(token, 0); 3763 if (next != null) { 3764 // ask watcher if this is allowed 3765 boolean resumeOK = true; 3766 try { 3767 resumeOK = mController.activityResuming(next.packageName); 3768 } catch (RemoteException e) { 3769 mController = null; 3770 Watchdog.getInstance().setActivityController(null); 3771 } 3772 3773 if (!resumeOK) { 3774 return false; 3775 } 3776 } 3777 } 3778 final long origId = Binder.clearCallingIdentity(); 3779 try { 3780 boolean res; 3781 if (finishTask && r == rootR) { 3782 // If requested, remove the task that is associated to this activity only if it 3783 // was the root activity in the task. The result code and data is ignored because 3784 // we don't support returning them across task boundaries. 3785 res = removeTaskByIdLocked(tr.taskId, 0); 3786 } else { 3787 res = tr.stack.requestFinishActivityLocked(token, resultCode, 3788 resultData, "app-request", true); 3789 } 3790 return res; 3791 } finally { 3792 Binder.restoreCallingIdentity(origId); 3793 } 3794 } 3795 } 3796 3797 @Override 3798 public final void finishHeavyWeightApp() { 3799 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 3800 != PackageManager.PERMISSION_GRANTED) { 3801 String msg = "Permission Denial: finishHeavyWeightApp() from pid=" 3802 + Binder.getCallingPid() 3803 + ", uid=" + Binder.getCallingUid() 3804 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 3805 Slog.w(TAG, msg); 3806 throw new SecurityException(msg); 3807 } 3808 3809 synchronized(this) { 3810 if (mHeavyWeightProcess == null) { 3811 return; 3812 } 3813 3814 ArrayList<ActivityRecord> activities = new ArrayList<ActivityRecord>( 3815 mHeavyWeightProcess.activities); 3816 for (int i=0; i<activities.size(); i++) { 3817 ActivityRecord r = activities.get(i); 3818 if (!r.finishing) { 3819 r.task.stack.finishActivityLocked(r, Activity.RESULT_CANCELED, 3820 null, "finish-heavy", true); 3821 } 3822 } 3823 3824 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 3825 mHeavyWeightProcess.userId, 0)); 3826 mHeavyWeightProcess = null; 3827 } 3828 } 3829 3830 @Override 3831 public void crashApplication(int uid, int initialPid, String packageName, 3832 String message) { 3833 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 3834 != PackageManager.PERMISSION_GRANTED) { 3835 String msg = "Permission Denial: crashApplication() from pid=" 3836 + Binder.getCallingPid() 3837 + ", uid=" + Binder.getCallingUid() 3838 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 3839 Slog.w(TAG, msg); 3840 throw new SecurityException(msg); 3841 } 3842 3843 synchronized(this) { 3844 ProcessRecord proc = null; 3845 3846 // Figure out which process to kill. We don't trust that initialPid 3847 // still has any relation to current pids, so must scan through the 3848 // list. 3849 synchronized (mPidsSelfLocked) { 3850 for (int i=0; i<mPidsSelfLocked.size(); i++) { 3851 ProcessRecord p = mPidsSelfLocked.valueAt(i); 3852 if (p.uid != uid) { 3853 continue; 3854 } 3855 if (p.pid == initialPid) { 3856 proc = p; 3857 break; 3858 } 3859 if (p.pkgList.containsKey(packageName)) { 3860 proc = p; 3861 } 3862 } 3863 } 3864 3865 if (proc == null) { 3866 Slog.w(TAG, "crashApplication: nothing for uid=" + uid 3867 + " initialPid=" + initialPid 3868 + " packageName=" + packageName); 3869 return; 3870 } 3871 3872 if (proc.thread != null) { 3873 if (proc.pid == Process.myPid()) { 3874 Log.w(TAG, "crashApplication: trying to crash self!"); 3875 return; 3876 } 3877 long ident = Binder.clearCallingIdentity(); 3878 try { 3879 proc.thread.scheduleCrash(message); 3880 } catch (RemoteException e) { 3881 } 3882 Binder.restoreCallingIdentity(ident); 3883 } 3884 } 3885 } 3886 3887 @Override 3888 public final void finishSubActivity(IBinder token, String resultWho, 3889 int requestCode) { 3890 synchronized(this) { 3891 final long origId = Binder.clearCallingIdentity(); 3892 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3893 if (r != null) { 3894 r.task.stack.finishSubActivityLocked(r, resultWho, requestCode); 3895 } 3896 Binder.restoreCallingIdentity(origId); 3897 } 3898 } 3899 3900 @Override 3901 public boolean finishActivityAffinity(IBinder token) { 3902 synchronized(this) { 3903 final long origId = Binder.clearCallingIdentity(); 3904 try { 3905 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3906 3907 ActivityRecord rootR = r.task.getRootActivity(); 3908 // Do not allow task to finish in Lock Task mode. 3909 if (r.task == mStackSupervisor.mLockTaskModeTask) { 3910 if (rootR == r) { 3911 mStackSupervisor.showLockTaskToast(); 3912 return false; 3913 } 3914 } 3915 boolean res = false; 3916 if (r != null) { 3917 res = r.task.stack.finishActivityAffinityLocked(r); 3918 } 3919 return res; 3920 } finally { 3921 Binder.restoreCallingIdentity(origId); 3922 } 3923 } 3924 } 3925 3926 @Override 3927 public void finishVoiceTask(IVoiceInteractionSession session) { 3928 synchronized(this) { 3929 final long origId = Binder.clearCallingIdentity(); 3930 try { 3931 mStackSupervisor.finishVoiceTask(session); 3932 } finally { 3933 Binder.restoreCallingIdentity(origId); 3934 } 3935 } 3936 3937 } 3938 3939 @Override 3940 public boolean willActivityBeVisible(IBinder token) { 3941 synchronized(this) { 3942 ActivityStack stack = ActivityRecord.getStackLocked(token); 3943 if (stack != null) { 3944 return stack.willActivityBeVisibleLocked(token); 3945 } 3946 return false; 3947 } 3948 } 3949 3950 @Override 3951 public void overridePendingTransition(IBinder token, String packageName, 3952 int enterAnim, int exitAnim) { 3953 synchronized(this) { 3954 ActivityRecord self = ActivityRecord.isInStackLocked(token); 3955 if (self == null) { 3956 return; 3957 } 3958 3959 final long origId = Binder.clearCallingIdentity(); 3960 3961 if (self.state == ActivityState.RESUMED 3962 || self.state == ActivityState.PAUSING) { 3963 mWindowManager.overridePendingAppTransition(packageName, 3964 enterAnim, exitAnim, null); 3965 } 3966 3967 Binder.restoreCallingIdentity(origId); 3968 } 3969 } 3970 3971 /** 3972 * Main function for removing an existing process from the activity manager 3973 * as a result of that process going away. Clears out all connections 3974 * to the process. 3975 */ 3976 private final void handleAppDiedLocked(ProcessRecord app, 3977 boolean restarting, boolean allowRestart) { 3978 int pid = app.pid; 3979 cleanUpApplicationRecordLocked(app, restarting, allowRestart, -1); 3980 if (!restarting) { 3981 removeLruProcessLocked(app); 3982 if (pid > 0) { 3983 ProcessList.remove(pid); 3984 } 3985 } 3986 3987 if (mProfileProc == app) { 3988 clearProfilerLocked(); 3989 } 3990 3991 // Remove this application's activities from active lists. 3992 boolean hasVisibleActivities = mStackSupervisor.handleAppDiedLocked(app); 3993 3994 app.activities.clear(); 3995 3996 if (app.instrumentationClass != null) { 3997 Slog.w(TAG, "Crash of app " + app.processName 3998 + " running instrumentation " + app.instrumentationClass); 3999 Bundle info = new Bundle(); 4000 info.putString("shortMsg", "Process crashed."); 4001 finishInstrumentationLocked(app, Activity.RESULT_CANCELED, info); 4002 } 4003 4004 if (!restarting) { 4005 if (!mStackSupervisor.resumeTopActivitiesLocked()) { 4006 // If there was nothing to resume, and we are not already 4007 // restarting this process, but there is a visible activity that 4008 // is hosted by the process... then make sure all visible 4009 // activities are running, taking care of restarting this 4010 // process. 4011 if (hasVisibleActivities) { 4012 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 4013 } 4014 } 4015 } 4016 } 4017 4018 private final int getLRURecordIndexForAppLocked(IApplicationThread thread) { 4019 IBinder threadBinder = thread.asBinder(); 4020 // Find the application record. 4021 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4022 ProcessRecord rec = mLruProcesses.get(i); 4023 if (rec.thread != null && rec.thread.asBinder() == threadBinder) { 4024 return i; 4025 } 4026 } 4027 return -1; 4028 } 4029 4030 final ProcessRecord getRecordForAppLocked( 4031 IApplicationThread thread) { 4032 if (thread == null) { 4033 return null; 4034 } 4035 4036 int appIndex = getLRURecordIndexForAppLocked(thread); 4037 return appIndex >= 0 ? mLruProcesses.get(appIndex) : null; 4038 } 4039 4040 final void doLowMemReportIfNeededLocked(ProcessRecord dyingProc) { 4041 // If there are no longer any background processes running, 4042 // and the app that died was not running instrumentation, 4043 // then tell everyone we are now low on memory. 4044 boolean haveBg = false; 4045 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4046 ProcessRecord rec = mLruProcesses.get(i); 4047 if (rec.thread != null 4048 && rec.setProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 4049 haveBg = true; 4050 break; 4051 } 4052 } 4053 4054 if (!haveBg) { 4055 boolean doReport = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 4056 if (doReport) { 4057 long now = SystemClock.uptimeMillis(); 4058 if (now < (mLastMemUsageReportTime+5*60*1000)) { 4059 doReport = false; 4060 } else { 4061 mLastMemUsageReportTime = now; 4062 } 4063 } 4064 final ArrayList<ProcessMemInfo> memInfos 4065 = doReport ? new ArrayList<ProcessMemInfo>(mLruProcesses.size()) : null; 4066 EventLog.writeEvent(EventLogTags.AM_LOW_MEMORY, mLruProcesses.size()); 4067 long now = SystemClock.uptimeMillis(); 4068 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4069 ProcessRecord rec = mLruProcesses.get(i); 4070 if (rec == dyingProc || rec.thread == null) { 4071 continue; 4072 } 4073 if (doReport) { 4074 memInfos.add(new ProcessMemInfo(rec.processName, rec.pid, rec.setAdj, 4075 rec.setProcState, rec.adjType, rec.makeAdjReason())); 4076 } 4077 if ((rec.lastLowMemory+GC_MIN_INTERVAL) <= now) { 4078 // The low memory report is overriding any current 4079 // state for a GC request. Make sure to do 4080 // heavy/important/visible/foreground processes first. 4081 if (rec.setAdj <= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 4082 rec.lastRequestedGc = 0; 4083 } else { 4084 rec.lastRequestedGc = rec.lastLowMemory; 4085 } 4086 rec.reportLowMemory = true; 4087 rec.lastLowMemory = now; 4088 mProcessesToGc.remove(rec); 4089 addProcessToGcListLocked(rec); 4090 } 4091 } 4092 if (doReport) { 4093 Message msg = mHandler.obtainMessage(REPORT_MEM_USAGE_MSG, memInfos); 4094 mHandler.sendMessage(msg); 4095 } 4096 scheduleAppGcsLocked(); 4097 } 4098 } 4099 4100 final void appDiedLocked(ProcessRecord app, int pid, 4101 IApplicationThread thread) { 4102 4103 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 4104 synchronized (stats) { 4105 stats.noteProcessDiedLocked(app.info.uid, pid); 4106 } 4107 4108 Process.killProcessGroup(app.info.uid, pid); 4109 4110 // Clean up already done if the process has been re-started. 4111 if (app.pid == pid && app.thread != null && 4112 app.thread.asBinder() == thread.asBinder()) { 4113 boolean doLowMem = app.instrumentationClass == null; 4114 boolean doOomAdj = doLowMem; 4115 if (!app.killedByAm) { 4116 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4117 + ") has died."); 4118 mAllowLowerMemLevel = true; 4119 } else { 4120 // Note that we always want to do oom adj to update our state with the 4121 // new number of procs. 4122 mAllowLowerMemLevel = false; 4123 doLowMem = false; 4124 } 4125 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4126 if (DEBUG_CLEANUP) Slog.v( 4127 TAG, "Dying app: " + app + ", pid: " + pid 4128 + ", thread: " + thread.asBinder()); 4129 handleAppDiedLocked(app, false, true); 4130 4131 if (doOomAdj) { 4132 updateOomAdjLocked(); 4133 } 4134 if (doLowMem) { 4135 doLowMemReportIfNeededLocked(app); 4136 } 4137 } else if (app.pid != pid) { 4138 // A new process has already been started. 4139 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4140 + ") has died and restarted (pid " + app.pid + ")."); 4141 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4142 } else if (DEBUG_PROCESSES) { 4143 Slog.d(TAG, "Received spurious death notification for thread " 4144 + thread.asBinder()); 4145 } 4146 } 4147 4148 /** 4149 * If a stack trace dump file is configured, dump process stack traces. 4150 * @param clearTraces causes the dump file to be erased prior to the new 4151 * traces being written, if true; when false, the new traces will be 4152 * appended to any existing file content. 4153 * @param firstPids of dalvik VM processes to dump stack traces for first 4154 * @param lastPids of dalvik VM processes to dump stack traces for last 4155 * @param nativeProcs optional list of native process names to dump stack crawls 4156 * @return file containing stack traces, or null if no dump file is configured 4157 */ 4158 public static File dumpStackTraces(boolean clearTraces, ArrayList<Integer> firstPids, 4159 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4160 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4161 if (tracesPath == null || tracesPath.length() == 0) { 4162 return null; 4163 } 4164 4165 File tracesFile = new File(tracesPath); 4166 try { 4167 File tracesDir = tracesFile.getParentFile(); 4168 if (!tracesDir.exists()) { 4169 tracesFile.mkdirs(); 4170 if (!SELinux.restorecon(tracesDir)) { 4171 return null; 4172 } 4173 } 4174 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4175 4176 if (clearTraces && tracesFile.exists()) tracesFile.delete(); 4177 tracesFile.createNewFile(); 4178 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4179 } catch (IOException e) { 4180 Slog.w(TAG, "Unable to prepare ANR traces file: " + tracesPath, e); 4181 return null; 4182 } 4183 4184 dumpStackTraces(tracesPath, firstPids, processCpuTracker, lastPids, nativeProcs); 4185 return tracesFile; 4186 } 4187 4188 private static void dumpStackTraces(String tracesPath, ArrayList<Integer> firstPids, 4189 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4190 // Use a FileObserver to detect when traces finish writing. 4191 // The order of traces is considered important to maintain for legibility. 4192 FileObserver observer = new FileObserver(tracesPath, FileObserver.CLOSE_WRITE) { 4193 @Override 4194 public synchronized void onEvent(int event, String path) { notify(); } 4195 }; 4196 4197 try { 4198 observer.startWatching(); 4199 4200 // First collect all of the stacks of the most important pids. 4201 if (firstPids != null) { 4202 try { 4203 int num = firstPids.size(); 4204 for (int i = 0; i < num; i++) { 4205 synchronized (observer) { 4206 Process.sendSignal(firstPids.get(i), Process.SIGNAL_QUIT); 4207 observer.wait(200); // Wait for write-close, give up after 200msec 4208 } 4209 } 4210 } catch (InterruptedException e) { 4211 Log.wtf(TAG, e); 4212 } 4213 } 4214 4215 // Next collect the stacks of the native pids 4216 if (nativeProcs != null) { 4217 int[] pids = Process.getPidsForCommands(nativeProcs); 4218 if (pids != null) { 4219 for (int pid : pids) { 4220 Debug.dumpNativeBacktraceToFile(pid, tracesPath); 4221 } 4222 } 4223 } 4224 4225 // Lastly, measure CPU usage. 4226 if (processCpuTracker != null) { 4227 processCpuTracker.init(); 4228 System.gc(); 4229 processCpuTracker.update(); 4230 try { 4231 synchronized (processCpuTracker) { 4232 processCpuTracker.wait(500); // measure over 1/2 second. 4233 } 4234 } catch (InterruptedException e) { 4235 } 4236 processCpuTracker.update(); 4237 4238 // We'll take the stack crawls of just the top apps using CPU. 4239 final int N = processCpuTracker.countWorkingStats(); 4240 int numProcs = 0; 4241 for (int i=0; i<N && numProcs<5; i++) { 4242 ProcessCpuTracker.Stats stats = processCpuTracker.getWorkingStats(i); 4243 if (lastPids.indexOfKey(stats.pid) >= 0) { 4244 numProcs++; 4245 try { 4246 synchronized (observer) { 4247 Process.sendSignal(stats.pid, Process.SIGNAL_QUIT); 4248 observer.wait(200); // Wait for write-close, give up after 200msec 4249 } 4250 } catch (InterruptedException e) { 4251 Log.wtf(TAG, e); 4252 } 4253 4254 } 4255 } 4256 } 4257 } finally { 4258 observer.stopWatching(); 4259 } 4260 } 4261 4262 final void logAppTooSlow(ProcessRecord app, long startTime, String msg) { 4263 if (true || IS_USER_BUILD) { 4264 return; 4265 } 4266 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4267 if (tracesPath == null || tracesPath.length() == 0) { 4268 return; 4269 } 4270 4271 StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads(); 4272 StrictMode.allowThreadDiskWrites(); 4273 try { 4274 final File tracesFile = new File(tracesPath); 4275 final File tracesDir = tracesFile.getParentFile(); 4276 final File tracesTmp = new File(tracesDir, "__tmp__"); 4277 try { 4278 if (!tracesDir.exists()) { 4279 tracesFile.mkdirs(); 4280 if (!SELinux.restorecon(tracesDir.getPath())) { 4281 return; 4282 } 4283 } 4284 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4285 4286 if (tracesFile.exists()) { 4287 tracesTmp.delete(); 4288 tracesFile.renameTo(tracesTmp); 4289 } 4290 StringBuilder sb = new StringBuilder(); 4291 Time tobj = new Time(); 4292 tobj.set(System.currentTimeMillis()); 4293 sb.append(tobj.format("%Y-%m-%d %H:%M:%S")); 4294 sb.append(": "); 4295 TimeUtils.formatDuration(SystemClock.uptimeMillis()-startTime, sb); 4296 sb.append(" since "); 4297 sb.append(msg); 4298 FileOutputStream fos = new FileOutputStream(tracesFile); 4299 fos.write(sb.toString().getBytes()); 4300 if (app == null) { 4301 fos.write("\n*** No application process!".getBytes()); 4302 } 4303 fos.close(); 4304 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4305 } catch (IOException e) { 4306 Slog.w(TAG, "Unable to prepare slow app traces file: " + tracesPath, e); 4307 return; 4308 } 4309 4310 if (app != null) { 4311 ArrayList<Integer> firstPids = new ArrayList<Integer>(); 4312 firstPids.add(app.pid); 4313 dumpStackTraces(tracesPath, firstPids, null, null, null); 4314 } 4315 4316 File lastTracesFile = null; 4317 File curTracesFile = null; 4318 for (int i=9; i>=0; i--) { 4319 String name = String.format(Locale.US, "slow%02d.txt", i); 4320 curTracesFile = new File(tracesDir, name); 4321 if (curTracesFile.exists()) { 4322 if (lastTracesFile != null) { 4323 curTracesFile.renameTo(lastTracesFile); 4324 } else { 4325 curTracesFile.delete(); 4326 } 4327 } 4328 lastTracesFile = curTracesFile; 4329 } 4330 tracesFile.renameTo(curTracesFile); 4331 if (tracesTmp.exists()) { 4332 tracesTmp.renameTo(tracesFile); 4333 } 4334 } finally { 4335 StrictMode.setThreadPolicy(oldPolicy); 4336 } 4337 } 4338 4339 final void appNotResponding(ProcessRecord app, ActivityRecord activity, 4340 ActivityRecord parent, boolean aboveSystem, final String annotation) { 4341 ArrayList<Integer> firstPids = new ArrayList<Integer>(5); 4342 SparseArray<Boolean> lastPids = new SparseArray<Boolean>(20); 4343 4344 if (mController != null) { 4345 try { 4346 // 0 == continue, -1 = kill process immediately 4347 int res = mController.appEarlyNotResponding(app.processName, app.pid, annotation); 4348 if (res < 0 && app.pid != MY_PID) { 4349 Process.killProcess(app.pid); 4350 Process.killProcessGroup(app.info.uid, app.pid); 4351 } 4352 } catch (RemoteException e) { 4353 mController = null; 4354 Watchdog.getInstance().setActivityController(null); 4355 } 4356 } 4357 4358 long anrTime = SystemClock.uptimeMillis(); 4359 if (MONITOR_CPU_USAGE) { 4360 updateCpuStatsNow(); 4361 } 4362 4363 synchronized (this) { 4364 // PowerManager.reboot() can block for a long time, so ignore ANRs while shutting down. 4365 if (mShuttingDown) { 4366 Slog.i(TAG, "During shutdown skipping ANR: " + app + " " + annotation); 4367 return; 4368 } else if (app.notResponding) { 4369 Slog.i(TAG, "Skipping duplicate ANR: " + app + " " + annotation); 4370 return; 4371 } else if (app.crashing) { 4372 Slog.i(TAG, "Crashing app skipping ANR: " + app + " " + annotation); 4373 return; 4374 } 4375 4376 // In case we come through here for the same app before completing 4377 // this one, mark as anring now so we will bail out. 4378 app.notResponding = true; 4379 4380 // Log the ANR to the event log. 4381 EventLog.writeEvent(EventLogTags.AM_ANR, app.userId, app.pid, 4382 app.processName, app.info.flags, annotation); 4383 4384 // Dump thread traces as quickly as we can, starting with "interesting" processes. 4385 firstPids.add(app.pid); 4386 4387 int parentPid = app.pid; 4388 if (parent != null && parent.app != null && parent.app.pid > 0) parentPid = parent.app.pid; 4389 if (parentPid != app.pid) firstPids.add(parentPid); 4390 4391 if (MY_PID != app.pid && MY_PID != parentPid) firstPids.add(MY_PID); 4392 4393 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 4394 ProcessRecord r = mLruProcesses.get(i); 4395 if (r != null && r.thread != null) { 4396 int pid = r.pid; 4397 if (pid > 0 && pid != app.pid && pid != parentPid && pid != MY_PID) { 4398 if (r.persistent) { 4399 firstPids.add(pid); 4400 } else { 4401 lastPids.put(pid, Boolean.TRUE); 4402 } 4403 } 4404 } 4405 } 4406 } 4407 4408 // Log the ANR to the main log. 4409 StringBuilder info = new StringBuilder(); 4410 info.setLength(0); 4411 info.append("ANR in ").append(app.processName); 4412 if (activity != null && activity.shortComponentName != null) { 4413 info.append(" (").append(activity.shortComponentName).append(")"); 4414 } 4415 info.append("\n"); 4416 info.append("PID: ").append(app.pid).append("\n"); 4417 if (annotation != null) { 4418 info.append("Reason: ").append(annotation).append("\n"); 4419 } 4420 if (parent != null && parent != activity) { 4421 info.append("Parent: ").append(parent.shortComponentName).append("\n"); 4422 } 4423 4424 final ProcessCpuTracker processCpuTracker = new ProcessCpuTracker(true); 4425 4426 File tracesFile = dumpStackTraces(true, firstPids, processCpuTracker, lastPids, 4427 NATIVE_STACKS_OF_INTEREST); 4428 4429 String cpuInfo = null; 4430 if (MONITOR_CPU_USAGE) { 4431 updateCpuStatsNow(); 4432 synchronized (mProcessCpuThread) { 4433 cpuInfo = mProcessCpuTracker.printCurrentState(anrTime); 4434 } 4435 info.append(processCpuTracker.printCurrentLoad()); 4436 info.append(cpuInfo); 4437 } 4438 4439 info.append(processCpuTracker.printCurrentState(anrTime)); 4440 4441 Slog.e(TAG, info.toString()); 4442 if (tracesFile == null) { 4443 // There is no trace file, so dump (only) the alleged culprit's threads to the log 4444 Process.sendSignal(app.pid, Process.SIGNAL_QUIT); 4445 } 4446 4447 addErrorToDropBox("anr", app, app.processName, activity, parent, annotation, 4448 cpuInfo, tracesFile, null); 4449 4450 if (mController != null) { 4451 try { 4452 // 0 == show dialog, 1 = keep waiting, -1 = kill process immediately 4453 int res = mController.appNotResponding(app.processName, app.pid, info.toString()); 4454 if (res != 0) { 4455 if (res < 0 && app.pid != MY_PID) { 4456 Process.killProcess(app.pid); 4457 Process.killProcessGroup(app.info.uid, app.pid); 4458 } else { 4459 synchronized (this) { 4460 mServices.scheduleServiceTimeoutLocked(app); 4461 } 4462 } 4463 return; 4464 } 4465 } catch (RemoteException e) { 4466 mController = null; 4467 Watchdog.getInstance().setActivityController(null); 4468 } 4469 } 4470 4471 // Unless configured otherwise, swallow ANRs in background processes & kill the process. 4472 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 4473 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 4474 4475 synchronized (this) { 4476 if (!showBackground && !app.isInterestingToUserLocked() && app.pid != MY_PID) { 4477 killUnneededProcessLocked(app, "background ANR"); 4478 return; 4479 } 4480 4481 // Set the app's notResponding state, and look up the errorReportReceiver 4482 makeAppNotRespondingLocked(app, 4483 activity != null ? activity.shortComponentName : null, 4484 annotation != null ? "ANR " + annotation : "ANR", 4485 info.toString()); 4486 4487 // Bring up the infamous App Not Responding dialog 4488 Message msg = Message.obtain(); 4489 HashMap<String, Object> map = new HashMap<String, Object>(); 4490 msg.what = SHOW_NOT_RESPONDING_MSG; 4491 msg.obj = map; 4492 msg.arg1 = aboveSystem ? 1 : 0; 4493 map.put("app", app); 4494 if (activity != null) { 4495 map.put("activity", activity); 4496 } 4497 4498 mHandler.sendMessage(msg); 4499 } 4500 } 4501 4502 final void showLaunchWarningLocked(final ActivityRecord cur, final ActivityRecord next) { 4503 if (!mLaunchWarningShown) { 4504 mLaunchWarningShown = true; 4505 mHandler.post(new Runnable() { 4506 @Override 4507 public void run() { 4508 synchronized (ActivityManagerService.this) { 4509 final Dialog d = new LaunchWarningWindow(mContext, cur, next); 4510 d.show(); 4511 mHandler.postDelayed(new Runnable() { 4512 @Override 4513 public void run() { 4514 synchronized (ActivityManagerService.this) { 4515 d.dismiss(); 4516 mLaunchWarningShown = false; 4517 } 4518 } 4519 }, 4000); 4520 } 4521 } 4522 }); 4523 } 4524 } 4525 4526 @Override 4527 public boolean clearApplicationUserData(final String packageName, 4528 final IPackageDataObserver observer, int userId) { 4529 enforceNotIsolatedCaller("clearApplicationUserData"); 4530 int uid = Binder.getCallingUid(); 4531 int pid = Binder.getCallingPid(); 4532 userId = handleIncomingUser(pid, uid, 4533 userId, false, ALLOW_FULL_ONLY, "clearApplicationUserData", null); 4534 long callingId = Binder.clearCallingIdentity(); 4535 try { 4536 IPackageManager pm = AppGlobals.getPackageManager(); 4537 int pkgUid = -1; 4538 synchronized(this) { 4539 try { 4540 pkgUid = pm.getPackageUid(packageName, userId); 4541 } catch (RemoteException e) { 4542 } 4543 if (pkgUid == -1) { 4544 Slog.w(TAG, "Invalid packageName: " + packageName); 4545 if (observer != null) { 4546 try { 4547 observer.onRemoveCompleted(packageName, false); 4548 } catch (RemoteException e) { 4549 Slog.i(TAG, "Observer no longer exists."); 4550 } 4551 } 4552 return false; 4553 } 4554 if (uid == pkgUid || checkComponentPermission( 4555 android.Manifest.permission.CLEAR_APP_USER_DATA, 4556 pid, uid, -1, true) 4557 == PackageManager.PERMISSION_GRANTED) { 4558 forceStopPackageLocked(packageName, pkgUid, "clear data"); 4559 } else { 4560 throw new SecurityException("PID " + pid + " does not have permission " 4561 + android.Manifest.permission.CLEAR_APP_USER_DATA + " to clear data" 4562 + " of package " + packageName); 4563 } 4564 } 4565 4566 try { 4567 // Clear application user data 4568 pm.clearApplicationUserData(packageName, observer, userId); 4569 4570 // Remove all permissions granted from/to this package 4571 removeUriPermissionsForPackageLocked(packageName, userId, true); 4572 4573 Intent intent = new Intent(Intent.ACTION_PACKAGE_DATA_CLEARED, 4574 Uri.fromParts("package", packageName, null)); 4575 intent.putExtra(Intent.EXTRA_UID, pkgUid); 4576 broadcastIntentInPackage("android", Process.SYSTEM_UID, intent, 4577 null, null, 0, null, null, null, false, false, userId); 4578 } catch (RemoteException e) { 4579 } 4580 } finally { 4581 Binder.restoreCallingIdentity(callingId); 4582 } 4583 return true; 4584 } 4585 4586 @Override 4587 public void killBackgroundProcesses(final String packageName, int userId) { 4588 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 4589 != PackageManager.PERMISSION_GRANTED && 4590 checkCallingPermission(android.Manifest.permission.RESTART_PACKAGES) 4591 != PackageManager.PERMISSION_GRANTED) { 4592 String msg = "Permission Denial: killBackgroundProcesses() from pid=" 4593 + Binder.getCallingPid() 4594 + ", uid=" + Binder.getCallingUid() 4595 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 4596 Slog.w(TAG, msg); 4597 throw new SecurityException(msg); 4598 } 4599 4600 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4601 userId, true, ALLOW_FULL_ONLY, "killBackgroundProcesses", null); 4602 long callingId = Binder.clearCallingIdentity(); 4603 try { 4604 IPackageManager pm = AppGlobals.getPackageManager(); 4605 synchronized(this) { 4606 int appId = -1; 4607 try { 4608 appId = UserHandle.getAppId(pm.getPackageUid(packageName, 0)); 4609 } catch (RemoteException e) { 4610 } 4611 if (appId == -1) { 4612 Slog.w(TAG, "Invalid packageName: " + packageName); 4613 return; 4614 } 4615 killPackageProcessesLocked(packageName, appId, userId, 4616 ProcessList.SERVICE_ADJ, false, true, true, false, "kill background"); 4617 } 4618 } finally { 4619 Binder.restoreCallingIdentity(callingId); 4620 } 4621 } 4622 4623 @Override 4624 public void killAllBackgroundProcesses() { 4625 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 4626 != PackageManager.PERMISSION_GRANTED) { 4627 String msg = "Permission Denial: killAllBackgroundProcesses() from pid=" 4628 + Binder.getCallingPid() 4629 + ", uid=" + Binder.getCallingUid() 4630 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 4631 Slog.w(TAG, msg); 4632 throw new SecurityException(msg); 4633 } 4634 4635 long callingId = Binder.clearCallingIdentity(); 4636 try { 4637 synchronized(this) { 4638 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 4639 final int NP = mProcessNames.getMap().size(); 4640 for (int ip=0; ip<NP; ip++) { 4641 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 4642 final int NA = apps.size(); 4643 for (int ia=0; ia<NA; ia++) { 4644 ProcessRecord app = apps.valueAt(ia); 4645 if (app.persistent) { 4646 // we don't kill persistent processes 4647 continue; 4648 } 4649 if (app.removed) { 4650 procs.add(app); 4651 } else if (app.setAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 4652 app.removed = true; 4653 procs.add(app); 4654 } 4655 } 4656 } 4657 4658 int N = procs.size(); 4659 for (int i=0; i<N; i++) { 4660 removeProcessLocked(procs.get(i), false, true, "kill all background"); 4661 } 4662 mAllowLowerMemLevel = true; 4663 updateOomAdjLocked(); 4664 doLowMemReportIfNeededLocked(null); 4665 } 4666 } finally { 4667 Binder.restoreCallingIdentity(callingId); 4668 } 4669 } 4670 4671 @Override 4672 public void forceStopPackage(final String packageName, int userId) { 4673 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4674 != PackageManager.PERMISSION_GRANTED) { 4675 String msg = "Permission Denial: forceStopPackage() from pid=" 4676 + Binder.getCallingPid() 4677 + ", uid=" + Binder.getCallingUid() 4678 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4679 Slog.w(TAG, msg); 4680 throw new SecurityException(msg); 4681 } 4682 final int callingPid = Binder.getCallingPid(); 4683 userId = handleIncomingUser(callingPid, Binder.getCallingUid(), 4684 userId, true, ALLOW_FULL_ONLY, "forceStopPackage", null); 4685 long callingId = Binder.clearCallingIdentity(); 4686 try { 4687 IPackageManager pm = AppGlobals.getPackageManager(); 4688 synchronized(this) { 4689 int[] users = userId == UserHandle.USER_ALL 4690 ? getUsersLocked() : new int[] { userId }; 4691 for (int user : users) { 4692 int pkgUid = -1; 4693 try { 4694 pkgUid = pm.getPackageUid(packageName, user); 4695 } catch (RemoteException e) { 4696 } 4697 if (pkgUid == -1) { 4698 Slog.w(TAG, "Invalid packageName: " + packageName); 4699 continue; 4700 } 4701 try { 4702 pm.setPackageStoppedState(packageName, true, user); 4703 } catch (RemoteException e) { 4704 } catch (IllegalArgumentException e) { 4705 Slog.w(TAG, "Failed trying to unstop package " 4706 + packageName + ": " + e); 4707 } 4708 if (isUserRunningLocked(user, false)) { 4709 forceStopPackageLocked(packageName, pkgUid, "from pid " + callingPid); 4710 } 4711 } 4712 } 4713 } finally { 4714 Binder.restoreCallingIdentity(callingId); 4715 } 4716 } 4717 4718 /* 4719 * The pkg name and app id have to be specified. 4720 */ 4721 @Override 4722 public void killApplicationWithAppId(String pkg, int appid, String reason) { 4723 if (pkg == null) { 4724 return; 4725 } 4726 // Make sure the uid is valid. 4727 if (appid < 0) { 4728 Slog.w(TAG, "Invalid appid specified for pkg : " + pkg); 4729 return; 4730 } 4731 int callerUid = Binder.getCallingUid(); 4732 // Only the system server can kill an application 4733 if (callerUid == Process.SYSTEM_UID) { 4734 // Post an aysnc message to kill the application 4735 Message msg = mHandler.obtainMessage(KILL_APPLICATION_MSG); 4736 msg.arg1 = appid; 4737 msg.arg2 = 0; 4738 Bundle bundle = new Bundle(); 4739 bundle.putString("pkg", pkg); 4740 bundle.putString("reason", reason); 4741 msg.obj = bundle; 4742 mHandler.sendMessage(msg); 4743 } else { 4744 throw new SecurityException(callerUid + " cannot kill pkg: " + 4745 pkg); 4746 } 4747 } 4748 4749 @Override 4750 public void closeSystemDialogs(String reason) { 4751 enforceNotIsolatedCaller("closeSystemDialogs"); 4752 4753 final int pid = Binder.getCallingPid(); 4754 final int uid = Binder.getCallingUid(); 4755 final long origId = Binder.clearCallingIdentity(); 4756 try { 4757 synchronized (this) { 4758 // Only allow this from foreground processes, so that background 4759 // applications can't abuse it to prevent system UI from being shown. 4760 if (uid >= Process.FIRST_APPLICATION_UID) { 4761 ProcessRecord proc; 4762 synchronized (mPidsSelfLocked) { 4763 proc = mPidsSelfLocked.get(pid); 4764 } 4765 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 4766 Slog.w(TAG, "Ignoring closeSystemDialogs " + reason 4767 + " from background process " + proc); 4768 return; 4769 } 4770 } 4771 closeSystemDialogsLocked(reason); 4772 } 4773 } finally { 4774 Binder.restoreCallingIdentity(origId); 4775 } 4776 } 4777 4778 void closeSystemDialogsLocked(String reason) { 4779 Intent intent = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS); 4780 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4781 | Intent.FLAG_RECEIVER_FOREGROUND); 4782 if (reason != null) { 4783 intent.putExtra("reason", reason); 4784 } 4785 mWindowManager.closeSystemDialogs(reason); 4786 4787 mStackSupervisor.closeSystemDialogsLocked(); 4788 4789 broadcastIntentLocked(null, null, intent, null, 4790 null, 0, null, null, null, AppOpsManager.OP_NONE, false, false, -1, 4791 Process.SYSTEM_UID, UserHandle.USER_ALL); 4792 } 4793 4794 @Override 4795 public Debug.MemoryInfo[] getProcessMemoryInfo(int[] pids) { 4796 enforceNotIsolatedCaller("getProcessMemoryInfo"); 4797 Debug.MemoryInfo[] infos = new Debug.MemoryInfo[pids.length]; 4798 for (int i=pids.length-1; i>=0; i--) { 4799 ProcessRecord proc; 4800 int oomAdj; 4801 synchronized (this) { 4802 synchronized (mPidsSelfLocked) { 4803 proc = mPidsSelfLocked.get(pids[i]); 4804 oomAdj = proc != null ? proc.setAdj : 0; 4805 } 4806 } 4807 infos[i] = new Debug.MemoryInfo(); 4808 Debug.getMemoryInfo(pids[i], infos[i]); 4809 if (proc != null) { 4810 synchronized (this) { 4811 if (proc.thread != null && proc.setAdj == oomAdj) { 4812 // Record this for posterity if the process has been stable. 4813 proc.baseProcessTracker.addPss(infos[i].getTotalPss(), 4814 infos[i].getTotalUss(), false, proc.pkgList); 4815 } 4816 } 4817 } 4818 } 4819 return infos; 4820 } 4821 4822 @Override 4823 public long[] getProcessPss(int[] pids) { 4824 enforceNotIsolatedCaller("getProcessPss"); 4825 long[] pss = new long[pids.length]; 4826 for (int i=pids.length-1; i>=0; i--) { 4827 ProcessRecord proc; 4828 int oomAdj; 4829 synchronized (this) { 4830 synchronized (mPidsSelfLocked) { 4831 proc = mPidsSelfLocked.get(pids[i]); 4832 oomAdj = proc != null ? proc.setAdj : 0; 4833 } 4834 } 4835 long[] tmpUss = new long[1]; 4836 pss[i] = Debug.getPss(pids[i], tmpUss); 4837 if (proc != null) { 4838 synchronized (this) { 4839 if (proc.thread != null && proc.setAdj == oomAdj) { 4840 // Record this for posterity if the process has been stable. 4841 proc.baseProcessTracker.addPss(pss[i], tmpUss[0], false, proc.pkgList); 4842 } 4843 } 4844 } 4845 } 4846 return pss; 4847 } 4848 4849 @Override 4850 public void killApplicationProcess(String processName, int uid) { 4851 if (processName == null) { 4852 return; 4853 } 4854 4855 int callerUid = Binder.getCallingUid(); 4856 // Only the system server can kill an application 4857 if (callerUid == Process.SYSTEM_UID) { 4858 synchronized (this) { 4859 ProcessRecord app = getProcessRecordLocked(processName, uid, true); 4860 if (app != null && app.thread != null) { 4861 try { 4862 app.thread.scheduleSuicide(); 4863 } catch (RemoteException e) { 4864 // If the other end already died, then our work here is done. 4865 } 4866 } else { 4867 Slog.w(TAG, "Process/uid not found attempting kill of " 4868 + processName + " / " + uid); 4869 } 4870 } 4871 } else { 4872 throw new SecurityException(callerUid + " cannot kill app process: " + 4873 processName); 4874 } 4875 } 4876 4877 private void forceStopPackageLocked(final String packageName, int uid, String reason) { 4878 forceStopPackageLocked(packageName, UserHandle.getAppId(uid), false, 4879 false, true, false, false, UserHandle.getUserId(uid), reason); 4880 Intent intent = new Intent(Intent.ACTION_PACKAGE_RESTARTED, 4881 Uri.fromParts("package", packageName, null)); 4882 if (!mProcessesReady) { 4883 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4884 | Intent.FLAG_RECEIVER_FOREGROUND); 4885 } 4886 intent.putExtra(Intent.EXTRA_UID, uid); 4887 intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(uid)); 4888 broadcastIntentLocked(null, null, intent, 4889 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 4890 false, false, 4891 MY_PID, Process.SYSTEM_UID, UserHandle.getUserId(uid)); 4892 } 4893 4894 private void forceStopUserLocked(int userId, String reason) { 4895 forceStopPackageLocked(null, -1, false, false, true, false, false, userId, reason); 4896 Intent intent = new Intent(Intent.ACTION_USER_STOPPED); 4897 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4898 | Intent.FLAG_RECEIVER_FOREGROUND); 4899 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 4900 broadcastIntentLocked(null, null, intent, 4901 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 4902 false, false, 4903 MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 4904 } 4905 4906 private final boolean killPackageProcessesLocked(String packageName, int appId, 4907 int userId, int minOomAdj, boolean callerWillRestart, boolean allowRestart, 4908 boolean doit, boolean evenPersistent, String reason) { 4909 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 4910 4911 // Remove all processes this package may have touched: all with the 4912 // same UID (except for the system or root user), and all whose name 4913 // matches the package name. 4914 final String procNamePrefix = packageName != null ? (packageName + ":") : null; 4915 final int NP = mProcessNames.getMap().size(); 4916 for (int ip=0; ip<NP; ip++) { 4917 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 4918 final int NA = apps.size(); 4919 for (int ia=0; ia<NA; ia++) { 4920 ProcessRecord app = apps.valueAt(ia); 4921 if (app.persistent && !evenPersistent) { 4922 // we don't kill persistent processes 4923 continue; 4924 } 4925 if (app.removed) { 4926 if (doit) { 4927 procs.add(app); 4928 } 4929 continue; 4930 } 4931 4932 // Skip process if it doesn't meet our oom adj requirement. 4933 if (app.setAdj < minOomAdj) { 4934 continue; 4935 } 4936 4937 // If no package is specified, we call all processes under the 4938 // give user id. 4939 if (packageName == null) { 4940 if (app.userId != userId) { 4941 continue; 4942 } 4943 if (appId >= 0 && UserHandle.getAppId(app.uid) != appId) { 4944 continue; 4945 } 4946 // Package has been specified, we want to hit all processes 4947 // that match it. We need to qualify this by the processes 4948 // that are running under the specified app and user ID. 4949 } else { 4950 if (UserHandle.getAppId(app.uid) != appId) { 4951 continue; 4952 } 4953 if (userId != UserHandle.USER_ALL && app.userId != userId) { 4954 continue; 4955 } 4956 if (!app.pkgList.containsKey(packageName)) { 4957 continue; 4958 } 4959 } 4960 4961 // Process has passed all conditions, kill it! 4962 if (!doit) { 4963 return true; 4964 } 4965 app.removed = true; 4966 procs.add(app); 4967 } 4968 } 4969 4970 int N = procs.size(); 4971 for (int i=0; i<N; i++) { 4972 removeProcessLocked(procs.get(i), callerWillRestart, allowRestart, reason); 4973 } 4974 updateOomAdjLocked(); 4975 return N > 0; 4976 } 4977 4978 private final boolean forceStopPackageLocked(String name, int appId, 4979 boolean callerWillRestart, boolean purgeCache, boolean doit, 4980 boolean evenPersistent, boolean uninstalling, int userId, String reason) { 4981 int i; 4982 int N; 4983 4984 if (userId == UserHandle.USER_ALL && name == null) { 4985 Slog.w(TAG, "Can't force stop all processes of all users, that is insane!"); 4986 } 4987 4988 if (appId < 0 && name != null) { 4989 try { 4990 appId = UserHandle.getAppId( 4991 AppGlobals.getPackageManager().getPackageUid(name, 0)); 4992 } catch (RemoteException e) { 4993 } 4994 } 4995 4996 if (doit) { 4997 if (name != null) { 4998 Slog.i(TAG, "Force stopping " + name + " appid=" + appId 4999 + " user=" + userId + ": " + reason); 5000 } else { 5001 Slog.i(TAG, "Force stopping u" + userId + ": " + reason); 5002 } 5003 5004 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 5005 for (int ip=pmap.size()-1; ip>=0; ip--) { 5006 SparseArray<Long> ba = pmap.valueAt(ip); 5007 for (i=ba.size()-1; i>=0; i--) { 5008 boolean remove = false; 5009 final int entUid = ba.keyAt(i); 5010 if (name != null) { 5011 if (userId == UserHandle.USER_ALL) { 5012 if (UserHandle.getAppId(entUid) == appId) { 5013 remove = true; 5014 } 5015 } else { 5016 if (entUid == UserHandle.getUid(userId, appId)) { 5017 remove = true; 5018 } 5019 } 5020 } else if (UserHandle.getUserId(entUid) == userId) { 5021 remove = true; 5022 } 5023 if (remove) { 5024 ba.removeAt(i); 5025 } 5026 } 5027 if (ba.size() == 0) { 5028 pmap.removeAt(ip); 5029 } 5030 } 5031 } 5032 5033 boolean didSomething = killPackageProcessesLocked(name, appId, userId, 5034 -100, callerWillRestart, true, doit, evenPersistent, 5035 name == null ? ("stop user " + userId) : ("stop " + name)); 5036 5037 if (mStackSupervisor.forceStopPackageLocked(name, doit, evenPersistent, userId)) { 5038 if (!doit) { 5039 return true; 5040 } 5041 didSomething = true; 5042 } 5043 5044 if (mServices.forceStopLocked(name, userId, evenPersistent, doit)) { 5045 if (!doit) { 5046 return true; 5047 } 5048 didSomething = true; 5049 } 5050 5051 if (name == null) { 5052 // Remove all sticky broadcasts from this user. 5053 mStickyBroadcasts.remove(userId); 5054 } 5055 5056 ArrayList<ContentProviderRecord> providers = new ArrayList<ContentProviderRecord>(); 5057 if (mProviderMap.collectForceStopProviders(name, appId, doit, evenPersistent, 5058 userId, providers)) { 5059 if (!doit) { 5060 return true; 5061 } 5062 didSomething = true; 5063 } 5064 N = providers.size(); 5065 for (i=0; i<N; i++) { 5066 removeDyingProviderLocked(null, providers.get(i), true); 5067 } 5068 5069 // Remove transient permissions granted from/to this package/user 5070 removeUriPermissionsForPackageLocked(name, userId, false); 5071 5072 if (name == null || uninstalling) { 5073 // Remove pending intents. For now we only do this when force 5074 // stopping users, because we have some problems when doing this 5075 // for packages -- app widgets are not currently cleaned up for 5076 // such packages, so they can be left with bad pending intents. 5077 if (mIntentSenderRecords.size() > 0) { 5078 Iterator<WeakReference<PendingIntentRecord>> it 5079 = mIntentSenderRecords.values().iterator(); 5080 while (it.hasNext()) { 5081 WeakReference<PendingIntentRecord> wpir = it.next(); 5082 if (wpir == null) { 5083 it.remove(); 5084 continue; 5085 } 5086 PendingIntentRecord pir = wpir.get(); 5087 if (pir == null) { 5088 it.remove(); 5089 continue; 5090 } 5091 if (name == null) { 5092 // Stopping user, remove all objects for the user. 5093 if (pir.key.userId != userId) { 5094 // Not the same user, skip it. 5095 continue; 5096 } 5097 } else { 5098 if (UserHandle.getAppId(pir.uid) != appId) { 5099 // Different app id, skip it. 5100 continue; 5101 } 5102 if (userId != UserHandle.USER_ALL && pir.key.userId != userId) { 5103 // Different user, skip it. 5104 continue; 5105 } 5106 if (!pir.key.packageName.equals(name)) { 5107 // Different package, skip it. 5108 continue; 5109 } 5110 } 5111 if (!doit) { 5112 return true; 5113 } 5114 didSomething = true; 5115 it.remove(); 5116 pir.canceled = true; 5117 if (pir.key.activity != null) { 5118 pir.key.activity.pendingResults.remove(pir.ref); 5119 } 5120 } 5121 } 5122 } 5123 5124 if (doit) { 5125 if (purgeCache && name != null) { 5126 AttributeCache ac = AttributeCache.instance(); 5127 if (ac != null) { 5128 ac.removePackage(name); 5129 } 5130 } 5131 if (mBooted) { 5132 mStackSupervisor.resumeTopActivitiesLocked(); 5133 mStackSupervisor.scheduleIdleLocked(); 5134 } 5135 } 5136 5137 return didSomething; 5138 } 5139 5140 private final boolean removeProcessLocked(ProcessRecord app, 5141 boolean callerWillRestart, boolean allowRestart, String reason) { 5142 final String name = app.processName; 5143 final int uid = app.uid; 5144 if (DEBUG_PROCESSES) Slog.d( 5145 TAG, "Force removing proc " + app.toShortString() + " (" + name 5146 + "/" + uid + ")"); 5147 5148 mProcessNames.remove(name, uid); 5149 mIsolatedProcesses.remove(app.uid); 5150 if (mHeavyWeightProcess == app) { 5151 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5152 mHeavyWeightProcess.userId, 0)); 5153 mHeavyWeightProcess = null; 5154 } 5155 boolean needRestart = false; 5156 if (app.pid > 0 && app.pid != MY_PID) { 5157 int pid = app.pid; 5158 synchronized (mPidsSelfLocked) { 5159 mPidsSelfLocked.remove(pid); 5160 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5161 } 5162 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 5163 if (app.isolated) { 5164 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5165 } 5166 killUnneededProcessLocked(app, reason); 5167 Process.killProcessGroup(app.info.uid, app.pid); 5168 handleAppDiedLocked(app, true, allowRestart); 5169 removeLruProcessLocked(app); 5170 5171 if (app.persistent && !app.isolated) { 5172 if (!callerWillRestart) { 5173 addAppLocked(app.info, false, null /* ABI override */); 5174 } else { 5175 needRestart = true; 5176 } 5177 } 5178 } else { 5179 mRemovedProcesses.add(app); 5180 } 5181 5182 return needRestart; 5183 } 5184 5185 private final void processStartTimedOutLocked(ProcessRecord app) { 5186 final int pid = app.pid; 5187 boolean gone = false; 5188 synchronized (mPidsSelfLocked) { 5189 ProcessRecord knownApp = mPidsSelfLocked.get(pid); 5190 if (knownApp != null && knownApp.thread == null) { 5191 mPidsSelfLocked.remove(pid); 5192 gone = true; 5193 } 5194 } 5195 5196 if (gone) { 5197 Slog.w(TAG, "Process " + app + " failed to attach"); 5198 EventLog.writeEvent(EventLogTags.AM_PROCESS_START_TIMEOUT, app.userId, 5199 pid, app.uid, app.processName); 5200 mProcessNames.remove(app.processName, app.uid); 5201 mIsolatedProcesses.remove(app.uid); 5202 if (mHeavyWeightProcess == app) { 5203 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5204 mHeavyWeightProcess.userId, 0)); 5205 mHeavyWeightProcess = null; 5206 } 5207 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 5208 if (app.isolated) { 5209 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5210 } 5211 // Take care of any launching providers waiting for this process. 5212 checkAppInLaunchingProvidersLocked(app, true); 5213 // Take care of any services that are waiting for the process. 5214 mServices.processStartTimedOutLocked(app); 5215 killUnneededProcessLocked(app, "start timeout"); 5216 if (mBackupTarget != null && mBackupTarget.app.pid == pid) { 5217 Slog.w(TAG, "Unattached app died before backup, skipping"); 5218 try { 5219 IBackupManager bm = IBackupManager.Stub.asInterface( 5220 ServiceManager.getService(Context.BACKUP_SERVICE)); 5221 bm.agentDisconnected(app.info.packageName); 5222 } catch (RemoteException e) { 5223 // Can't happen; the backup manager is local 5224 } 5225 } 5226 if (isPendingBroadcastProcessLocked(pid)) { 5227 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 5228 skipPendingBroadcastLocked(pid); 5229 } 5230 } else { 5231 Slog.w(TAG, "Spurious process start timeout - pid not known for " + app); 5232 } 5233 } 5234 5235 private final boolean attachApplicationLocked(IApplicationThread thread, 5236 int pid) { 5237 5238 // Find the application record that is being attached... either via 5239 // the pid if we are running in multiple processes, or just pull the 5240 // next app record if we are emulating process with anonymous threads. 5241 ProcessRecord app; 5242 if (pid != MY_PID && pid >= 0) { 5243 synchronized (mPidsSelfLocked) { 5244 app = mPidsSelfLocked.get(pid); 5245 } 5246 } else { 5247 app = null; 5248 } 5249 5250 if (app == null) { 5251 Slog.w(TAG, "No pending application record for pid " + pid 5252 + " (IApplicationThread " + thread + "); dropping process"); 5253 EventLog.writeEvent(EventLogTags.AM_DROP_PROCESS, pid); 5254 if (pid > 0 && pid != MY_PID) { 5255 Process.killProcessQuiet(pid); 5256 //TODO: Process.killProcessGroup(app.info.uid, pid); 5257 } else { 5258 try { 5259 thread.scheduleExit(); 5260 } catch (Exception e) { 5261 // Ignore exceptions. 5262 } 5263 } 5264 return false; 5265 } 5266 5267 // If this application record is still attached to a previous 5268 // process, clean it up now. 5269 if (app.thread != null) { 5270 handleAppDiedLocked(app, true, true); 5271 } 5272 5273 // Tell the process all about itself. 5274 5275 if (localLOGV) Slog.v( 5276 TAG, "Binding process pid " + pid + " to record " + app); 5277 5278 final String processName = app.processName; 5279 try { 5280 AppDeathRecipient adr = new AppDeathRecipient( 5281 app, pid, thread); 5282 thread.asBinder().linkToDeath(adr, 0); 5283 app.deathRecipient = adr; 5284 } catch (RemoteException e) { 5285 app.resetPackageList(mProcessStats); 5286 startProcessLocked(app, "link fail", processName, null /* ABI override */); 5287 return false; 5288 } 5289 5290 EventLog.writeEvent(EventLogTags.AM_PROC_BOUND, app.userId, app.pid, app.processName); 5291 5292 app.makeActive(thread, mProcessStats); 5293 app.curAdj = app.setAdj = -100; 5294 app.curSchedGroup = app.setSchedGroup = Process.THREAD_GROUP_DEFAULT; 5295 app.forcingToForeground = null; 5296 updateProcessForegroundLocked(app, false, false); 5297 app.hasShownUi = false; 5298 app.debugging = false; 5299 app.cached = false; 5300 5301 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5302 5303 boolean normalMode = mProcessesReady || isAllowedWhileBooting(app.info); 5304 List<ProviderInfo> providers = normalMode ? generateApplicationProvidersLocked(app) : null; 5305 5306 if (!normalMode) { 5307 Slog.i(TAG, "Launching preboot mode app: " + app); 5308 } 5309 5310 if (localLOGV) Slog.v( 5311 TAG, "New app record " + app 5312 + " thread=" + thread.asBinder() + " pid=" + pid); 5313 try { 5314 int testMode = IApplicationThread.DEBUG_OFF; 5315 if (mDebugApp != null && mDebugApp.equals(processName)) { 5316 testMode = mWaitForDebugger 5317 ? IApplicationThread.DEBUG_WAIT 5318 : IApplicationThread.DEBUG_ON; 5319 app.debugging = true; 5320 if (mDebugTransient) { 5321 mDebugApp = mOrigDebugApp; 5322 mWaitForDebugger = mOrigWaitForDebugger; 5323 } 5324 } 5325 String profileFile = app.instrumentationProfileFile; 5326 ParcelFileDescriptor profileFd = null; 5327 boolean profileAutoStop = false; 5328 if (mProfileApp != null && mProfileApp.equals(processName)) { 5329 mProfileProc = app; 5330 profileFile = mProfileFile; 5331 profileFd = mProfileFd; 5332 profileAutoStop = mAutoStopProfiler; 5333 } 5334 boolean enableOpenGlTrace = false; 5335 if (mOpenGlTraceApp != null && mOpenGlTraceApp.equals(processName)) { 5336 enableOpenGlTrace = true; 5337 mOpenGlTraceApp = null; 5338 } 5339 5340 // If the app is being launched for restore or full backup, set it up specially 5341 boolean isRestrictedBackupMode = false; 5342 if (mBackupTarget != null && mBackupAppName.equals(processName)) { 5343 isRestrictedBackupMode = (mBackupTarget.backupMode == BackupRecord.RESTORE) 5344 || (mBackupTarget.backupMode == BackupRecord.RESTORE_FULL) 5345 || (mBackupTarget.backupMode == BackupRecord.BACKUP_FULL); 5346 } 5347 5348 ensurePackageDexOpt(app.instrumentationInfo != null 5349 ? app.instrumentationInfo.packageName 5350 : app.info.packageName); 5351 if (app.instrumentationClass != null) { 5352 ensurePackageDexOpt(app.instrumentationClass.getPackageName()); 5353 } 5354 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Binding proc " 5355 + processName + " with config " + mConfiguration); 5356 ApplicationInfo appInfo = app.instrumentationInfo != null 5357 ? app.instrumentationInfo : app.info; 5358 app.compat = compatibilityInfoForPackageLocked(appInfo); 5359 if (profileFd != null) { 5360 profileFd = profileFd.dup(); 5361 } 5362 thread.bindApplication(processName, appInfo, providers, 5363 app.instrumentationClass, profileFile, profileFd, profileAutoStop, 5364 app.instrumentationArguments, app.instrumentationWatcher, 5365 app.instrumentationUiAutomationConnection, testMode, enableOpenGlTrace, 5366 isRestrictedBackupMode || !normalMode, app.persistent, 5367 new Configuration(mConfiguration), app.compat, getCommonServicesLocked(), 5368 mCoreSettingsObserver.getCoreSettingsLocked()); 5369 updateLruProcessLocked(app, false, null); 5370 app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis(); 5371 } catch (Exception e) { 5372 // todo: Yikes! What should we do? For now we will try to 5373 // start another process, but that could easily get us in 5374 // an infinite loop of restarting processes... 5375 Slog.w(TAG, "Exception thrown during bind!", e); 5376 5377 app.resetPackageList(mProcessStats); 5378 app.unlinkDeathRecipient(); 5379 startProcessLocked(app, "bind fail", processName, null /* ABI override */); 5380 return false; 5381 } 5382 5383 // Remove this record from the list of starting applications. 5384 mPersistentStartingProcesses.remove(app); 5385 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 5386 "Attach application locked removing on hold: " + app); 5387 mProcessesOnHold.remove(app); 5388 5389 boolean badApp = false; 5390 boolean didSomething = false; 5391 5392 // See if the top visible activity is waiting to run in this process... 5393 if (normalMode) { 5394 try { 5395 if (mStackSupervisor.attachApplicationLocked(app)) { 5396 didSomething = true; 5397 } 5398 } catch (Exception e) { 5399 badApp = true; 5400 } 5401 } 5402 5403 // Find any services that should be running in this process... 5404 if (!badApp) { 5405 try { 5406 didSomething |= mServices.attachApplicationLocked(app, processName); 5407 } catch (Exception e) { 5408 badApp = true; 5409 } 5410 } 5411 5412 // Check if a next-broadcast receiver is in this process... 5413 if (!badApp && isPendingBroadcastProcessLocked(pid)) { 5414 try { 5415 didSomething |= sendPendingBroadcastsLocked(app); 5416 } catch (Exception e) { 5417 // If the app died trying to launch the receiver we declare it 'bad' 5418 badApp = true; 5419 } 5420 } 5421 5422 // Check whether the next backup agent is in this process... 5423 if (!badApp && mBackupTarget != null && mBackupTarget.appInfo.uid == app.uid) { 5424 if (DEBUG_BACKUP) Slog.v(TAG, "New app is backup target, launching agent for " + app); 5425 ensurePackageDexOpt(mBackupTarget.appInfo.packageName); 5426 try { 5427 thread.scheduleCreateBackupAgent(mBackupTarget.appInfo, 5428 compatibilityInfoForPackageLocked(mBackupTarget.appInfo), 5429 mBackupTarget.backupMode); 5430 } catch (Exception e) { 5431 Slog.w(TAG, "Exception scheduling backup agent creation: "); 5432 e.printStackTrace(); 5433 } 5434 } 5435 5436 if (badApp) { 5437 // todo: Also need to kill application to deal with all 5438 // kinds of exceptions. 5439 handleAppDiedLocked(app, false, true); 5440 return false; 5441 } 5442 5443 if (!didSomething) { 5444 updateOomAdjLocked(); 5445 } 5446 5447 return true; 5448 } 5449 5450 @Override 5451 public final void attachApplication(IApplicationThread thread) { 5452 synchronized (this) { 5453 int callingPid = Binder.getCallingPid(); 5454 final long origId = Binder.clearCallingIdentity(); 5455 attachApplicationLocked(thread, callingPid); 5456 Binder.restoreCallingIdentity(origId); 5457 } 5458 } 5459 5460 @Override 5461 public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) { 5462 final long origId = Binder.clearCallingIdentity(); 5463 synchronized (this) { 5464 ActivityStack stack = ActivityRecord.getStackLocked(token); 5465 if (stack != null) { 5466 ActivityRecord r = 5467 mStackSupervisor.activityIdleInternalLocked(token, false, config); 5468 if (stopProfiling) { 5469 if ((mProfileProc == r.app) && (mProfileFd != null)) { 5470 try { 5471 mProfileFd.close(); 5472 } catch (IOException e) { 5473 } 5474 clearProfilerLocked(); 5475 } 5476 } 5477 } 5478 } 5479 Binder.restoreCallingIdentity(origId); 5480 } 5481 5482 void enableScreenAfterBoot() { 5483 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN, 5484 SystemClock.uptimeMillis()); 5485 mWindowManager.enableScreenAfterBoot(); 5486 5487 synchronized (this) { 5488 updateEventDispatchingLocked(); 5489 } 5490 } 5491 5492 @Override 5493 public void showBootMessage(final CharSequence msg, final boolean always) { 5494 enforceNotIsolatedCaller("showBootMessage"); 5495 mWindowManager.showBootMessage(msg, always); 5496 } 5497 5498 @Override 5499 public void dismissKeyguardOnNextActivity() { 5500 enforceNotIsolatedCaller("dismissKeyguardOnNextActivity"); 5501 final long token = Binder.clearCallingIdentity(); 5502 try { 5503 synchronized (this) { 5504 if (DEBUG_LOCKSCREEN) logLockScreen(""); 5505 if (mLockScreenShown) { 5506 mLockScreenShown = false; 5507 comeOutOfSleepIfNeededLocked(); 5508 } 5509 mStackSupervisor.setDismissKeyguard(true); 5510 } 5511 } finally { 5512 Binder.restoreCallingIdentity(token); 5513 } 5514 } 5515 5516 final void finishBooting() { 5517 // Register receivers to handle package update events 5518 mPackageMonitor.register(mContext, Looper.getMainLooper(), false); 5519 5520 synchronized (this) { 5521 // Ensure that any processes we had put on hold are now started 5522 // up. 5523 final int NP = mProcessesOnHold.size(); 5524 if (NP > 0) { 5525 ArrayList<ProcessRecord> procs = 5526 new ArrayList<ProcessRecord>(mProcessesOnHold); 5527 for (int ip=0; ip<NP; ip++) { 5528 if (DEBUG_PROCESSES) Slog.v(TAG, "Starting process on hold: " 5529 + procs.get(ip)); 5530 startProcessLocked(procs.get(ip), "on-hold", null, null /* ABI override */); 5531 } 5532 } 5533 5534 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 5535 // Start looking for apps that are abusing wake locks. 5536 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 5537 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 5538 // Tell anyone interested that we are done booting! 5539 SystemProperties.set("sys.boot_completed", "1"); 5540 SystemProperties.set("dev.bootcomplete", "1"); 5541 for (int i=0; i<mStartedUsers.size(); i++) { 5542 UserStartedState uss = mStartedUsers.valueAt(i); 5543 if (uss.mState == UserStartedState.STATE_BOOTING) { 5544 uss.mState = UserStartedState.STATE_RUNNING; 5545 final int userId = mStartedUsers.keyAt(i); 5546 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 5547 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 5548 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 5549 broadcastIntentLocked(null, null, intent, null, 5550 new IIntentReceiver.Stub() { 5551 @Override 5552 public void performReceive(Intent intent, int resultCode, 5553 String data, Bundle extras, boolean ordered, 5554 boolean sticky, int sendingUser) { 5555 synchronized (ActivityManagerService.this) { 5556 requestPssAllProcsLocked(SystemClock.uptimeMillis(), 5557 true, false); 5558 } 5559 } 5560 }, 5561 0, null, null, 5562 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, 5563 AppOpsManager.OP_NONE, true, false, MY_PID, Process.SYSTEM_UID, 5564 userId); 5565 } 5566 } 5567 scheduleStartProfilesLocked(); 5568 } 5569 } 5570 } 5571 5572 final void ensureBootCompleted() { 5573 boolean booting; 5574 boolean enableScreen; 5575 synchronized (this) { 5576 booting = mBooting; 5577 mBooting = false; 5578 enableScreen = !mBooted; 5579 mBooted = true; 5580 } 5581 5582 if (booting) { 5583 finishBooting(); 5584 } 5585 5586 if (enableScreen) { 5587 enableScreenAfterBoot(); 5588 } 5589 } 5590 5591 @Override 5592 public final void activityResumed(IBinder token) { 5593 final long origId = Binder.clearCallingIdentity(); 5594 synchronized(this) { 5595 ActivityStack stack = ActivityRecord.getStackLocked(token); 5596 if (stack != null) { 5597 ActivityRecord.activityResumedLocked(token); 5598 } 5599 } 5600 Binder.restoreCallingIdentity(origId); 5601 } 5602 5603 @Override 5604 public final void activityPaused(IBinder token, PersistableBundle persistentState) { 5605 final long origId = Binder.clearCallingIdentity(); 5606 synchronized(this) { 5607 ActivityStack stack = ActivityRecord.getStackLocked(token); 5608 if (stack != null) { 5609 stack.activityPausedLocked(token, false, persistentState); 5610 } 5611 } 5612 Binder.restoreCallingIdentity(origId); 5613 } 5614 5615 @Override 5616 public final void activityStopped(IBinder token, Bundle icicle, 5617 PersistableBundle persistentState, CharSequence description) { 5618 if (localLOGV) Slog.v(TAG, "Activity stopped: token=" + token); 5619 5620 // Refuse possible leaked file descriptors 5621 if (icicle != null && icicle.hasFileDescriptors()) { 5622 throw new IllegalArgumentException("File descriptors passed in Bundle"); 5623 } 5624 5625 final long origId = Binder.clearCallingIdentity(); 5626 5627 synchronized (this) { 5628 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5629 if (r != null) { 5630 r.task.stack.activityStoppedLocked(r, icicle, persistentState, description); 5631 } 5632 } 5633 5634 trimApplications(); 5635 5636 Binder.restoreCallingIdentity(origId); 5637 } 5638 5639 @Override 5640 public final void activityDestroyed(IBinder token) { 5641 if (DEBUG_SWITCH) Slog.v(TAG, "ACTIVITY DESTROYED: " + token); 5642 synchronized (this) { 5643 ActivityStack stack = ActivityRecord.getStackLocked(token); 5644 if (stack != null) { 5645 stack.activityDestroyedLocked(token); 5646 } 5647 } 5648 } 5649 5650 @Override 5651 public final void mediaResourcesReleased(IBinder token) { 5652 final long origId = Binder.clearCallingIdentity(); 5653 try { 5654 synchronized (this) { 5655 ActivityStack stack = ActivityRecord.getStackLocked(token); 5656 if (stack != null) { 5657 stack.mediaResourcesReleased(token); 5658 } 5659 } 5660 } finally { 5661 Binder.restoreCallingIdentity(origId); 5662 } 5663 } 5664 5665 @Override 5666 public final void notifyLaunchTaskBehindComplete(IBinder token) { 5667 mStackSupervisor.scheduleLaunchTaskBehindComplete(token); 5668 } 5669 5670 @Override 5671 public String getCallingPackage(IBinder token) { 5672 synchronized (this) { 5673 ActivityRecord r = getCallingRecordLocked(token); 5674 return r != null ? r.info.packageName : null; 5675 } 5676 } 5677 5678 @Override 5679 public ComponentName getCallingActivity(IBinder token) { 5680 synchronized (this) { 5681 ActivityRecord r = getCallingRecordLocked(token); 5682 return r != null ? r.intent.getComponent() : null; 5683 } 5684 } 5685 5686 private ActivityRecord getCallingRecordLocked(IBinder token) { 5687 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5688 if (r == null) { 5689 return null; 5690 } 5691 return r.resultTo; 5692 } 5693 5694 @Override 5695 public ComponentName getActivityClassForToken(IBinder token) { 5696 synchronized(this) { 5697 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5698 if (r == null) { 5699 return null; 5700 } 5701 return r.intent.getComponent(); 5702 } 5703 } 5704 5705 @Override 5706 public String getPackageForToken(IBinder token) { 5707 synchronized(this) { 5708 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5709 if (r == null) { 5710 return null; 5711 } 5712 return r.packageName; 5713 } 5714 } 5715 5716 @Override 5717 public IIntentSender getIntentSender(int type, 5718 String packageName, IBinder token, String resultWho, 5719 int requestCode, Intent[] intents, String[] resolvedTypes, 5720 int flags, Bundle options, int userId) { 5721 enforceNotIsolatedCaller("getIntentSender"); 5722 // Refuse possible leaked file descriptors 5723 if (intents != null) { 5724 if (intents.length < 1) { 5725 throw new IllegalArgumentException("Intents array length must be >= 1"); 5726 } 5727 for (int i=0; i<intents.length; i++) { 5728 Intent intent = intents[i]; 5729 if (intent != null) { 5730 if (intent.hasFileDescriptors()) { 5731 throw new IllegalArgumentException("File descriptors passed in Intent"); 5732 } 5733 if (type == ActivityManager.INTENT_SENDER_BROADCAST && 5734 (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 5735 throw new IllegalArgumentException( 5736 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 5737 } 5738 intents[i] = new Intent(intent); 5739 } 5740 } 5741 if (resolvedTypes != null && resolvedTypes.length != intents.length) { 5742 throw new IllegalArgumentException( 5743 "Intent array length does not match resolvedTypes length"); 5744 } 5745 } 5746 if (options != null) { 5747 if (options.hasFileDescriptors()) { 5748 throw new IllegalArgumentException("File descriptors passed in options"); 5749 } 5750 } 5751 5752 synchronized(this) { 5753 int callingUid = Binder.getCallingUid(); 5754 int origUserId = userId; 5755 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 5756 type == ActivityManager.INTENT_SENDER_BROADCAST, 5757 ALLOW_NON_FULL, "getIntentSender", null); 5758 if (origUserId == UserHandle.USER_CURRENT) { 5759 // We don't want to evaluate this until the pending intent is 5760 // actually executed. However, we do want to always do the 5761 // security checking for it above. 5762 userId = UserHandle.USER_CURRENT; 5763 } 5764 try { 5765 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 5766 int uid = AppGlobals.getPackageManager() 5767 .getPackageUid(packageName, UserHandle.getUserId(callingUid)); 5768 if (!UserHandle.isSameApp(callingUid, uid)) { 5769 String msg = "Permission Denial: getIntentSender() from pid=" 5770 + Binder.getCallingPid() 5771 + ", uid=" + Binder.getCallingUid() 5772 + ", (need uid=" + uid + ")" 5773 + " is not allowed to send as package " + packageName; 5774 Slog.w(TAG, msg); 5775 throw new SecurityException(msg); 5776 } 5777 } 5778 5779 return getIntentSenderLocked(type, packageName, callingUid, userId, 5780 token, resultWho, requestCode, intents, resolvedTypes, flags, options); 5781 5782 } catch (RemoteException e) { 5783 throw new SecurityException(e); 5784 } 5785 } 5786 } 5787 5788 IIntentSender getIntentSenderLocked(int type, String packageName, 5789 int callingUid, int userId, IBinder token, String resultWho, 5790 int requestCode, Intent[] intents, String[] resolvedTypes, int flags, 5791 Bundle options) { 5792 if (DEBUG_MU) 5793 Slog.v(TAG_MU, "getIntentSenderLocked(): uid=" + callingUid); 5794 ActivityRecord activity = null; 5795 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 5796 activity = ActivityRecord.isInStackLocked(token); 5797 if (activity == null) { 5798 return null; 5799 } 5800 if (activity.finishing) { 5801 return null; 5802 } 5803 } 5804 5805 final boolean noCreate = (flags&PendingIntent.FLAG_NO_CREATE) != 0; 5806 final boolean cancelCurrent = (flags&PendingIntent.FLAG_CANCEL_CURRENT) != 0; 5807 final boolean updateCurrent = (flags&PendingIntent.FLAG_UPDATE_CURRENT) != 0; 5808 flags &= ~(PendingIntent.FLAG_NO_CREATE|PendingIntent.FLAG_CANCEL_CURRENT 5809 |PendingIntent.FLAG_UPDATE_CURRENT); 5810 5811 PendingIntentRecord.Key key = new PendingIntentRecord.Key( 5812 type, packageName, activity, resultWho, 5813 requestCode, intents, resolvedTypes, flags, options, userId); 5814 WeakReference<PendingIntentRecord> ref; 5815 ref = mIntentSenderRecords.get(key); 5816 PendingIntentRecord rec = ref != null ? ref.get() : null; 5817 if (rec != null) { 5818 if (!cancelCurrent) { 5819 if (updateCurrent) { 5820 if (rec.key.requestIntent != null) { 5821 rec.key.requestIntent.replaceExtras(intents != null ? 5822 intents[intents.length - 1] : null); 5823 } 5824 if (intents != null) { 5825 intents[intents.length-1] = rec.key.requestIntent; 5826 rec.key.allIntents = intents; 5827 rec.key.allResolvedTypes = resolvedTypes; 5828 } else { 5829 rec.key.allIntents = null; 5830 rec.key.allResolvedTypes = null; 5831 } 5832 } 5833 return rec; 5834 } 5835 rec.canceled = true; 5836 mIntentSenderRecords.remove(key); 5837 } 5838 if (noCreate) { 5839 return rec; 5840 } 5841 rec = new PendingIntentRecord(this, key, callingUid); 5842 mIntentSenderRecords.put(key, rec.ref); 5843 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 5844 if (activity.pendingResults == null) { 5845 activity.pendingResults 5846 = new HashSet<WeakReference<PendingIntentRecord>>(); 5847 } 5848 activity.pendingResults.add(rec.ref); 5849 } 5850 return rec; 5851 } 5852 5853 @Override 5854 public void cancelIntentSender(IIntentSender sender) { 5855 if (!(sender instanceof PendingIntentRecord)) { 5856 return; 5857 } 5858 synchronized(this) { 5859 PendingIntentRecord rec = (PendingIntentRecord)sender; 5860 try { 5861 int uid = AppGlobals.getPackageManager() 5862 .getPackageUid(rec.key.packageName, UserHandle.getCallingUserId()); 5863 if (!UserHandle.isSameApp(uid, Binder.getCallingUid())) { 5864 String msg = "Permission Denial: cancelIntentSender() from pid=" 5865 + Binder.getCallingPid() 5866 + ", uid=" + Binder.getCallingUid() 5867 + " is not allowed to cancel packges " 5868 + rec.key.packageName; 5869 Slog.w(TAG, msg); 5870 throw new SecurityException(msg); 5871 } 5872 } catch (RemoteException e) { 5873 throw new SecurityException(e); 5874 } 5875 cancelIntentSenderLocked(rec, true); 5876 } 5877 } 5878 5879 void cancelIntentSenderLocked(PendingIntentRecord rec, boolean cleanActivity) { 5880 rec.canceled = true; 5881 mIntentSenderRecords.remove(rec.key); 5882 if (cleanActivity && rec.key.activity != null) { 5883 rec.key.activity.pendingResults.remove(rec.ref); 5884 } 5885 } 5886 5887 @Override 5888 public String getPackageForIntentSender(IIntentSender pendingResult) { 5889 if (!(pendingResult instanceof PendingIntentRecord)) { 5890 return null; 5891 } 5892 try { 5893 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5894 return res.key.packageName; 5895 } catch (ClassCastException e) { 5896 } 5897 return null; 5898 } 5899 5900 @Override 5901 public int getUidForIntentSender(IIntentSender sender) { 5902 if (sender instanceof PendingIntentRecord) { 5903 try { 5904 PendingIntentRecord res = (PendingIntentRecord)sender; 5905 return res.uid; 5906 } catch (ClassCastException e) { 5907 } 5908 } 5909 return -1; 5910 } 5911 5912 @Override 5913 public boolean isIntentSenderTargetedToPackage(IIntentSender pendingResult) { 5914 if (!(pendingResult instanceof PendingIntentRecord)) { 5915 return false; 5916 } 5917 try { 5918 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5919 if (res.key.allIntents == null) { 5920 return false; 5921 } 5922 for (int i=0; i<res.key.allIntents.length; i++) { 5923 Intent intent = res.key.allIntents[i]; 5924 if (intent.getPackage() != null && intent.getComponent() != null) { 5925 return false; 5926 } 5927 } 5928 return true; 5929 } catch (ClassCastException e) { 5930 } 5931 return false; 5932 } 5933 5934 @Override 5935 public boolean isIntentSenderAnActivity(IIntentSender pendingResult) { 5936 if (!(pendingResult instanceof PendingIntentRecord)) { 5937 return false; 5938 } 5939 try { 5940 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5941 if (res.key.type == ActivityManager.INTENT_SENDER_ACTIVITY) { 5942 return true; 5943 } 5944 return false; 5945 } catch (ClassCastException e) { 5946 } 5947 return false; 5948 } 5949 5950 @Override 5951 public Intent getIntentForIntentSender(IIntentSender pendingResult) { 5952 if (!(pendingResult instanceof PendingIntentRecord)) { 5953 return null; 5954 } 5955 try { 5956 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5957 return res.key.requestIntent != null ? new Intent(res.key.requestIntent) : null; 5958 } catch (ClassCastException e) { 5959 } 5960 return null; 5961 } 5962 5963 @Override 5964 public String getTagForIntentSender(IIntentSender pendingResult, String prefix) { 5965 if (!(pendingResult instanceof PendingIntentRecord)) { 5966 return null; 5967 } 5968 try { 5969 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5970 Intent intent = res.key.requestIntent; 5971 if (intent != null) { 5972 if (res.lastTag != null && res.lastTagPrefix == prefix && (res.lastTagPrefix == null 5973 || res.lastTagPrefix.equals(prefix))) { 5974 return res.lastTag; 5975 } 5976 res.lastTagPrefix = prefix; 5977 StringBuilder sb = new StringBuilder(128); 5978 if (prefix != null) { 5979 sb.append(prefix); 5980 } 5981 if (intent.getAction() != null) { 5982 sb.append(intent.getAction()); 5983 } else if (intent.getComponent() != null) { 5984 intent.getComponent().appendShortString(sb); 5985 } else { 5986 sb.append("?"); 5987 } 5988 return res.lastTag = sb.toString(); 5989 } 5990 } catch (ClassCastException e) { 5991 } 5992 return null; 5993 } 5994 5995 @Override 5996 public void setProcessLimit(int max) { 5997 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 5998 "setProcessLimit()"); 5999 synchronized (this) { 6000 mProcessLimit = max < 0 ? ProcessList.MAX_CACHED_APPS : max; 6001 mProcessLimitOverride = max; 6002 } 6003 trimApplications(); 6004 } 6005 6006 @Override 6007 public int getProcessLimit() { 6008 synchronized (this) { 6009 return mProcessLimitOverride; 6010 } 6011 } 6012 6013 void foregroundTokenDied(ForegroundToken token) { 6014 synchronized (ActivityManagerService.this) { 6015 synchronized (mPidsSelfLocked) { 6016 ForegroundToken cur 6017 = mForegroundProcesses.get(token.pid); 6018 if (cur != token) { 6019 return; 6020 } 6021 mForegroundProcesses.remove(token.pid); 6022 ProcessRecord pr = mPidsSelfLocked.get(token.pid); 6023 if (pr == null) { 6024 return; 6025 } 6026 pr.forcingToForeground = null; 6027 updateProcessForegroundLocked(pr, false, false); 6028 } 6029 updateOomAdjLocked(); 6030 } 6031 } 6032 6033 @Override 6034 public void setProcessForeground(IBinder token, int pid, boolean isForeground) { 6035 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 6036 "setProcessForeground()"); 6037 synchronized(this) { 6038 boolean changed = false; 6039 6040 synchronized (mPidsSelfLocked) { 6041 ProcessRecord pr = mPidsSelfLocked.get(pid); 6042 if (pr == null && isForeground) { 6043 Slog.w(TAG, "setProcessForeground called on unknown pid: " + pid); 6044 return; 6045 } 6046 ForegroundToken oldToken = mForegroundProcesses.get(pid); 6047 if (oldToken != null) { 6048 oldToken.token.unlinkToDeath(oldToken, 0); 6049 mForegroundProcesses.remove(pid); 6050 if (pr != null) { 6051 pr.forcingToForeground = null; 6052 } 6053 changed = true; 6054 } 6055 if (isForeground && token != null) { 6056 ForegroundToken newToken = new ForegroundToken() { 6057 @Override 6058 public void binderDied() { 6059 foregroundTokenDied(this); 6060 } 6061 }; 6062 newToken.pid = pid; 6063 newToken.token = token; 6064 try { 6065 token.linkToDeath(newToken, 0); 6066 mForegroundProcesses.put(pid, newToken); 6067 pr.forcingToForeground = token; 6068 changed = true; 6069 } catch (RemoteException e) { 6070 // If the process died while doing this, we will later 6071 // do the cleanup with the process death link. 6072 } 6073 } 6074 } 6075 6076 if (changed) { 6077 updateOomAdjLocked(); 6078 } 6079 } 6080 } 6081 6082 // ========================================================= 6083 // PERMISSIONS 6084 // ========================================================= 6085 6086 static class PermissionController extends IPermissionController.Stub { 6087 ActivityManagerService mActivityManagerService; 6088 PermissionController(ActivityManagerService activityManagerService) { 6089 mActivityManagerService = activityManagerService; 6090 } 6091 6092 @Override 6093 public boolean checkPermission(String permission, int pid, int uid) { 6094 return mActivityManagerService.checkPermission(permission, pid, 6095 uid) == PackageManager.PERMISSION_GRANTED; 6096 } 6097 } 6098 6099 class IntentFirewallInterface implements IntentFirewall.AMSInterface { 6100 @Override 6101 public int checkComponentPermission(String permission, int pid, int uid, 6102 int owningUid, boolean exported) { 6103 return ActivityManagerService.this.checkComponentPermission(permission, pid, uid, 6104 owningUid, exported); 6105 } 6106 6107 @Override 6108 public Object getAMSLock() { 6109 return ActivityManagerService.this; 6110 } 6111 } 6112 6113 /** 6114 * This can be called with or without the global lock held. 6115 */ 6116 int checkComponentPermission(String permission, int pid, int uid, 6117 int owningUid, boolean exported) { 6118 // We might be performing an operation on behalf of an indirect binder 6119 // invocation, e.g. via {@link #openContentUri}. Check and adjust the 6120 // client identity accordingly before proceeding. 6121 Identity tlsIdentity = sCallerIdentity.get(); 6122 if (tlsIdentity != null) { 6123 Slog.d(TAG, "checkComponentPermission() adjusting {pid,uid} to {" 6124 + tlsIdentity.pid + "," + tlsIdentity.uid + "}"); 6125 uid = tlsIdentity.uid; 6126 pid = tlsIdentity.pid; 6127 } 6128 6129 if (pid == MY_PID) { 6130 return PackageManager.PERMISSION_GRANTED; 6131 } 6132 6133 return ActivityManager.checkComponentPermission(permission, uid, 6134 owningUid, exported); 6135 } 6136 6137 /** 6138 * As the only public entry point for permissions checking, this method 6139 * can enforce the semantic that requesting a check on a null global 6140 * permission is automatically denied. (Internally a null permission 6141 * string is used when calling {@link #checkComponentPermission} in cases 6142 * when only uid-based security is needed.) 6143 * 6144 * This can be called with or without the global lock held. 6145 */ 6146 @Override 6147 public int checkPermission(String permission, int pid, int uid) { 6148 if (permission == null) { 6149 return PackageManager.PERMISSION_DENIED; 6150 } 6151 return checkComponentPermission(permission, pid, UserHandle.getAppId(uid), -1, true); 6152 } 6153 6154 /** 6155 * Binder IPC calls go through the public entry point. 6156 * This can be called with or without the global lock held. 6157 */ 6158 int checkCallingPermission(String permission) { 6159 return checkPermission(permission, 6160 Binder.getCallingPid(), 6161 UserHandle.getAppId(Binder.getCallingUid())); 6162 } 6163 6164 /** 6165 * This can be called with or without the global lock held. 6166 */ 6167 void enforceCallingPermission(String permission, String func) { 6168 if (checkCallingPermission(permission) 6169 == PackageManager.PERMISSION_GRANTED) { 6170 return; 6171 } 6172 6173 String msg = "Permission Denial: " + func + " from pid=" 6174 + Binder.getCallingPid() 6175 + ", uid=" + Binder.getCallingUid() 6176 + " requires " + permission; 6177 Slog.w(TAG, msg); 6178 throw new SecurityException(msg); 6179 } 6180 6181 /** 6182 * Determine if UID is holding permissions required to access {@link Uri} in 6183 * the given {@link ProviderInfo}. Final permission checking is always done 6184 * in {@link ContentProvider}. 6185 */ 6186 private final boolean checkHoldingPermissionsLocked( 6187 IPackageManager pm, ProviderInfo pi, GrantUri grantUri, int uid, final int modeFlags) { 6188 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6189 "checkHoldingPermissionsLocked: uri=" + grantUri + " uid=" + uid); 6190 if (UserHandle.getUserId(uid) != grantUri.sourceUserId) { 6191 return false; 6192 } 6193 return checkHoldingPermissionsInternalLocked(pm, pi, grantUri, uid, modeFlags, true); 6194 } 6195 6196 private final boolean checkHoldingPermissionsInternalLocked(IPackageManager pm, ProviderInfo pi, 6197 GrantUri grantUri, int uid, final int modeFlags, boolean considerUidPermissions) { 6198 if (pi.applicationInfo.uid == uid) { 6199 return true; 6200 } else if (!pi.exported) { 6201 return false; 6202 } 6203 6204 boolean readMet = (modeFlags & Intent.FLAG_GRANT_READ_URI_PERMISSION) == 0; 6205 boolean writeMet = (modeFlags & Intent.FLAG_GRANT_WRITE_URI_PERMISSION) == 0; 6206 try { 6207 // check if target holds top-level <provider> permissions 6208 if (!readMet && pi.readPermission != null && considerUidPermissions 6209 && (pm.checkUidPermission(pi.readPermission, uid) == PERMISSION_GRANTED)) { 6210 readMet = true; 6211 } 6212 if (!writeMet && pi.writePermission != null && considerUidPermissions 6213 && (pm.checkUidPermission(pi.writePermission, uid) == PERMISSION_GRANTED)) { 6214 writeMet = true; 6215 } 6216 6217 // track if unprotected read/write is allowed; any denied 6218 // <path-permission> below removes this ability 6219 boolean allowDefaultRead = pi.readPermission == null; 6220 boolean allowDefaultWrite = pi.writePermission == null; 6221 6222 // check if target holds any <path-permission> that match uri 6223 final PathPermission[] pps = pi.pathPermissions; 6224 if (pps != null) { 6225 final String path = grantUri.uri.getPath(); 6226 int i = pps.length; 6227 while (i > 0 && (!readMet || !writeMet)) { 6228 i--; 6229 PathPermission pp = pps[i]; 6230 if (pp.match(path)) { 6231 if (!readMet) { 6232 final String pprperm = pp.getReadPermission(); 6233 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking read perm for " 6234 + pprperm + " for " + pp.getPath() 6235 + ": match=" + pp.match(path) 6236 + " check=" + pm.checkUidPermission(pprperm, uid)); 6237 if (pprperm != null) { 6238 if (considerUidPermissions && pm.checkUidPermission(pprperm, uid) 6239 == PERMISSION_GRANTED) { 6240 readMet = true; 6241 } else { 6242 allowDefaultRead = false; 6243 } 6244 } 6245 } 6246 if (!writeMet) { 6247 final String ppwperm = pp.getWritePermission(); 6248 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking write perm " 6249 + ppwperm + " for " + pp.getPath() 6250 + ": match=" + pp.match(path) 6251 + " check=" + pm.checkUidPermission(ppwperm, uid)); 6252 if (ppwperm != null) { 6253 if (considerUidPermissions && pm.checkUidPermission(ppwperm, uid) 6254 == PERMISSION_GRANTED) { 6255 writeMet = true; 6256 } else { 6257 allowDefaultWrite = false; 6258 } 6259 } 6260 } 6261 } 6262 } 6263 } 6264 6265 // grant unprotected <provider> read/write, if not blocked by 6266 // <path-permission> above 6267 if (allowDefaultRead) readMet = true; 6268 if (allowDefaultWrite) writeMet = true; 6269 6270 } catch (RemoteException e) { 6271 return false; 6272 } 6273 6274 return readMet && writeMet; 6275 } 6276 6277 private ProviderInfo getProviderInfoLocked(String authority, int userHandle) { 6278 ProviderInfo pi = null; 6279 ContentProviderRecord cpr = mProviderMap.getProviderByName(authority, userHandle); 6280 if (cpr != null) { 6281 pi = cpr.info; 6282 } else { 6283 try { 6284 pi = AppGlobals.getPackageManager().resolveContentProvider( 6285 authority, PackageManager.GET_URI_PERMISSION_PATTERNS, userHandle); 6286 } catch (RemoteException ex) { 6287 } 6288 } 6289 return pi; 6290 } 6291 6292 private UriPermission findUriPermissionLocked(int targetUid, GrantUri grantUri) { 6293 final ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6294 if (targetUris != null) { 6295 return targetUris.get(grantUri); 6296 } 6297 return null; 6298 } 6299 6300 private UriPermission findOrCreateUriPermissionLocked(String sourcePkg, 6301 String targetPkg, int targetUid, GrantUri grantUri) { 6302 ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6303 if (targetUris == null) { 6304 targetUris = Maps.newArrayMap(); 6305 mGrantedUriPermissions.put(targetUid, targetUris); 6306 } 6307 6308 UriPermission perm = targetUris.get(grantUri); 6309 if (perm == null) { 6310 perm = new UriPermission(sourcePkg, targetPkg, targetUid, grantUri); 6311 targetUris.put(grantUri, perm); 6312 } 6313 6314 return perm; 6315 } 6316 6317 private final boolean checkUriPermissionLocked(GrantUri grantUri, int uid, 6318 final int modeFlags) { 6319 final boolean persistable = (modeFlags & Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION) != 0; 6320 final int minStrength = persistable ? UriPermission.STRENGTH_PERSISTABLE 6321 : UriPermission.STRENGTH_OWNED; 6322 6323 // Root gets to do everything. 6324 if (uid == 0) { 6325 return true; 6326 } 6327 6328 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 6329 if (perms == null) return false; 6330 6331 // First look for exact match 6332 final UriPermission exactPerm = perms.get(grantUri); 6333 if (exactPerm != null && exactPerm.getStrength(modeFlags) >= minStrength) { 6334 return true; 6335 } 6336 6337 // No exact match, look for prefixes 6338 final int N = perms.size(); 6339 for (int i = 0; i < N; i++) { 6340 final UriPermission perm = perms.valueAt(i); 6341 if (perm.uri.prefix && grantUri.uri.isPathPrefixMatch(perm.uri.uri) 6342 && perm.getStrength(modeFlags) >= minStrength) { 6343 return true; 6344 } 6345 } 6346 6347 return false; 6348 } 6349 6350 @Override 6351 public int checkUriPermission(Uri uri, int pid, int uid, 6352 final int modeFlags, int userId) { 6353 enforceNotIsolatedCaller("checkUriPermission"); 6354 6355 // Another redirected-binder-call permissions check as in 6356 // {@link checkComponentPermission}. 6357 Identity tlsIdentity = sCallerIdentity.get(); 6358 if (tlsIdentity != null) { 6359 uid = tlsIdentity.uid; 6360 pid = tlsIdentity.pid; 6361 } 6362 6363 // Our own process gets to do everything. 6364 if (pid == MY_PID) { 6365 return PackageManager.PERMISSION_GRANTED; 6366 } 6367 synchronized (this) { 6368 return checkUriPermissionLocked(new GrantUri(userId, uri, false), uid, modeFlags) 6369 ? PackageManager.PERMISSION_GRANTED 6370 : PackageManager.PERMISSION_DENIED; 6371 } 6372 } 6373 6374 /** 6375 * Check if the targetPkg can be granted permission to access uri by 6376 * the callingUid using the given modeFlags. Throws a security exception 6377 * if callingUid is not allowed to do this. Returns the uid of the target 6378 * if the URI permission grant should be performed; returns -1 if it is not 6379 * needed (for example targetPkg already has permission to access the URI). 6380 * If you already know the uid of the target, you can supply it in 6381 * lastTargetUid else set that to -1. 6382 */ 6383 int checkGrantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 6384 final int modeFlags, int lastTargetUid) { 6385 if (!Intent.isAccessUriMode(modeFlags)) { 6386 return -1; 6387 } 6388 6389 if (targetPkg != null) { 6390 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6391 "Checking grant " + targetPkg + " permission to " + grantUri); 6392 } 6393 6394 final IPackageManager pm = AppGlobals.getPackageManager(); 6395 6396 // If this is not a content: uri, we can't do anything with it. 6397 if (!ContentResolver.SCHEME_CONTENT.equals(grantUri.uri.getScheme())) { 6398 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6399 "Can't grant URI permission for non-content URI: " + grantUri); 6400 return -1; 6401 } 6402 6403 final String authority = grantUri.uri.getAuthority(); 6404 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6405 if (pi == null) { 6406 Slog.w(TAG, "No content provider found for permission check: " + 6407 grantUri.uri.toSafeString()); 6408 return -1; 6409 } 6410 6411 int targetUid = lastTargetUid; 6412 if (targetUid < 0 && targetPkg != null) { 6413 try { 6414 targetUid = pm.getPackageUid(targetPkg, UserHandle.getUserId(callingUid)); 6415 if (targetUid < 0) { 6416 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6417 "Can't grant URI permission no uid for: " + targetPkg); 6418 return -1; 6419 } 6420 } catch (RemoteException ex) { 6421 return -1; 6422 } 6423 } 6424 6425 if (targetUid >= 0) { 6426 // First... does the target actually need this permission? 6427 if (checkHoldingPermissionsLocked(pm, pi, grantUri, targetUid, modeFlags)) { 6428 // No need to grant the target this permission. 6429 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6430 "Target " + targetPkg + " already has full permission to " + grantUri); 6431 return -1; 6432 } 6433 } else { 6434 // First... there is no target package, so can anyone access it? 6435 boolean allowed = pi.exported; 6436 if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) { 6437 if (pi.readPermission != null) { 6438 allowed = false; 6439 } 6440 } 6441 if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) { 6442 if (pi.writePermission != null) { 6443 allowed = false; 6444 } 6445 } 6446 if (allowed) { 6447 return -1; 6448 } 6449 } 6450 6451 /* There is a special cross user grant if: 6452 * - The target is on another user. 6453 * - Apps on the current user can access the uri without any uid permissions. 6454 * In this case, we grant a uri permission, even if the ContentProvider does not normally 6455 * grant uri permissions. 6456 */ 6457 boolean specialCrossUserGrant = UserHandle.getUserId(targetUid) != grantUri.sourceUserId 6458 && checkHoldingPermissionsInternalLocked(pm, pi, grantUri, callingUid, 6459 modeFlags, false /*without considering the uid permissions*/); 6460 6461 // Second... is the provider allowing granting of URI permissions? 6462 if (!specialCrossUserGrant) { 6463 if (!pi.grantUriPermissions) { 6464 throw new SecurityException("Provider " + pi.packageName 6465 + "/" + pi.name 6466 + " does not allow granting of Uri permissions (uri " 6467 + grantUri + ")"); 6468 } 6469 if (pi.uriPermissionPatterns != null) { 6470 final int N = pi.uriPermissionPatterns.length; 6471 boolean allowed = false; 6472 for (int i=0; i<N; i++) { 6473 if (pi.uriPermissionPatterns[i] != null 6474 && pi.uriPermissionPatterns[i].match(grantUri.uri.getPath())) { 6475 allowed = true; 6476 break; 6477 } 6478 } 6479 if (!allowed) { 6480 throw new SecurityException("Provider " + pi.packageName 6481 + "/" + pi.name 6482 + " does not allow granting of permission to path of Uri " 6483 + grantUri); 6484 } 6485 } 6486 } 6487 6488 // Third... does the caller itself have permission to access 6489 // this uri? 6490 if (UserHandle.getAppId(callingUid) != Process.SYSTEM_UID) { 6491 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 6492 // Require they hold a strong enough Uri permission 6493 if (!checkUriPermissionLocked(grantUri, callingUid, modeFlags)) { 6494 throw new SecurityException("Uid " + callingUid 6495 + " does not have permission to uri " + grantUri); 6496 } 6497 } 6498 } 6499 return targetUid; 6500 } 6501 6502 @Override 6503 public int checkGrantUriPermission(int callingUid, String targetPkg, Uri uri, 6504 final int modeFlags, int userId) { 6505 enforceNotIsolatedCaller("checkGrantUriPermission"); 6506 synchronized(this) { 6507 return checkGrantUriPermissionLocked(callingUid, targetPkg, 6508 new GrantUri(userId, uri, false), modeFlags, -1); 6509 } 6510 } 6511 6512 void grantUriPermissionUncheckedLocked(int targetUid, String targetPkg, GrantUri grantUri, 6513 final int modeFlags, UriPermissionOwner owner) { 6514 if (!Intent.isAccessUriMode(modeFlags)) { 6515 return; 6516 } 6517 6518 // So here we are: the caller has the assumed permission 6519 // to the uri, and the target doesn't. Let's now give this to 6520 // the target. 6521 6522 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6523 "Granting " + targetPkg + "/" + targetUid + " permission to " + grantUri); 6524 6525 final String authority = grantUri.uri.getAuthority(); 6526 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6527 if (pi == null) { 6528 Slog.w(TAG, "No content provider found for grant: " + grantUri.toSafeString()); 6529 return; 6530 } 6531 6532 if ((modeFlags & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0) { 6533 grantUri.prefix = true; 6534 } 6535 final UriPermission perm = findOrCreateUriPermissionLocked( 6536 pi.packageName, targetPkg, targetUid, grantUri); 6537 perm.grantModes(modeFlags, owner); 6538 } 6539 6540 void grantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 6541 final int modeFlags, UriPermissionOwner owner) { 6542 if (targetPkg == null) { 6543 throw new NullPointerException("targetPkg"); 6544 } 6545 6546 int targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, modeFlags, 6547 -1); 6548 if (targetUid < 0) { 6549 return; 6550 } 6551 6552 grantUriPermissionUncheckedLocked(targetUid, targetPkg, grantUri, modeFlags, 6553 owner); 6554 } 6555 6556 static class NeededUriGrants extends ArrayList<GrantUri> { 6557 final String targetPkg; 6558 final int targetUid; 6559 final int flags; 6560 6561 NeededUriGrants(String targetPkg, int targetUid, int flags) { 6562 this.targetPkg = targetPkg; 6563 this.targetUid = targetUid; 6564 this.flags = flags; 6565 } 6566 } 6567 6568 /** 6569 * Like checkGrantUriPermissionLocked, but takes an Intent. 6570 */ 6571 NeededUriGrants checkGrantUriPermissionFromIntentLocked(int callingUid, 6572 String targetPkg, Intent intent, int mode, NeededUriGrants needed, int targetUserId) { 6573 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6574 "Checking URI perm to data=" + (intent != null ? intent.getData() : null) 6575 + " clip=" + (intent != null ? intent.getClipData() : null) 6576 + " from " + intent + "; flags=0x" 6577 + Integer.toHexString(intent != null ? intent.getFlags() : 0)); 6578 6579 if (targetPkg == null) { 6580 throw new NullPointerException("targetPkg"); 6581 } 6582 6583 if (intent == null) { 6584 return null; 6585 } 6586 Uri data = intent.getData(); 6587 ClipData clip = intent.getClipData(); 6588 if (data == null && clip == null) { 6589 return null; 6590 } 6591 final IPackageManager pm = AppGlobals.getPackageManager(); 6592 int targetUid; 6593 if (needed != null) { 6594 targetUid = needed.targetUid; 6595 } else { 6596 try { 6597 targetUid = pm.getPackageUid(targetPkg, targetUserId); 6598 } catch (RemoteException ex) { 6599 return null; 6600 } 6601 if (targetUid < 0) { 6602 if (DEBUG_URI_PERMISSION) { 6603 Slog.v(TAG, "Can't grant URI permission no uid for: " + targetPkg 6604 + " on user " + targetUserId); 6605 } 6606 return null; 6607 } 6608 } 6609 if (data != null) { 6610 GrantUri grantUri = GrantUri.resolve(UserHandle.getUserId(callingUid), data); 6611 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 6612 targetUid); 6613 if (targetUid > 0) { 6614 if (needed == null) { 6615 needed = new NeededUriGrants(targetPkg, targetUid, mode); 6616 } 6617 needed.add(grantUri); 6618 } 6619 } 6620 if (clip != null) { 6621 for (int i=0; i<clip.getItemCount(); i++) { 6622 Uri uri = clip.getItemAt(i).getUri(); 6623 if (uri != null) { 6624 GrantUri grantUri = GrantUri.resolve(UserHandle.getUserId(callingUid), uri); 6625 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 6626 targetUid); 6627 if (targetUid > 0) { 6628 if (needed == null) { 6629 needed = new NeededUriGrants(targetPkg, targetUid, mode); 6630 } 6631 needed.add(grantUri); 6632 } 6633 } else { 6634 Intent clipIntent = clip.getItemAt(i).getIntent(); 6635 if (clipIntent != null) { 6636 NeededUriGrants newNeeded = checkGrantUriPermissionFromIntentLocked( 6637 callingUid, targetPkg, clipIntent, mode, needed, targetUserId); 6638 if (newNeeded != null) { 6639 needed = newNeeded; 6640 } 6641 } 6642 } 6643 } 6644 } 6645 6646 return needed; 6647 } 6648 6649 /** 6650 * Like grantUriPermissionUncheckedLocked, but takes an Intent. 6651 */ 6652 void grantUriPermissionUncheckedFromIntentLocked(NeededUriGrants needed, 6653 UriPermissionOwner owner) { 6654 if (needed != null) { 6655 for (int i=0; i<needed.size(); i++) { 6656 GrantUri grantUri = needed.get(i); 6657 grantUriPermissionUncheckedLocked(needed.targetUid, needed.targetPkg, 6658 grantUri, needed.flags, owner); 6659 } 6660 } 6661 } 6662 6663 void grantUriPermissionFromIntentLocked(int callingUid, 6664 String targetPkg, Intent intent, UriPermissionOwner owner, int targetUserId) { 6665 NeededUriGrants needed = checkGrantUriPermissionFromIntentLocked(callingUid, targetPkg, 6666 intent, intent != null ? intent.getFlags() : 0, null, targetUserId); 6667 if (needed == null) { 6668 return; 6669 } 6670 6671 grantUriPermissionUncheckedFromIntentLocked(needed, owner); 6672 } 6673 6674 @Override 6675 public void grantUriPermission(IApplicationThread caller, String targetPkg, Uri uri, 6676 final int modeFlags, int userId) { 6677 enforceNotIsolatedCaller("grantUriPermission"); 6678 GrantUri grantUri = new GrantUri(userId, uri, false); 6679 synchronized(this) { 6680 final ProcessRecord r = getRecordForAppLocked(caller); 6681 if (r == null) { 6682 throw new SecurityException("Unable to find app for caller " 6683 + caller 6684 + " when granting permission to uri " + grantUri); 6685 } 6686 if (targetPkg == null) { 6687 throw new IllegalArgumentException("null target"); 6688 } 6689 if (grantUri == null) { 6690 throw new IllegalArgumentException("null uri"); 6691 } 6692 6693 Preconditions.checkFlagsArgument(modeFlags, Intent.FLAG_GRANT_READ_URI_PERMISSION 6694 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION 6695 | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION 6696 | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION); 6697 6698 grantUriPermissionLocked(r.uid, targetPkg, grantUri, modeFlags, null); 6699 } 6700 } 6701 6702 void removeUriPermissionIfNeededLocked(UriPermission perm) { 6703 if (perm.modeFlags == 0) { 6704 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 6705 perm.targetUid); 6706 if (perms != null) { 6707 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6708 "Removing " + perm.targetUid + " permission to " + perm.uri); 6709 6710 perms.remove(perm.uri); 6711 if (perms.isEmpty()) { 6712 mGrantedUriPermissions.remove(perm.targetUid); 6713 } 6714 } 6715 } 6716 } 6717 6718 private void revokeUriPermissionLocked(int callingUid, GrantUri grantUri, final int modeFlags) { 6719 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Revoking all granted permissions to " + grantUri); 6720 6721 final IPackageManager pm = AppGlobals.getPackageManager(); 6722 final String authority = grantUri.uri.getAuthority(); 6723 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6724 if (pi == null) { 6725 Slog.w(TAG, "No content provider found for permission revoke: " 6726 + grantUri.toSafeString()); 6727 return; 6728 } 6729 6730 // Does the caller have this permission on the URI? 6731 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 6732 // Right now, if you are not the original owner of the permission, 6733 // you are not allowed to revoke it. 6734 //if (!checkUriPermissionLocked(uri, callingUid, modeFlags)) { 6735 throw new SecurityException("Uid " + callingUid 6736 + " does not have permission to uri " + grantUri); 6737 //} 6738 } 6739 6740 boolean persistChanged = false; 6741 6742 // Go through all of the permissions and remove any that match. 6743 int N = mGrantedUriPermissions.size(); 6744 for (int i = 0; i < N; i++) { 6745 final int targetUid = mGrantedUriPermissions.keyAt(i); 6746 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6747 6748 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 6749 final UriPermission perm = it.next(); 6750 if (perm.uri.sourceUserId == grantUri.sourceUserId 6751 && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) { 6752 if (DEBUG_URI_PERMISSION) 6753 Slog.v(TAG, 6754 "Revoking " + perm.targetUid + " permission to " + perm.uri); 6755 persistChanged |= perm.revokeModes( 6756 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 6757 if (perm.modeFlags == 0) { 6758 it.remove(); 6759 } 6760 } 6761 } 6762 6763 if (perms.isEmpty()) { 6764 mGrantedUriPermissions.remove(targetUid); 6765 N--; 6766 i--; 6767 } 6768 } 6769 6770 if (persistChanged) { 6771 schedulePersistUriGrants(); 6772 } 6773 } 6774 6775 @Override 6776 public void revokeUriPermission(IApplicationThread caller, Uri uri, final int modeFlags, 6777 int userId) { 6778 enforceNotIsolatedCaller("revokeUriPermission"); 6779 synchronized(this) { 6780 final ProcessRecord r = getRecordForAppLocked(caller); 6781 if (r == null) { 6782 throw new SecurityException("Unable to find app for caller " 6783 + caller 6784 + " when revoking permission to uri " + uri); 6785 } 6786 if (uri == null) { 6787 Slog.w(TAG, "revokeUriPermission: null uri"); 6788 return; 6789 } 6790 6791 if (!Intent.isAccessUriMode(modeFlags)) { 6792 return; 6793 } 6794 6795 final IPackageManager pm = AppGlobals.getPackageManager(); 6796 final String authority = uri.getAuthority(); 6797 final ProviderInfo pi = getProviderInfoLocked(authority, userId); 6798 if (pi == null) { 6799 Slog.w(TAG, "No content provider found for permission revoke: " 6800 + uri.toSafeString()); 6801 return; 6802 } 6803 6804 revokeUriPermissionLocked(r.uid, new GrantUri(userId, uri, false), modeFlags); 6805 } 6806 } 6807 6808 /** 6809 * Remove any {@link UriPermission} granted <em>from</em> or <em>to</em> the 6810 * given package. 6811 * 6812 * @param packageName Package name to match, or {@code null} to apply to all 6813 * packages. 6814 * @param userHandle User to match, or {@link UserHandle#USER_ALL} to apply 6815 * to all users. 6816 * @param persistable If persistable grants should be removed. 6817 */ 6818 private void removeUriPermissionsForPackageLocked( 6819 String packageName, int userHandle, boolean persistable) { 6820 if (userHandle == UserHandle.USER_ALL && packageName == null) { 6821 throw new IllegalArgumentException("Must narrow by either package or user"); 6822 } 6823 6824 boolean persistChanged = false; 6825 6826 int N = mGrantedUriPermissions.size(); 6827 for (int i = 0; i < N; i++) { 6828 final int targetUid = mGrantedUriPermissions.keyAt(i); 6829 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6830 6831 // Only inspect grants matching user 6832 if (userHandle == UserHandle.USER_ALL 6833 || userHandle == UserHandle.getUserId(targetUid)) { 6834 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 6835 final UriPermission perm = it.next(); 6836 6837 // Only inspect grants matching package 6838 if (packageName == null || perm.sourcePkg.equals(packageName) 6839 || perm.targetPkg.equals(packageName)) { 6840 persistChanged |= perm.revokeModes( 6841 persistable ? ~0 : ~Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 6842 6843 // Only remove when no modes remain; any persisted grants 6844 // will keep this alive. 6845 if (perm.modeFlags == 0) { 6846 it.remove(); 6847 } 6848 } 6849 } 6850 6851 if (perms.isEmpty()) { 6852 mGrantedUriPermissions.remove(targetUid); 6853 N--; 6854 i--; 6855 } 6856 } 6857 } 6858 6859 if (persistChanged) { 6860 schedulePersistUriGrants(); 6861 } 6862 } 6863 6864 @Override 6865 public IBinder newUriPermissionOwner(String name) { 6866 enforceNotIsolatedCaller("newUriPermissionOwner"); 6867 synchronized(this) { 6868 UriPermissionOwner owner = new UriPermissionOwner(this, name); 6869 return owner.getExternalTokenLocked(); 6870 } 6871 } 6872 6873 @Override 6874 public void grantUriPermissionFromOwner(IBinder token, int fromUid, String targetPkg, Uri uri, 6875 final int modeFlags, int userId) { 6876 synchronized(this) { 6877 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 6878 if (owner == null) { 6879 throw new IllegalArgumentException("Unknown owner: " + token); 6880 } 6881 if (fromUid != Binder.getCallingUid()) { 6882 if (Binder.getCallingUid() != Process.myUid()) { 6883 // Only system code can grant URI permissions on behalf 6884 // of other users. 6885 throw new SecurityException("nice try"); 6886 } 6887 } 6888 if (targetPkg == null) { 6889 throw new IllegalArgumentException("null target"); 6890 } 6891 if (uri == null) { 6892 throw new IllegalArgumentException("null uri"); 6893 } 6894 6895 grantUriPermissionLocked(fromUid, targetPkg, new GrantUri(userId, uri, false), 6896 modeFlags, owner); 6897 } 6898 } 6899 6900 @Override 6901 public void revokeUriPermissionFromOwner(IBinder token, Uri uri, int mode, int userId) { 6902 synchronized(this) { 6903 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 6904 if (owner == null) { 6905 throw new IllegalArgumentException("Unknown owner: " + token); 6906 } 6907 6908 if (uri == null) { 6909 owner.removeUriPermissionsLocked(mode); 6910 } else { 6911 owner.removeUriPermissionLocked(new GrantUri(userId, uri, false), mode); 6912 } 6913 } 6914 } 6915 6916 private void schedulePersistUriGrants() { 6917 if (!mHandler.hasMessages(PERSIST_URI_GRANTS_MSG)) { 6918 mHandler.sendMessageDelayed(mHandler.obtainMessage(PERSIST_URI_GRANTS_MSG), 6919 10 * DateUtils.SECOND_IN_MILLIS); 6920 } 6921 } 6922 6923 private void writeGrantedUriPermissions() { 6924 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "writeGrantedUriPermissions()"); 6925 6926 // Snapshot permissions so we can persist without lock 6927 ArrayList<UriPermission.Snapshot> persist = Lists.newArrayList(); 6928 synchronized (this) { 6929 final int size = mGrantedUriPermissions.size(); 6930 for (int i = 0; i < size; i++) { 6931 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6932 for (UriPermission perm : perms.values()) { 6933 if (perm.persistedModeFlags != 0) { 6934 persist.add(perm.snapshot()); 6935 } 6936 } 6937 } 6938 } 6939 6940 FileOutputStream fos = null; 6941 try { 6942 fos = mGrantFile.startWrite(); 6943 6944 XmlSerializer out = new FastXmlSerializer(); 6945 out.setOutput(fos, "utf-8"); 6946 out.startDocument(null, true); 6947 out.startTag(null, TAG_URI_GRANTS); 6948 for (UriPermission.Snapshot perm : persist) { 6949 out.startTag(null, TAG_URI_GRANT); 6950 writeIntAttribute(out, ATTR_SOURCE_USER_ID, perm.uri.sourceUserId); 6951 writeIntAttribute(out, ATTR_TARGET_USER_ID, perm.targetUserId); 6952 out.attribute(null, ATTR_SOURCE_PKG, perm.sourcePkg); 6953 out.attribute(null, ATTR_TARGET_PKG, perm.targetPkg); 6954 out.attribute(null, ATTR_URI, String.valueOf(perm.uri.uri)); 6955 writeBooleanAttribute(out, ATTR_PREFIX, perm.uri.prefix); 6956 writeIntAttribute(out, ATTR_MODE_FLAGS, perm.persistedModeFlags); 6957 writeLongAttribute(out, ATTR_CREATED_TIME, perm.persistedCreateTime); 6958 out.endTag(null, TAG_URI_GRANT); 6959 } 6960 out.endTag(null, TAG_URI_GRANTS); 6961 out.endDocument(); 6962 6963 mGrantFile.finishWrite(fos); 6964 } catch (IOException e) { 6965 if (fos != null) { 6966 mGrantFile.failWrite(fos); 6967 } 6968 } 6969 } 6970 6971 private void readGrantedUriPermissionsLocked() { 6972 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "readGrantedUriPermissions()"); 6973 6974 final long now = System.currentTimeMillis(); 6975 6976 FileInputStream fis = null; 6977 try { 6978 fis = mGrantFile.openRead(); 6979 final XmlPullParser in = Xml.newPullParser(); 6980 in.setInput(fis, null); 6981 6982 int type; 6983 while ((type = in.next()) != END_DOCUMENT) { 6984 final String tag = in.getName(); 6985 if (type == START_TAG) { 6986 if (TAG_URI_GRANT.equals(tag)) { 6987 final int sourceUserId; 6988 final int targetUserId; 6989 final int userHandle = readIntAttribute(in, 6990 ATTR_USER_HANDLE, UserHandle.USER_NULL); 6991 if (userHandle != UserHandle.USER_NULL) { 6992 // For backwards compatibility. 6993 sourceUserId = userHandle; 6994 targetUserId = userHandle; 6995 } else { 6996 sourceUserId = readIntAttribute(in, ATTR_SOURCE_USER_ID); 6997 targetUserId = readIntAttribute(in, ATTR_TARGET_USER_ID); 6998 } 6999 final String sourcePkg = in.getAttributeValue(null, ATTR_SOURCE_PKG); 7000 final String targetPkg = in.getAttributeValue(null, ATTR_TARGET_PKG); 7001 final Uri uri = Uri.parse(in.getAttributeValue(null, ATTR_URI)); 7002 final boolean prefix = readBooleanAttribute(in, ATTR_PREFIX); 7003 final int modeFlags = readIntAttribute(in, ATTR_MODE_FLAGS); 7004 final long createdTime = readLongAttribute(in, ATTR_CREATED_TIME, now); 7005 7006 // Sanity check that provider still belongs to source package 7007 final ProviderInfo pi = getProviderInfoLocked( 7008 uri.getAuthority(), sourceUserId); 7009 if (pi != null && sourcePkg.equals(pi.packageName)) { 7010 int targetUid = -1; 7011 try { 7012 targetUid = AppGlobals.getPackageManager() 7013 .getPackageUid(targetPkg, targetUserId); 7014 } catch (RemoteException e) { 7015 } 7016 if (targetUid != -1) { 7017 final UriPermission perm = findOrCreateUriPermissionLocked( 7018 sourcePkg, targetPkg, targetUid, 7019 new GrantUri(sourceUserId, uri, prefix)); 7020 perm.initPersistedModes(modeFlags, createdTime); 7021 } 7022 } else { 7023 Slog.w(TAG, "Persisted grant for " + uri + " had source " + sourcePkg 7024 + " but instead found " + pi); 7025 } 7026 } 7027 } 7028 } 7029 } catch (FileNotFoundException e) { 7030 // Missing grants is okay 7031 } catch (IOException e) { 7032 Log.wtf(TAG, "Failed reading Uri grants", e); 7033 } catch (XmlPullParserException e) { 7034 Log.wtf(TAG, "Failed reading Uri grants", e); 7035 } finally { 7036 IoUtils.closeQuietly(fis); 7037 } 7038 } 7039 7040 @Override 7041 public void takePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 7042 enforceNotIsolatedCaller("takePersistableUriPermission"); 7043 7044 Preconditions.checkFlagsArgument(modeFlags, 7045 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 7046 7047 synchronized (this) { 7048 final int callingUid = Binder.getCallingUid(); 7049 boolean persistChanged = false; 7050 GrantUri grantUri = new GrantUri(userId, uri, false); 7051 7052 UriPermission exactPerm = findUriPermissionLocked(callingUid, 7053 new GrantUri(userId, uri, false)); 7054 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 7055 new GrantUri(userId, uri, true)); 7056 7057 final boolean exactValid = (exactPerm != null) 7058 && ((modeFlags & exactPerm.persistableModeFlags) == modeFlags); 7059 final boolean prefixValid = (prefixPerm != null) 7060 && ((modeFlags & prefixPerm.persistableModeFlags) == modeFlags); 7061 7062 if (!(exactValid || prefixValid)) { 7063 throw new SecurityException("No persistable permission grants found for UID " 7064 + callingUid + " and Uri " + grantUri.toSafeString()); 7065 } 7066 7067 if (exactValid) { 7068 persistChanged |= exactPerm.takePersistableModes(modeFlags); 7069 } 7070 if (prefixValid) { 7071 persistChanged |= prefixPerm.takePersistableModes(modeFlags); 7072 } 7073 7074 persistChanged |= maybePrunePersistedUriGrantsLocked(callingUid); 7075 7076 if (persistChanged) { 7077 schedulePersistUriGrants(); 7078 } 7079 } 7080 } 7081 7082 @Override 7083 public void releasePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 7084 enforceNotIsolatedCaller("releasePersistableUriPermission"); 7085 7086 Preconditions.checkFlagsArgument(modeFlags, 7087 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 7088 7089 synchronized (this) { 7090 final int callingUid = Binder.getCallingUid(); 7091 boolean persistChanged = false; 7092 7093 UriPermission exactPerm = findUriPermissionLocked(callingUid, 7094 new GrantUri(userId, uri, false)); 7095 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 7096 new GrantUri(userId, uri, true)); 7097 if (exactPerm == null && prefixPerm == null) { 7098 throw new SecurityException("No permission grants found for UID " + callingUid 7099 + " and Uri " + uri.toSafeString()); 7100 } 7101 7102 if (exactPerm != null) { 7103 persistChanged |= exactPerm.releasePersistableModes(modeFlags); 7104 removeUriPermissionIfNeededLocked(exactPerm); 7105 } 7106 if (prefixPerm != null) { 7107 persistChanged |= prefixPerm.releasePersistableModes(modeFlags); 7108 removeUriPermissionIfNeededLocked(prefixPerm); 7109 } 7110 7111 if (persistChanged) { 7112 schedulePersistUriGrants(); 7113 } 7114 } 7115 } 7116 7117 /** 7118 * Prune any older {@link UriPermission} for the given UID until outstanding 7119 * persisted grants are below {@link #MAX_PERSISTED_URI_GRANTS}. 7120 * 7121 * @return if any mutations occured that require persisting. 7122 */ 7123 private boolean maybePrunePersistedUriGrantsLocked(int uid) { 7124 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 7125 if (perms == null) return false; 7126 if (perms.size() < MAX_PERSISTED_URI_GRANTS) return false; 7127 7128 final ArrayList<UriPermission> persisted = Lists.newArrayList(); 7129 for (UriPermission perm : perms.values()) { 7130 if (perm.persistedModeFlags != 0) { 7131 persisted.add(perm); 7132 } 7133 } 7134 7135 final int trimCount = persisted.size() - MAX_PERSISTED_URI_GRANTS; 7136 if (trimCount <= 0) return false; 7137 7138 Collections.sort(persisted, new UriPermission.PersistedTimeComparator()); 7139 for (int i = 0; i < trimCount; i++) { 7140 final UriPermission perm = persisted.get(i); 7141 7142 if (DEBUG_URI_PERMISSION) { 7143 Slog.v(TAG, "Trimming grant created at " + perm.persistedCreateTime); 7144 } 7145 7146 perm.releasePersistableModes(~0); 7147 removeUriPermissionIfNeededLocked(perm); 7148 } 7149 7150 return true; 7151 } 7152 7153 @Override 7154 public ParceledListSlice<android.content.UriPermission> getPersistedUriPermissions( 7155 String packageName, boolean incoming) { 7156 enforceNotIsolatedCaller("getPersistedUriPermissions"); 7157 Preconditions.checkNotNull(packageName, "packageName"); 7158 7159 final int callingUid = Binder.getCallingUid(); 7160 final IPackageManager pm = AppGlobals.getPackageManager(); 7161 try { 7162 final int packageUid = pm.getPackageUid(packageName, UserHandle.getUserId(callingUid)); 7163 if (packageUid != callingUid) { 7164 throw new SecurityException( 7165 "Package " + packageName + " does not belong to calling UID " + callingUid); 7166 } 7167 } catch (RemoteException e) { 7168 throw new SecurityException("Failed to verify package name ownership"); 7169 } 7170 7171 final ArrayList<android.content.UriPermission> result = Lists.newArrayList(); 7172 synchronized (this) { 7173 if (incoming) { 7174 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 7175 callingUid); 7176 if (perms == null) { 7177 Slog.w(TAG, "No permission grants found for " + packageName); 7178 } else { 7179 for (UriPermission perm : perms.values()) { 7180 if (packageName.equals(perm.targetPkg) && perm.persistedModeFlags != 0) { 7181 result.add(perm.buildPersistedPublicApiObject()); 7182 } 7183 } 7184 } 7185 } else { 7186 final int size = mGrantedUriPermissions.size(); 7187 for (int i = 0; i < size; i++) { 7188 final ArrayMap<GrantUri, UriPermission> perms = 7189 mGrantedUriPermissions.valueAt(i); 7190 for (UriPermission perm : perms.values()) { 7191 if (packageName.equals(perm.sourcePkg) && perm.persistedModeFlags != 0) { 7192 result.add(perm.buildPersistedPublicApiObject()); 7193 } 7194 } 7195 } 7196 } 7197 } 7198 return new ParceledListSlice<android.content.UriPermission>(result); 7199 } 7200 7201 @Override 7202 public void showWaitingForDebugger(IApplicationThread who, boolean waiting) { 7203 synchronized (this) { 7204 ProcessRecord app = 7205 who != null ? getRecordForAppLocked(who) : null; 7206 if (app == null) return; 7207 7208 Message msg = Message.obtain(); 7209 msg.what = WAIT_FOR_DEBUGGER_MSG; 7210 msg.obj = app; 7211 msg.arg1 = waiting ? 1 : 0; 7212 mHandler.sendMessage(msg); 7213 } 7214 } 7215 7216 @Override 7217 public void getMemoryInfo(ActivityManager.MemoryInfo outInfo) { 7218 final long homeAppMem = mProcessList.getMemLevel(ProcessList.HOME_APP_ADJ); 7219 final long cachedAppMem = mProcessList.getMemLevel(ProcessList.CACHED_APP_MIN_ADJ); 7220 outInfo.availMem = Process.getFreeMemory(); 7221 outInfo.totalMem = Process.getTotalMemory(); 7222 outInfo.threshold = homeAppMem; 7223 outInfo.lowMemory = outInfo.availMem < (homeAppMem + ((cachedAppMem-homeAppMem)/2)); 7224 outInfo.hiddenAppThreshold = cachedAppMem; 7225 outInfo.secondaryServerThreshold = mProcessList.getMemLevel( 7226 ProcessList.SERVICE_ADJ); 7227 outInfo.visibleAppThreshold = mProcessList.getMemLevel( 7228 ProcessList.VISIBLE_APP_ADJ); 7229 outInfo.foregroundAppThreshold = mProcessList.getMemLevel( 7230 ProcessList.FOREGROUND_APP_ADJ); 7231 } 7232 7233 // ========================================================= 7234 // TASK MANAGEMENT 7235 // ========================================================= 7236 7237 @Override 7238 public List<IAppTask> getAppTasks() { 7239 final PackageManager pm = mContext.getPackageManager(); 7240 int callingUid = Binder.getCallingUid(); 7241 long ident = Binder.clearCallingIdentity(); 7242 7243 // Compose the list of packages for this id to test against 7244 HashSet<String> packages = new HashSet<String>(); 7245 String[] uidPackages = pm.getPackagesForUid(callingUid); 7246 for (int i = 0; i < uidPackages.length; i++) { 7247 packages.add(uidPackages[i]); 7248 } 7249 7250 synchronized(this) { 7251 ArrayList<IAppTask> list = new ArrayList<IAppTask>(); 7252 try { 7253 if (localLOGV) Slog.v(TAG, "getAppTasks"); 7254 7255 final int N = mRecentTasks.size(); 7256 for (int i = 0; i < N; i++) { 7257 TaskRecord tr = mRecentTasks.get(i); 7258 // Skip tasks that are not created by the caller 7259 if (packages.contains(tr.getBaseIntent().getComponent().getPackageName())) { 7260 ActivityManager.RecentTaskInfo taskInfo = 7261 createRecentTaskInfoFromTaskRecord(tr); 7262 AppTaskImpl taskImpl = new AppTaskImpl(taskInfo.persistentId, callingUid); 7263 list.add(taskImpl); 7264 } 7265 } 7266 } finally { 7267 Binder.restoreCallingIdentity(ident); 7268 } 7269 return list; 7270 } 7271 } 7272 7273 @Override 7274 public List<RunningTaskInfo> getTasks(int maxNum, int flags) { 7275 final int callingUid = Binder.getCallingUid(); 7276 ArrayList<RunningTaskInfo> list = new ArrayList<RunningTaskInfo>(); 7277 7278 synchronized(this) { 7279 if (localLOGV) Slog.v( 7280 TAG, "getTasks: max=" + maxNum + ", flags=" + flags); 7281 7282 final boolean allowed = checkCallingPermission( 7283 android.Manifest.permission.GET_TASKS) 7284 == PackageManager.PERMISSION_GRANTED; 7285 if (!allowed) { 7286 Slog.w(TAG, "getTasks: caller " + callingUid 7287 + " does not hold GET_TASKS; limiting output"); 7288 } 7289 7290 // TODO: Improve with MRU list from all ActivityStacks. 7291 mStackSupervisor.getTasksLocked(maxNum, list, callingUid, allowed); 7292 } 7293 7294 return list; 7295 } 7296 7297 TaskRecord getMostRecentTask() { 7298 return mRecentTasks.get(0); 7299 } 7300 7301 /** 7302 * Creates a new RecentTaskInfo from a TaskRecord. 7303 */ 7304 private ActivityManager.RecentTaskInfo createRecentTaskInfoFromTaskRecord(TaskRecord tr) { 7305 // Update the task description to reflect any changes in the task stack 7306 tr.updateTaskDescription(); 7307 7308 // Compose the recent task info 7309 ActivityManager.RecentTaskInfo rti = new ActivityManager.RecentTaskInfo(); 7310 rti.id = tr.getTopActivity() == null ? -1 : tr.taskId; 7311 rti.persistentId = tr.taskId; 7312 rti.baseIntent = new Intent(tr.getBaseIntent()); 7313 rti.origActivity = tr.origActivity; 7314 rti.description = tr.lastDescription; 7315 rti.stackId = tr.stack != null ? tr.stack.mStackId : -1; 7316 rti.userId = tr.userId; 7317 rti.taskDescription = new ActivityManager.TaskDescription(tr.lastTaskDescription); 7318 rti.firstActiveTime = tr.firstActiveTime; 7319 rti.lastActiveTime = tr.lastActiveTime; 7320 rti.affiliatedTaskId = tr.mAffiliatedTaskId; 7321 return rti; 7322 } 7323 7324 @Override 7325 public List<ActivityManager.RecentTaskInfo> getRecentTasks(int maxNum, int flags, int userId) { 7326 final int callingUid = Binder.getCallingUid(); 7327 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 7328 false, ALLOW_FULL_ONLY, "getRecentTasks", null); 7329 7330 final boolean includeProfiles = (flags & ActivityManager.RECENT_INCLUDE_PROFILES) != 0; 7331 final boolean withExcluded = (flags&ActivityManager.RECENT_WITH_EXCLUDED) != 0; 7332 synchronized (this) { 7333 final boolean allowed = checkCallingPermission(android.Manifest.permission.GET_TASKS) 7334 == PackageManager.PERMISSION_GRANTED; 7335 if (!allowed) { 7336 Slog.w(TAG, "getRecentTasks: caller " + callingUid 7337 + " does not hold GET_TASKS; limiting output"); 7338 } 7339 final boolean detailed = checkCallingPermission( 7340 android.Manifest.permission.GET_DETAILED_TASKS) 7341 == PackageManager.PERMISSION_GRANTED; 7342 7343 IPackageManager pm = AppGlobals.getPackageManager(); 7344 7345 final int N = mRecentTasks.size(); 7346 ArrayList<ActivityManager.RecentTaskInfo> res 7347 = new ArrayList<ActivityManager.RecentTaskInfo>( 7348 maxNum < N ? maxNum : N); 7349 7350 final Set<Integer> includedUsers; 7351 if (includeProfiles) { 7352 includedUsers = getProfileIdsLocked(userId); 7353 } else { 7354 includedUsers = new HashSet<Integer>(); 7355 } 7356 includedUsers.add(Integer.valueOf(userId)); 7357 7358 // Regroup affiliated tasks together. 7359 for (int i = 0; i < N; ) { 7360 TaskRecord task = mRecentTasks.remove(i); 7361 if (mTmpRecents.contains(task)) { 7362 continue; 7363 } 7364 int affiliatedTaskId = task.mAffiliatedTaskId; 7365 while (true) { 7366 TaskRecord next = task.mNextAffiliate; 7367 if (next == null) { 7368 break; 7369 } 7370 if (next.mAffiliatedTaskId != affiliatedTaskId) { 7371 Slog.e(TAG, "Error in Recents: next.affiliatedTaskId=" + 7372 next.mAffiliatedTaskId + " affiliatedTaskId=" + affiliatedTaskId); 7373 task.setNextAffiliate(null); 7374 if (next.mPrevAffiliate == task) { 7375 next.setPrevAffiliate(null); 7376 } 7377 break; 7378 } 7379 if (next.mPrevAffiliate != task) { 7380 Slog.e(TAG, "Error in Recents chain prev.mNextAffiliate=" + 7381 next.mPrevAffiliate + " task=" + task); 7382 next.setPrevAffiliate(null); 7383 break; 7384 } 7385 if (!mRecentTasks.contains(next)) { 7386 Slog.e(TAG, "Error in Recents: next=" + next + " not in mRecentTasks"); 7387 task.setNextAffiliate(null); 7388 if (next.mPrevAffiliate == task) { 7389 next.setPrevAffiliate(null); 7390 } 7391 break; 7392 } 7393 task = next; 7394 } 7395 // task is now the end of the list 7396 do { 7397 mRecentTasks.remove(task); 7398 mRecentTasks.add(i++, task); 7399 mTmpRecents.add(task); 7400 } while ((task = task.mPrevAffiliate) != null); 7401 } 7402 mTmpRecents.clear(); 7403 // mRecentTasks is now in sorted, affiliated order. 7404 7405 for (int i=0; i<N && maxNum > 0; i++) { 7406 TaskRecord tr = mRecentTasks.get(i); 7407 // Only add calling user or related users recent tasks 7408 if (!includedUsers.contains(Integer.valueOf(tr.userId))) continue; 7409 7410 // Return the entry if desired by the caller. We always return 7411 // the first entry, because callers always expect this to be the 7412 // foreground app. We may filter others if the caller has 7413 // not supplied RECENT_WITH_EXCLUDED and there is some reason 7414 // we should exclude the entry. 7415 7416 if (i == 0 7417 || withExcluded 7418 || (tr.intent == null) 7419 || ((tr.intent.getFlags() & Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS) 7420 == 0)) { 7421 if (!allowed) { 7422 // If the caller doesn't have the GET_TASKS permission, then only 7423 // allow them to see a small subset of tasks -- their own and home. 7424 if (!tr.isHomeTask() && tr.creatorUid != callingUid) { 7425 continue; 7426 } 7427 } 7428 if (tr.intent != null && 7429 (tr.intent.getFlags() & Intent.FLAG_ACTIVITY_AUTO_REMOVE_FROM_RECENTS) 7430 != 0 && tr.getTopActivity() == null) { 7431 // Don't include auto remove tasks that are finished or finishing. 7432 continue; 7433 } 7434 7435 ActivityManager.RecentTaskInfo rti = createRecentTaskInfoFromTaskRecord(tr); 7436 if (!detailed) { 7437 rti.baseIntent.replaceExtras((Bundle)null); 7438 } 7439 7440 if ((flags&ActivityManager.RECENT_IGNORE_UNAVAILABLE) != 0) { 7441 // Check whether this activity is currently available. 7442 try { 7443 if (rti.origActivity != null) { 7444 if (pm.getActivityInfo(rti.origActivity, 0, userId) 7445 == null) { 7446 continue; 7447 } 7448 } else if (rti.baseIntent != null) { 7449 if (pm.queryIntentActivities(rti.baseIntent, 7450 null, 0, userId) == null) { 7451 continue; 7452 } 7453 } 7454 } catch (RemoteException e) { 7455 // Will never happen. 7456 } 7457 } 7458 7459 res.add(rti); 7460 maxNum--; 7461 } 7462 } 7463 return res; 7464 } 7465 } 7466 7467 private TaskRecord recentTaskForIdLocked(int id) { 7468 final int N = mRecentTasks.size(); 7469 for (int i=0; i<N; i++) { 7470 TaskRecord tr = mRecentTasks.get(i); 7471 if (tr.taskId == id) { 7472 return tr; 7473 } 7474 } 7475 return null; 7476 } 7477 7478 @Override 7479 public ActivityManager.TaskThumbnail getTaskThumbnail(int id) { 7480 synchronized (this) { 7481 enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER, 7482 "getTaskThumbnail()"); 7483 TaskRecord tr = recentTaskForIdLocked(id); 7484 if (tr != null) { 7485 return tr.getTaskThumbnailLocked(); 7486 } 7487 } 7488 return null; 7489 } 7490 7491 @Override 7492 public void setTaskDescription(IBinder token, ActivityManager.TaskDescription td) { 7493 synchronized (this) { 7494 ActivityRecord r = ActivityRecord.isInStackLocked(token); 7495 if (r != null) { 7496 r.taskDescription = td; 7497 r.task.updateTaskDescription(); 7498 } 7499 } 7500 } 7501 7502 private void killUnneededProcessLocked(ProcessRecord pr, String reason) { 7503 if (!pr.killedByAm) { 7504 Slog.i(TAG, "Killing " + pr.toShortString() + " (adj " + pr.setAdj + "): " + reason); 7505 EventLog.writeEvent(EventLogTags.AM_KILL, pr.userId, pr.pid, 7506 pr.processName, pr.setAdj, reason); 7507 pr.killedByAm = true; 7508 Process.killProcessQuiet(pr.pid); 7509 Process.killProcessGroup(pr.info.uid, pr.pid); 7510 } 7511 } 7512 7513 private void cleanUpRemovedTaskLocked(TaskRecord tr, int flags) { 7514 tr.disposeThumbnail(); 7515 mRecentTasks.remove(tr); 7516 tr.closeRecentsChain(); 7517 final boolean killProcesses = (flags&ActivityManager.REMOVE_TASK_KILL_PROCESS) != 0; 7518 Intent baseIntent = new Intent( 7519 tr.intent != null ? tr.intent : tr.affinityIntent); 7520 ComponentName component = baseIntent.getComponent(); 7521 if (component == null) { 7522 Slog.w(TAG, "Now component for base intent of task: " + tr); 7523 return; 7524 } 7525 7526 // Find any running services associated with this app. 7527 mServices.cleanUpRemovedTaskLocked(tr, component, baseIntent); 7528 7529 if (killProcesses) { 7530 // Find any running processes associated with this app. 7531 final String pkg = component.getPackageName(); 7532 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 7533 ArrayMap<String, SparseArray<ProcessRecord>> pmap = mProcessNames.getMap(); 7534 for (int i=0; i<pmap.size(); i++) { 7535 SparseArray<ProcessRecord> uids = pmap.valueAt(i); 7536 for (int j=0; j<uids.size(); j++) { 7537 ProcessRecord proc = uids.valueAt(j); 7538 if (proc.userId != tr.userId) { 7539 continue; 7540 } 7541 if (!proc.pkgList.containsKey(pkg)) { 7542 continue; 7543 } 7544 procs.add(proc); 7545 } 7546 } 7547 7548 // Kill the running processes. 7549 for (int i=0; i<procs.size(); i++) { 7550 ProcessRecord pr = procs.get(i); 7551 if (pr == mHomeProcess) { 7552 // Don't kill the home process along with tasks from the same package. 7553 continue; 7554 } 7555 if (pr.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 7556 killUnneededProcessLocked(pr, "remove task"); 7557 } else { 7558 pr.waitingToKill = "remove task"; 7559 } 7560 } 7561 } 7562 } 7563 7564 /** 7565 * Removes the task with the specified task id. 7566 * 7567 * @param taskId Identifier of the task to be removed. 7568 * @param flags Additional operational flags. May be 0 or 7569 * {@link ActivityManager#REMOVE_TASK_KILL_PROCESS}. 7570 * @return Returns true if the given task was found and removed. 7571 */ 7572 private boolean removeTaskByIdLocked(int taskId, int flags) { 7573 TaskRecord tr = recentTaskForIdLocked(taskId); 7574 if (tr != null) { 7575 tr.removeTaskActivitiesLocked(); 7576 cleanUpRemovedTaskLocked(tr, flags); 7577 if (tr.isPersistable) { 7578 notifyTaskPersisterLocked(tr, true); 7579 } 7580 return true; 7581 } 7582 return false; 7583 } 7584 7585 @Override 7586 public boolean removeTask(int taskId, int flags) { 7587 synchronized (this) { 7588 enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, 7589 "removeTask()"); 7590 long ident = Binder.clearCallingIdentity(); 7591 try { 7592 return removeTaskByIdLocked(taskId, flags); 7593 } finally { 7594 Binder.restoreCallingIdentity(ident); 7595 } 7596 } 7597 } 7598 7599 /** 7600 * TODO: Add mController hook 7601 */ 7602 @Override 7603 public void moveTaskToFront(int taskId, int flags, Bundle options) { 7604 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7605 "moveTaskToFront()"); 7606 7607 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToFront: moving taskId=" + taskId); 7608 synchronized(this) { 7609 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7610 Binder.getCallingUid(), "Task to front")) { 7611 ActivityOptions.abort(options); 7612 return; 7613 } 7614 final long origId = Binder.clearCallingIdentity(); 7615 try { 7616 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 7617 if (task == null) { 7618 return; 7619 } 7620 if (mStackSupervisor.isLockTaskModeViolation(task)) { 7621 mStackSupervisor.showLockTaskToast(); 7622 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode"); 7623 return; 7624 } 7625 final ActivityRecord prev = mStackSupervisor.topRunningActivityLocked(); 7626 if (prev != null && prev.isRecentsActivity()) { 7627 task.setTaskToReturnTo(ActivityRecord.RECENTS_ACTIVITY_TYPE); 7628 } 7629 mStackSupervisor.findTaskToMoveToFrontLocked(task, flags, options); 7630 } finally { 7631 Binder.restoreCallingIdentity(origId); 7632 } 7633 ActivityOptions.abort(options); 7634 } 7635 } 7636 7637 @Override 7638 public void moveTaskToBack(int taskId) { 7639 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7640 "moveTaskToBack()"); 7641 7642 synchronized(this) { 7643 TaskRecord tr = recentTaskForIdLocked(taskId); 7644 if (tr != null) { 7645 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToBack: moving task=" + tr); 7646 ActivityStack stack = tr.stack; 7647 if (stack.mResumedActivity != null && stack.mResumedActivity.task == tr) { 7648 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7649 Binder.getCallingUid(), "Task to back")) { 7650 return; 7651 } 7652 } 7653 final long origId = Binder.clearCallingIdentity(); 7654 try { 7655 stack.moveTaskToBackLocked(taskId, null); 7656 } finally { 7657 Binder.restoreCallingIdentity(origId); 7658 } 7659 } 7660 } 7661 } 7662 7663 /** 7664 * Moves an activity, and all of the other activities within the same task, to the bottom 7665 * of the history stack. The activity's order within the task is unchanged. 7666 * 7667 * @param token A reference to the activity we wish to move 7668 * @param nonRoot If false then this only works if the activity is the root 7669 * of a task; if true it will work for any activity in a task. 7670 * @return Returns true if the move completed, false if not. 7671 */ 7672 @Override 7673 public boolean moveActivityTaskToBack(IBinder token, boolean nonRoot) { 7674 enforceNotIsolatedCaller("moveActivityTaskToBack"); 7675 synchronized(this) { 7676 final long origId = Binder.clearCallingIdentity(); 7677 int taskId = ActivityRecord.getTaskForActivityLocked(token, !nonRoot); 7678 if (taskId >= 0) { 7679 return ActivityRecord.getStackLocked(token).moveTaskToBackLocked(taskId, null); 7680 } 7681 Binder.restoreCallingIdentity(origId); 7682 } 7683 return false; 7684 } 7685 7686 @Override 7687 public void moveTaskBackwards(int task) { 7688 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7689 "moveTaskBackwards()"); 7690 7691 synchronized(this) { 7692 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7693 Binder.getCallingUid(), "Task backwards")) { 7694 return; 7695 } 7696 final long origId = Binder.clearCallingIdentity(); 7697 moveTaskBackwardsLocked(task); 7698 Binder.restoreCallingIdentity(origId); 7699 } 7700 } 7701 7702 private final void moveTaskBackwardsLocked(int task) { 7703 Slog.e(TAG, "moveTaskBackwards not yet implemented!"); 7704 } 7705 7706 @Override 7707 public IBinder getHomeActivityToken() throws RemoteException { 7708 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7709 "getHomeActivityToken()"); 7710 synchronized (this) { 7711 return mStackSupervisor.getHomeActivityToken(); 7712 } 7713 } 7714 7715 @Override 7716 public IActivityContainer createActivityContainer(IBinder parentActivityToken, 7717 IActivityContainerCallback callback) throws RemoteException { 7718 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7719 "createActivityContainer()"); 7720 synchronized (this) { 7721 if (parentActivityToken == null) { 7722 throw new IllegalArgumentException("parent token must not be null"); 7723 } 7724 ActivityRecord r = ActivityRecord.forToken(parentActivityToken); 7725 if (r == null) { 7726 return null; 7727 } 7728 if (callback == null) { 7729 throw new IllegalArgumentException("callback must not be null"); 7730 } 7731 return mStackSupervisor.createActivityContainer(r, callback); 7732 } 7733 } 7734 7735 @Override 7736 public void deleteActivityContainer(IActivityContainer container) throws RemoteException { 7737 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7738 "deleteActivityContainer()"); 7739 synchronized (this) { 7740 mStackSupervisor.deleteActivityContainer(container); 7741 } 7742 } 7743 7744 @Override 7745 public IActivityContainer getEnclosingActivityContainer(IBinder activityToken) 7746 throws RemoteException { 7747 synchronized (this) { 7748 ActivityStack stack = ActivityRecord.getStackLocked(activityToken); 7749 if (stack != null) { 7750 return stack.mActivityContainer; 7751 } 7752 return null; 7753 } 7754 } 7755 7756 @Override 7757 public void moveTaskToStack(int taskId, int stackId, boolean toTop) { 7758 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7759 "moveTaskToStack()"); 7760 if (stackId == HOME_STACK_ID) { 7761 Slog.e(TAG, "moveTaskToStack: Attempt to move task " + taskId + " to home stack", 7762 new RuntimeException("here").fillInStackTrace()); 7763 } 7764 synchronized (this) { 7765 long ident = Binder.clearCallingIdentity(); 7766 try { 7767 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToStack: moving task=" + taskId + " to stackId=" 7768 + stackId + " toTop=" + toTop); 7769 mStackSupervisor.moveTaskToStack(taskId, stackId, toTop); 7770 } finally { 7771 Binder.restoreCallingIdentity(ident); 7772 } 7773 } 7774 } 7775 7776 @Override 7777 public void resizeStack(int stackBoxId, Rect bounds) { 7778 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7779 "resizeStackBox()"); 7780 long ident = Binder.clearCallingIdentity(); 7781 try { 7782 mWindowManager.resizeStack(stackBoxId, bounds); 7783 } finally { 7784 Binder.restoreCallingIdentity(ident); 7785 } 7786 } 7787 7788 @Override 7789 public List<StackInfo> getAllStackInfos() { 7790 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7791 "getAllStackInfos()"); 7792 long ident = Binder.clearCallingIdentity(); 7793 try { 7794 synchronized (this) { 7795 return mStackSupervisor.getAllStackInfosLocked(); 7796 } 7797 } finally { 7798 Binder.restoreCallingIdentity(ident); 7799 } 7800 } 7801 7802 @Override 7803 public StackInfo getStackInfo(int stackId) { 7804 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7805 "getStackInfo()"); 7806 long ident = Binder.clearCallingIdentity(); 7807 try { 7808 synchronized (this) { 7809 return mStackSupervisor.getStackInfoLocked(stackId); 7810 } 7811 } finally { 7812 Binder.restoreCallingIdentity(ident); 7813 } 7814 } 7815 7816 @Override 7817 public boolean isInHomeStack(int taskId) { 7818 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7819 "getStackInfo()"); 7820 long ident = Binder.clearCallingIdentity(); 7821 try { 7822 synchronized (this) { 7823 TaskRecord tr = recentTaskForIdLocked(taskId); 7824 return tr != null && tr.stack != null && tr.stack.isHomeStack(); 7825 } 7826 } finally { 7827 Binder.restoreCallingIdentity(ident); 7828 } 7829 } 7830 7831 @Override 7832 public int getTaskForActivity(IBinder token, boolean onlyRoot) { 7833 synchronized(this) { 7834 return ActivityRecord.getTaskForActivityLocked(token, onlyRoot); 7835 } 7836 } 7837 7838 private boolean isLockTaskAuthorized(String pkg) { 7839 final DevicePolicyManager dpm = (DevicePolicyManager) 7840 mContext.getSystemService(Context.DEVICE_POLICY_SERVICE); 7841 try { 7842 int uid = mContext.getPackageManager().getPackageUid(pkg, 7843 Binder.getCallingUserHandle().getIdentifier()); 7844 return (uid == Binder.getCallingUid()) && dpm != null && dpm.isLockTaskPermitted(pkg); 7845 } catch (NameNotFoundException e) { 7846 return false; 7847 } 7848 } 7849 7850 void startLockTaskMode(TaskRecord task) { 7851 final String pkg; 7852 synchronized (this) { 7853 pkg = task.intent.getComponent().getPackageName(); 7854 } 7855 boolean isSystemInitiated = Binder.getCallingUid() == Process.SYSTEM_UID; 7856 if (!isSystemInitiated && !isLockTaskAuthorized(pkg)) { 7857 final TaskRecord taskRecord = task; 7858 mHandler.post(new Runnable() { 7859 @Override 7860 public void run() { 7861 mLockToAppRequest.showLockTaskPrompt(taskRecord); 7862 } 7863 }); 7864 return; 7865 } 7866 long ident = Binder.clearCallingIdentity(); 7867 try { 7868 synchronized (this) { 7869 // Since we lost lock on task, make sure it is still there. 7870 task = mStackSupervisor.anyTaskForIdLocked(task.taskId); 7871 if (task != null) { 7872 if (!isSystemInitiated 7873 && ((mFocusedActivity == null) || (task != mFocusedActivity.task))) { 7874 throw new IllegalArgumentException("Invalid task, not in foreground"); 7875 } 7876 mStackSupervisor.setLockTaskModeLocked(task, !isSystemInitiated); 7877 } 7878 } 7879 } finally { 7880 Binder.restoreCallingIdentity(ident); 7881 } 7882 } 7883 7884 @Override 7885 public void startLockTaskMode(int taskId) { 7886 final TaskRecord task; 7887 long ident = Binder.clearCallingIdentity(); 7888 try { 7889 synchronized (this) { 7890 task = mStackSupervisor.anyTaskForIdLocked(taskId); 7891 } 7892 } finally { 7893 Binder.restoreCallingIdentity(ident); 7894 } 7895 if (task != null) { 7896 startLockTaskMode(task); 7897 } 7898 } 7899 7900 @Override 7901 public void startLockTaskMode(IBinder token) { 7902 final TaskRecord task; 7903 long ident = Binder.clearCallingIdentity(); 7904 try { 7905 synchronized (this) { 7906 final ActivityRecord r = ActivityRecord.forToken(token); 7907 if (r == null) { 7908 return; 7909 } 7910 task = r.task; 7911 } 7912 } finally { 7913 Binder.restoreCallingIdentity(ident); 7914 } 7915 if (task != null) { 7916 startLockTaskMode(task); 7917 } 7918 } 7919 7920 @Override 7921 public void startLockTaskModeOnCurrent() throws RemoteException { 7922 checkCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS); 7923 ActivityRecord r = null; 7924 synchronized (this) { 7925 r = mStackSupervisor.topRunningActivityLocked(); 7926 } 7927 startLockTaskMode(r.task); 7928 } 7929 7930 @Override 7931 public void stopLockTaskMode() { 7932 // Verify that the user matches the package of the intent for the TaskRecord 7933 // we are locked to or systtem. This will ensure the same caller for startLockTaskMode 7934 // and stopLockTaskMode. 7935 final int callingUid = Binder.getCallingUid(); 7936 if (callingUid != Process.SYSTEM_UID) { 7937 try { 7938 String pkg = 7939 mStackSupervisor.mLockTaskModeTask.intent.getComponent().getPackageName(); 7940 int uid = mContext.getPackageManager().getPackageUid(pkg, 7941 Binder.getCallingUserHandle().getIdentifier()); 7942 if (uid != callingUid) { 7943 throw new SecurityException("Invalid uid, expected " + uid); 7944 } 7945 } catch (NameNotFoundException e) { 7946 Log.d(TAG, "stopLockTaskMode " + e); 7947 return; 7948 } 7949 } 7950 long ident = Binder.clearCallingIdentity(); 7951 try { 7952 Log.d(TAG, "stopLockTaskMode"); 7953 // Stop lock task 7954 synchronized (this) { 7955 mStackSupervisor.setLockTaskModeLocked(null, false); 7956 } 7957 } finally { 7958 Binder.restoreCallingIdentity(ident); 7959 } 7960 } 7961 7962 @Override 7963 public void stopLockTaskModeOnCurrent() throws RemoteException { 7964 checkCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS); 7965 long ident = Binder.clearCallingIdentity(); 7966 try { 7967 stopLockTaskMode(); 7968 } finally { 7969 Binder.restoreCallingIdentity(ident); 7970 } 7971 } 7972 7973 @Override 7974 public boolean isInLockTaskMode() { 7975 synchronized (this) { 7976 return mStackSupervisor.isInLockTaskMode(); 7977 } 7978 } 7979 7980 // ========================================================= 7981 // CONTENT PROVIDERS 7982 // ========================================================= 7983 7984 private final List<ProviderInfo> generateApplicationProvidersLocked(ProcessRecord app) { 7985 List<ProviderInfo> providers = null; 7986 try { 7987 providers = AppGlobals.getPackageManager(). 7988 queryContentProviders(app.processName, app.uid, 7989 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS); 7990 } catch (RemoteException ex) { 7991 } 7992 if (DEBUG_MU) 7993 Slog.v(TAG_MU, "generateApplicationProvidersLocked, app.info.uid = " + app.uid); 7994 int userId = app.userId; 7995 if (providers != null) { 7996 int N = providers.size(); 7997 app.pubProviders.ensureCapacity(N + app.pubProviders.size()); 7998 for (int i=0; i<N; i++) { 7999 ProviderInfo cpi = 8000 (ProviderInfo)providers.get(i); 8001 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo, 8002 cpi.name, cpi.flags); 8003 if (singleton && UserHandle.getUserId(app.uid) != 0) { 8004 // This is a singleton provider, but a user besides the 8005 // default user is asking to initialize a process it runs 8006 // in... well, no, it doesn't actually run in this process, 8007 // it runs in the process of the default user. Get rid of it. 8008 providers.remove(i); 8009 N--; 8010 i--; 8011 continue; 8012 } 8013 8014 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 8015 ContentProviderRecord cpr = mProviderMap.getProviderByClass(comp, userId); 8016 if (cpr == null) { 8017 cpr = new ContentProviderRecord(this, cpi, app.info, comp, singleton); 8018 mProviderMap.putProviderByClass(comp, cpr); 8019 } 8020 if (DEBUG_MU) 8021 Slog.v(TAG_MU, "generateApplicationProvidersLocked, cpi.uid = " + cpr.uid); 8022 app.pubProviders.put(cpi.name, cpr); 8023 if (!cpi.multiprocess || !"android".equals(cpi.packageName)) { 8024 // Don't add this if it is a platform component that is marked 8025 // to run in multiple processes, because this is actually 8026 // part of the framework so doesn't make sense to track as a 8027 // separate apk in the process. 8028 app.addPackage(cpi.applicationInfo.packageName, cpi.applicationInfo.versionCode, 8029 mProcessStats); 8030 } 8031 ensurePackageDexOpt(cpi.applicationInfo.packageName); 8032 } 8033 } 8034 return providers; 8035 } 8036 8037 /** 8038 * Check if {@link ProcessRecord} has a possible chance at accessing the 8039 * given {@link ProviderInfo}. Final permission checking is always done 8040 * in {@link ContentProvider}. 8041 */ 8042 private final String checkContentProviderPermissionLocked( 8043 ProviderInfo cpi, ProcessRecord r, int userId, boolean checkUser) { 8044 final int callingPid = (r != null) ? r.pid : Binder.getCallingPid(); 8045 final int callingUid = (r != null) ? r.uid : Binder.getCallingUid(); 8046 boolean checkedGrants = false; 8047 if (checkUser) { 8048 // Looking for cross-user grants before enforcing the typical cross-users permissions 8049 int tmpTargetUserId = unsafeConvertIncomingUser(UserHandle.getUserId(callingUid)); 8050 if (tmpTargetUserId != userId) { 8051 if (checkAuthorityGrants(callingUid, cpi, tmpTargetUserId, checkUser)) { 8052 return null; 8053 } 8054 checkedGrants = true; 8055 } 8056 userId = handleIncomingUser(callingPid, callingUid, userId, 8057 false, ALLOW_NON_FULL_IN_PROFILE, 8058 "checkContentProviderPermissionLocked " + cpi.authority, null); 8059 if (userId != tmpTargetUserId) { 8060 // When we actually went to determine the final targer user ID, this ended 8061 // up different than our initial check for the authority. This is because 8062 // they had asked for USER_CURRENT_OR_SELF and we ended up switching to 8063 // SELF. So we need to re-check the grants again. 8064 checkedGrants = false; 8065 } 8066 } 8067 if (checkComponentPermission(cpi.readPermission, callingPid, callingUid, 8068 cpi.applicationInfo.uid, cpi.exported) 8069 == PackageManager.PERMISSION_GRANTED) { 8070 return null; 8071 } 8072 if (checkComponentPermission(cpi.writePermission, callingPid, callingUid, 8073 cpi.applicationInfo.uid, cpi.exported) 8074 == PackageManager.PERMISSION_GRANTED) { 8075 return null; 8076 } 8077 8078 PathPermission[] pps = cpi.pathPermissions; 8079 if (pps != null) { 8080 int i = pps.length; 8081 while (i > 0) { 8082 i--; 8083 PathPermission pp = pps[i]; 8084 String pprperm = pp.getReadPermission(); 8085 if (pprperm != null && checkComponentPermission(pprperm, callingPid, callingUid, 8086 cpi.applicationInfo.uid, cpi.exported) 8087 == PackageManager.PERMISSION_GRANTED) { 8088 return null; 8089 } 8090 String ppwperm = pp.getWritePermission(); 8091 if (ppwperm != null && checkComponentPermission(ppwperm, callingPid, callingUid, 8092 cpi.applicationInfo.uid, cpi.exported) 8093 == PackageManager.PERMISSION_GRANTED) { 8094 return null; 8095 } 8096 } 8097 } 8098 if (!checkedGrants && checkAuthorityGrants(callingUid, cpi, userId, checkUser)) { 8099 return null; 8100 } 8101 8102 String msg; 8103 if (!cpi.exported) { 8104 msg = "Permission Denial: opening provider " + cpi.name 8105 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 8106 + ", uid=" + callingUid + ") that is not exported from uid " 8107 + cpi.applicationInfo.uid; 8108 } else { 8109 msg = "Permission Denial: opening provider " + cpi.name 8110 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 8111 + ", uid=" + callingUid + ") requires " 8112 + cpi.readPermission + " or " + cpi.writePermission; 8113 } 8114 Slog.w(TAG, msg); 8115 return msg; 8116 } 8117 8118 /** 8119 * Returns if the ContentProvider has granted a uri to callingUid 8120 */ 8121 boolean checkAuthorityGrants(int callingUid, ProviderInfo cpi, int userId, boolean checkUser) { 8122 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 8123 if (perms != null) { 8124 for (int i=perms.size()-1; i>=0; i--) { 8125 GrantUri grantUri = perms.keyAt(i); 8126 if (grantUri.sourceUserId == userId || !checkUser) { 8127 if (matchesProvider(grantUri.uri, cpi)) { 8128 return true; 8129 } 8130 } 8131 } 8132 } 8133 return false; 8134 } 8135 8136 /** 8137 * Returns true if the uri authority is one of the authorities specified in the provider. 8138 */ 8139 boolean matchesProvider(Uri uri, ProviderInfo cpi) { 8140 String uriAuth = uri.getAuthority(); 8141 String cpiAuth = cpi.authority; 8142 if (cpiAuth.indexOf(';') == -1) { 8143 return cpiAuth.equals(uriAuth); 8144 } 8145 String[] cpiAuths = cpiAuth.split(";"); 8146 int length = cpiAuths.length; 8147 for (int i = 0; i < length; i++) { 8148 if (cpiAuths[i].equals(uriAuth)) return true; 8149 } 8150 return false; 8151 } 8152 8153 ContentProviderConnection incProviderCountLocked(ProcessRecord r, 8154 final ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 8155 if (r != null) { 8156 for (int i=0; i<r.conProviders.size(); i++) { 8157 ContentProviderConnection conn = r.conProviders.get(i); 8158 if (conn.provider == cpr) { 8159 if (DEBUG_PROVIDER) Slog.v(TAG, 8160 "Adding provider requested by " 8161 + r.processName + " from process " 8162 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 8163 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 8164 if (stable) { 8165 conn.stableCount++; 8166 conn.numStableIncs++; 8167 } else { 8168 conn.unstableCount++; 8169 conn.numUnstableIncs++; 8170 } 8171 return conn; 8172 } 8173 } 8174 ContentProviderConnection conn = new ContentProviderConnection(cpr, r); 8175 if (stable) { 8176 conn.stableCount = 1; 8177 conn.numStableIncs = 1; 8178 } else { 8179 conn.unstableCount = 1; 8180 conn.numUnstableIncs = 1; 8181 } 8182 cpr.connections.add(conn); 8183 r.conProviders.add(conn); 8184 return conn; 8185 } 8186 cpr.addExternalProcessHandleLocked(externalProcessToken); 8187 return null; 8188 } 8189 8190 boolean decProviderCountLocked(ContentProviderConnection conn, 8191 ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 8192 if (conn != null) { 8193 cpr = conn.provider; 8194 if (DEBUG_PROVIDER) Slog.v(TAG, 8195 "Removing provider requested by " 8196 + conn.client.processName + " from process " 8197 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 8198 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 8199 if (stable) { 8200 conn.stableCount--; 8201 } else { 8202 conn.unstableCount--; 8203 } 8204 if (conn.stableCount == 0 && conn.unstableCount == 0) { 8205 cpr.connections.remove(conn); 8206 conn.client.conProviders.remove(conn); 8207 return true; 8208 } 8209 return false; 8210 } 8211 cpr.removeExternalProcessHandleLocked(externalProcessToken); 8212 return false; 8213 } 8214 8215 private final ContentProviderHolder getContentProviderImpl(IApplicationThread caller, 8216 String name, IBinder token, boolean stable, int userId) { 8217 ContentProviderRecord cpr; 8218 ContentProviderConnection conn = null; 8219 ProviderInfo cpi = null; 8220 8221 synchronized(this) { 8222 ProcessRecord r = null; 8223 if (caller != null) { 8224 r = getRecordForAppLocked(caller); 8225 if (r == null) { 8226 throw new SecurityException( 8227 "Unable to find app for caller " + caller 8228 + " (pid=" + Binder.getCallingPid() 8229 + ") when getting content provider " + name); 8230 } 8231 } 8232 8233 boolean checkCrossUser = true; 8234 8235 // First check if this content provider has been published... 8236 cpr = mProviderMap.getProviderByName(name, userId); 8237 // If that didn't work, check if it exists for user 0 and then 8238 // verify that it's a singleton provider before using it. 8239 if (cpr == null && userId != UserHandle.USER_OWNER) { 8240 cpr = mProviderMap.getProviderByName(name, UserHandle.USER_OWNER); 8241 if (cpr != null) { 8242 cpi = cpr.info; 8243 if (isSingleton(cpi.processName, cpi.applicationInfo, 8244 cpi.name, cpi.flags) 8245 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid)) { 8246 userId = UserHandle.USER_OWNER; 8247 checkCrossUser = false; 8248 } else { 8249 cpr = null; 8250 cpi = null; 8251 } 8252 } 8253 } 8254 8255 boolean providerRunning = cpr != null; 8256 if (providerRunning) { 8257 cpi = cpr.info; 8258 String msg; 8259 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, checkCrossUser)) 8260 != null) { 8261 throw new SecurityException(msg); 8262 } 8263 8264 if (r != null && cpr.canRunHere(r)) { 8265 // This provider has been published or is in the process 8266 // of being published... but it is also allowed to run 8267 // in the caller's process, so don't make a connection 8268 // and just let the caller instantiate its own instance. 8269 ContentProviderHolder holder = cpr.newHolder(null); 8270 // don't give caller the provider object, it needs 8271 // to make its own. 8272 holder.provider = null; 8273 return holder; 8274 } 8275 8276 final long origId = Binder.clearCallingIdentity(); 8277 8278 // In this case the provider instance already exists, so we can 8279 // return it right away. 8280 conn = incProviderCountLocked(r, cpr, token, stable); 8281 if (conn != null && (conn.stableCount+conn.unstableCount) == 1) { 8282 if (cpr.proc != null && r.setAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 8283 // If this is a perceptible app accessing the provider, 8284 // make sure to count it as being accessed and thus 8285 // back up on the LRU list. This is good because 8286 // content providers are often expensive to start. 8287 updateLruProcessLocked(cpr.proc, false, null); 8288 } 8289 } 8290 8291 if (cpr.proc != null) { 8292 if (false) { 8293 if (cpr.name.flattenToShortString().equals( 8294 "com.android.providers.calendar/.CalendarProvider2")) { 8295 Slog.v(TAG, "****************** KILLING " 8296 + cpr.name.flattenToShortString()); 8297 Process.killProcess(cpr.proc.pid); 8298 } 8299 } 8300 boolean success = updateOomAdjLocked(cpr.proc); 8301 if (DEBUG_PROVIDER) Slog.i(TAG, "Adjust success: " + success); 8302 // NOTE: there is still a race here where a signal could be 8303 // pending on the process even though we managed to update its 8304 // adj level. Not sure what to do about this, but at least 8305 // the race is now smaller. 8306 if (!success) { 8307 // Uh oh... it looks like the provider's process 8308 // has been killed on us. We need to wait for a new 8309 // process to be started, and make sure its death 8310 // doesn't kill our process. 8311 Slog.i(TAG, 8312 "Existing provider " + cpr.name.flattenToShortString() 8313 + " is crashing; detaching " + r); 8314 boolean lastRef = decProviderCountLocked(conn, cpr, token, stable); 8315 appDiedLocked(cpr.proc, cpr.proc.pid, cpr.proc.thread); 8316 if (!lastRef) { 8317 // This wasn't the last ref our process had on 8318 // the provider... we have now been killed, bail. 8319 return null; 8320 } 8321 providerRunning = false; 8322 conn = null; 8323 } 8324 } 8325 8326 Binder.restoreCallingIdentity(origId); 8327 } 8328 8329 boolean singleton; 8330 if (!providerRunning) { 8331 try { 8332 cpi = AppGlobals.getPackageManager(). 8333 resolveContentProvider(name, 8334 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS, userId); 8335 } catch (RemoteException ex) { 8336 } 8337 if (cpi == null) { 8338 return null; 8339 } 8340 // If the provider is a singleton AND 8341 // (it's a call within the same user || the provider is a 8342 // privileged app) 8343 // Then allow connecting to the singleton provider 8344 singleton = isSingleton(cpi.processName, cpi.applicationInfo, 8345 cpi.name, cpi.flags) 8346 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid); 8347 if (singleton) { 8348 userId = UserHandle.USER_OWNER; 8349 } 8350 cpi.applicationInfo = getAppInfoForUser(cpi.applicationInfo, userId); 8351 8352 String msg; 8353 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, !singleton)) 8354 != null) { 8355 throw new SecurityException(msg); 8356 } 8357 8358 if (!mProcessesReady && !mDidUpdate && !mWaitingUpdate 8359 && !cpi.processName.equals("system")) { 8360 // If this content provider does not run in the system 8361 // process, and the system is not yet ready to run other 8362 // processes, then fail fast instead of hanging. 8363 throw new IllegalArgumentException( 8364 "Attempt to launch content provider before system ready"); 8365 } 8366 8367 // Make sure that the user who owns this provider is started. If not, 8368 // we don't want to allow it to run. 8369 if (mStartedUsers.get(userId) == null) { 8370 Slog.w(TAG, "Unable to launch app " 8371 + cpi.applicationInfo.packageName + "/" 8372 + cpi.applicationInfo.uid + " for provider " 8373 + name + ": user " + userId + " is stopped"); 8374 return null; 8375 } 8376 8377 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 8378 cpr = mProviderMap.getProviderByClass(comp, userId); 8379 final boolean firstClass = cpr == null; 8380 if (firstClass) { 8381 try { 8382 ApplicationInfo ai = 8383 AppGlobals.getPackageManager(). 8384 getApplicationInfo( 8385 cpi.applicationInfo.packageName, 8386 STOCK_PM_FLAGS, userId); 8387 if (ai == null) { 8388 Slog.w(TAG, "No package info for content provider " 8389 + cpi.name); 8390 return null; 8391 } 8392 ai = getAppInfoForUser(ai, userId); 8393 cpr = new ContentProviderRecord(this, cpi, ai, comp, singleton); 8394 } catch (RemoteException ex) { 8395 // pm is in same process, this will never happen. 8396 } 8397 } 8398 8399 if (r != null && cpr.canRunHere(r)) { 8400 // If this is a multiprocess provider, then just return its 8401 // info and allow the caller to instantiate it. Only do 8402 // this if the provider is the same user as the caller's 8403 // process, or can run as root (so can be in any process). 8404 return cpr.newHolder(null); 8405 } 8406 8407 if (DEBUG_PROVIDER) { 8408 RuntimeException e = new RuntimeException("here"); 8409 Slog.w(TAG, "LAUNCHING REMOTE PROVIDER (myuid " + (r != null ? r.uid : null) 8410 + " pruid " + cpr.appInfo.uid + "): " + cpr.info.name, e); 8411 } 8412 8413 // This is single process, and our app is now connecting to it. 8414 // See if we are already in the process of launching this 8415 // provider. 8416 final int N = mLaunchingProviders.size(); 8417 int i; 8418 for (i=0; i<N; i++) { 8419 if (mLaunchingProviders.get(i) == cpr) { 8420 break; 8421 } 8422 } 8423 8424 // If the provider is not already being launched, then get it 8425 // started. 8426 if (i >= N) { 8427 final long origId = Binder.clearCallingIdentity(); 8428 8429 try { 8430 // Content provider is now in use, its package can't be stopped. 8431 try { 8432 AppGlobals.getPackageManager().setPackageStoppedState( 8433 cpr.appInfo.packageName, false, userId); 8434 } catch (RemoteException e) { 8435 } catch (IllegalArgumentException e) { 8436 Slog.w(TAG, "Failed trying to unstop package " 8437 + cpr.appInfo.packageName + ": " + e); 8438 } 8439 8440 // Use existing process if already started 8441 ProcessRecord proc = getProcessRecordLocked( 8442 cpi.processName, cpr.appInfo.uid, false); 8443 if (proc != null && proc.thread != null) { 8444 if (DEBUG_PROVIDER) { 8445 Slog.d(TAG, "Installing in existing process " + proc); 8446 } 8447 proc.pubProviders.put(cpi.name, cpr); 8448 try { 8449 proc.thread.scheduleInstallProvider(cpi); 8450 } catch (RemoteException e) { 8451 } 8452 } else { 8453 proc = startProcessLocked(cpi.processName, 8454 cpr.appInfo, false, 0, "content provider", 8455 new ComponentName(cpi.applicationInfo.packageName, 8456 cpi.name), false, false, false); 8457 if (proc == null) { 8458 Slog.w(TAG, "Unable to launch app " 8459 + cpi.applicationInfo.packageName + "/" 8460 + cpi.applicationInfo.uid + " for provider " 8461 + name + ": process is bad"); 8462 return null; 8463 } 8464 } 8465 cpr.launchingApp = proc; 8466 mLaunchingProviders.add(cpr); 8467 } finally { 8468 Binder.restoreCallingIdentity(origId); 8469 } 8470 } 8471 8472 // Make sure the provider is published (the same provider class 8473 // may be published under multiple names). 8474 if (firstClass) { 8475 mProviderMap.putProviderByClass(comp, cpr); 8476 } 8477 8478 mProviderMap.putProviderByName(name, cpr); 8479 conn = incProviderCountLocked(r, cpr, token, stable); 8480 if (conn != null) { 8481 conn.waiting = true; 8482 } 8483 } 8484 } 8485 8486 // Wait for the provider to be published... 8487 synchronized (cpr) { 8488 while (cpr.provider == null) { 8489 if (cpr.launchingApp == null) { 8490 Slog.w(TAG, "Unable to launch app " 8491 + cpi.applicationInfo.packageName + "/" 8492 + cpi.applicationInfo.uid + " for provider " 8493 + name + ": launching app became null"); 8494 EventLog.writeEvent(EventLogTags.AM_PROVIDER_LOST_PROCESS, 8495 UserHandle.getUserId(cpi.applicationInfo.uid), 8496 cpi.applicationInfo.packageName, 8497 cpi.applicationInfo.uid, name); 8498 return null; 8499 } 8500 try { 8501 if (DEBUG_MU) { 8502 Slog.v(TAG_MU, "Waiting to start provider " + cpr + " launchingApp=" 8503 + cpr.launchingApp); 8504 } 8505 if (conn != null) { 8506 conn.waiting = true; 8507 } 8508 cpr.wait(); 8509 } catch (InterruptedException ex) { 8510 } finally { 8511 if (conn != null) { 8512 conn.waiting = false; 8513 } 8514 } 8515 } 8516 } 8517 return cpr != null ? cpr.newHolder(conn) : null; 8518 } 8519 8520 @Override 8521 public final ContentProviderHolder getContentProvider( 8522 IApplicationThread caller, String name, int userId, boolean stable) { 8523 enforceNotIsolatedCaller("getContentProvider"); 8524 if (caller == null) { 8525 String msg = "null IApplicationThread when getting content provider " 8526 + name; 8527 Slog.w(TAG, msg); 8528 throw new SecurityException(msg); 8529 } 8530 // The incoming user check is now handled in checkContentProviderPermissionLocked() to deal 8531 // with cross-user grant. 8532 return getContentProviderImpl(caller, name, null, stable, userId); 8533 } 8534 8535 public ContentProviderHolder getContentProviderExternal( 8536 String name, int userId, IBinder token) { 8537 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 8538 "Do not have permission in call getContentProviderExternal()"); 8539 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 8540 false, ALLOW_FULL_ONLY, "getContentProvider", null); 8541 return getContentProviderExternalUnchecked(name, token, userId); 8542 } 8543 8544 private ContentProviderHolder getContentProviderExternalUnchecked(String name, 8545 IBinder token, int userId) { 8546 return getContentProviderImpl(null, name, token, true, userId); 8547 } 8548 8549 /** 8550 * Drop a content provider from a ProcessRecord's bookkeeping 8551 */ 8552 public void removeContentProvider(IBinder connection, boolean stable) { 8553 enforceNotIsolatedCaller("removeContentProvider"); 8554 long ident = Binder.clearCallingIdentity(); 8555 try { 8556 synchronized (this) { 8557 ContentProviderConnection conn; 8558 try { 8559 conn = (ContentProviderConnection)connection; 8560 } catch (ClassCastException e) { 8561 String msg ="removeContentProvider: " + connection 8562 + " not a ContentProviderConnection"; 8563 Slog.w(TAG, msg); 8564 throw new IllegalArgumentException(msg); 8565 } 8566 if (conn == null) { 8567 throw new NullPointerException("connection is null"); 8568 } 8569 if (decProviderCountLocked(conn, null, null, stable)) { 8570 updateOomAdjLocked(); 8571 } 8572 } 8573 } finally { 8574 Binder.restoreCallingIdentity(ident); 8575 } 8576 } 8577 8578 public void removeContentProviderExternal(String name, IBinder token) { 8579 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 8580 "Do not have permission in call removeContentProviderExternal()"); 8581 removeContentProviderExternalUnchecked(name, token, UserHandle.getCallingUserId()); 8582 } 8583 8584 private void removeContentProviderExternalUnchecked(String name, IBinder token, int userId) { 8585 synchronized (this) { 8586 ContentProviderRecord cpr = mProviderMap.getProviderByName(name, userId); 8587 if(cpr == null) { 8588 //remove from mProvidersByClass 8589 if(localLOGV) Slog.v(TAG, name+" content provider not found in providers list"); 8590 return; 8591 } 8592 8593 //update content provider record entry info 8594 ComponentName comp = new ComponentName(cpr.info.packageName, cpr.info.name); 8595 ContentProviderRecord localCpr = mProviderMap.getProviderByClass(comp, userId); 8596 if (localCpr.hasExternalProcessHandles()) { 8597 if (localCpr.removeExternalProcessHandleLocked(token)) { 8598 updateOomAdjLocked(); 8599 } else { 8600 Slog.e(TAG, "Attmpt to remove content provider " + localCpr 8601 + " with no external reference for token: " 8602 + token + "."); 8603 } 8604 } else { 8605 Slog.e(TAG, "Attmpt to remove content provider: " + localCpr 8606 + " with no external references."); 8607 } 8608 } 8609 } 8610 8611 public final void publishContentProviders(IApplicationThread caller, 8612 List<ContentProviderHolder> providers) { 8613 if (providers == null) { 8614 return; 8615 } 8616 8617 enforceNotIsolatedCaller("publishContentProviders"); 8618 synchronized (this) { 8619 final ProcessRecord r = getRecordForAppLocked(caller); 8620 if (DEBUG_MU) 8621 Slog.v(TAG_MU, "ProcessRecord uid = " + r.uid); 8622 if (r == null) { 8623 throw new SecurityException( 8624 "Unable to find app for caller " + caller 8625 + " (pid=" + Binder.getCallingPid() 8626 + ") when publishing content providers"); 8627 } 8628 8629 final long origId = Binder.clearCallingIdentity(); 8630 8631 final int N = providers.size(); 8632 for (int i=0; i<N; i++) { 8633 ContentProviderHolder src = providers.get(i); 8634 if (src == null || src.info == null || src.provider == null) { 8635 continue; 8636 } 8637 ContentProviderRecord dst = r.pubProviders.get(src.info.name); 8638 if (DEBUG_MU) 8639 Slog.v(TAG_MU, "ContentProviderRecord uid = " + dst.uid); 8640 if (dst != null) { 8641 ComponentName comp = new ComponentName(dst.info.packageName, dst.info.name); 8642 mProviderMap.putProviderByClass(comp, dst); 8643 String names[] = dst.info.authority.split(";"); 8644 for (int j = 0; j < names.length; j++) { 8645 mProviderMap.putProviderByName(names[j], dst); 8646 } 8647 8648 int NL = mLaunchingProviders.size(); 8649 int j; 8650 for (j=0; j<NL; j++) { 8651 if (mLaunchingProviders.get(j) == dst) { 8652 mLaunchingProviders.remove(j); 8653 j--; 8654 NL--; 8655 } 8656 } 8657 synchronized (dst) { 8658 dst.provider = src.provider; 8659 dst.proc = r; 8660 dst.notifyAll(); 8661 } 8662 updateOomAdjLocked(r); 8663 } 8664 } 8665 8666 Binder.restoreCallingIdentity(origId); 8667 } 8668 } 8669 8670 public boolean refContentProvider(IBinder connection, int stable, int unstable) { 8671 ContentProviderConnection conn; 8672 try { 8673 conn = (ContentProviderConnection)connection; 8674 } catch (ClassCastException e) { 8675 String msg ="refContentProvider: " + connection 8676 + " not a ContentProviderConnection"; 8677 Slog.w(TAG, msg); 8678 throw new IllegalArgumentException(msg); 8679 } 8680 if (conn == null) { 8681 throw new NullPointerException("connection is null"); 8682 } 8683 8684 synchronized (this) { 8685 if (stable > 0) { 8686 conn.numStableIncs += stable; 8687 } 8688 stable = conn.stableCount + stable; 8689 if (stable < 0) { 8690 throw new IllegalStateException("stableCount < 0: " + stable); 8691 } 8692 8693 if (unstable > 0) { 8694 conn.numUnstableIncs += unstable; 8695 } 8696 unstable = conn.unstableCount + unstable; 8697 if (unstable < 0) { 8698 throw new IllegalStateException("unstableCount < 0: " + unstable); 8699 } 8700 8701 if ((stable+unstable) <= 0) { 8702 throw new IllegalStateException("ref counts can't go to zero here: stable=" 8703 + stable + " unstable=" + unstable); 8704 } 8705 conn.stableCount = stable; 8706 conn.unstableCount = unstable; 8707 return !conn.dead; 8708 } 8709 } 8710 8711 public void unstableProviderDied(IBinder connection) { 8712 ContentProviderConnection conn; 8713 try { 8714 conn = (ContentProviderConnection)connection; 8715 } catch (ClassCastException e) { 8716 String msg ="refContentProvider: " + connection 8717 + " not a ContentProviderConnection"; 8718 Slog.w(TAG, msg); 8719 throw new IllegalArgumentException(msg); 8720 } 8721 if (conn == null) { 8722 throw new NullPointerException("connection is null"); 8723 } 8724 8725 // Safely retrieve the content provider associated with the connection. 8726 IContentProvider provider; 8727 synchronized (this) { 8728 provider = conn.provider.provider; 8729 } 8730 8731 if (provider == null) { 8732 // Um, yeah, we're way ahead of you. 8733 return; 8734 } 8735 8736 // Make sure the caller is being honest with us. 8737 if (provider.asBinder().pingBinder()) { 8738 // Er, no, still looks good to us. 8739 synchronized (this) { 8740 Slog.w(TAG, "unstableProviderDied: caller " + Binder.getCallingUid() 8741 + " says " + conn + " died, but we don't agree"); 8742 return; 8743 } 8744 } 8745 8746 // Well look at that! It's dead! 8747 synchronized (this) { 8748 if (conn.provider.provider != provider) { 8749 // But something changed... good enough. 8750 return; 8751 } 8752 8753 ProcessRecord proc = conn.provider.proc; 8754 if (proc == null || proc.thread == null) { 8755 // Seems like the process is already cleaned up. 8756 return; 8757 } 8758 8759 // As far as we're concerned, this is just like receiving a 8760 // death notification... just a bit prematurely. 8761 Slog.i(TAG, "Process " + proc.processName + " (pid " + proc.pid 8762 + ") early provider death"); 8763 final long ident = Binder.clearCallingIdentity(); 8764 try { 8765 appDiedLocked(proc, proc.pid, proc.thread); 8766 } finally { 8767 Binder.restoreCallingIdentity(ident); 8768 } 8769 } 8770 } 8771 8772 @Override 8773 public void appNotRespondingViaProvider(IBinder connection) { 8774 enforceCallingPermission( 8775 android.Manifest.permission.REMOVE_TASKS, "appNotRespondingViaProvider()"); 8776 8777 final ContentProviderConnection conn = (ContentProviderConnection) connection; 8778 if (conn == null) { 8779 Slog.w(TAG, "ContentProviderConnection is null"); 8780 return; 8781 } 8782 8783 final ProcessRecord host = conn.provider.proc; 8784 if (host == null) { 8785 Slog.w(TAG, "Failed to find hosting ProcessRecord"); 8786 return; 8787 } 8788 8789 final long token = Binder.clearCallingIdentity(); 8790 try { 8791 appNotResponding(host, null, null, false, "ContentProvider not responding"); 8792 } finally { 8793 Binder.restoreCallingIdentity(token); 8794 } 8795 } 8796 8797 public final void installSystemProviders() { 8798 List<ProviderInfo> providers; 8799 synchronized (this) { 8800 ProcessRecord app = mProcessNames.get("system", Process.SYSTEM_UID); 8801 providers = generateApplicationProvidersLocked(app); 8802 if (providers != null) { 8803 for (int i=providers.size()-1; i>=0; i--) { 8804 ProviderInfo pi = (ProviderInfo)providers.get(i); 8805 if ((pi.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) == 0) { 8806 Slog.w(TAG, "Not installing system proc provider " + pi.name 8807 + ": not system .apk"); 8808 providers.remove(i); 8809 } 8810 } 8811 } 8812 } 8813 if (providers != null) { 8814 mSystemThread.installSystemProviders(providers); 8815 } 8816 8817 mCoreSettingsObserver = new CoreSettingsObserver(this); 8818 8819 mUsageStatsService.monitorPackages(); 8820 } 8821 8822 /** 8823 * Allows app to retrieve the MIME type of a URI without having permission 8824 * to access its content provider. 8825 * 8826 * CTS tests for this functionality can be run with "runtest cts-appsecurity". 8827 * 8828 * Test cases are at cts/tests/appsecurity-tests/test-apps/UsePermissionDiffCert/ 8829 * src/com/android/cts/usespermissiondiffcertapp/AccessPermissionWithDiffSigTest.java 8830 */ 8831 public String getProviderMimeType(Uri uri, int userId) { 8832 enforceNotIsolatedCaller("getProviderMimeType"); 8833 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 8834 userId, false, ALLOW_NON_FULL_IN_PROFILE, "getProviderMimeType", null); 8835 final String name = uri.getAuthority(); 8836 final long ident = Binder.clearCallingIdentity(); 8837 ContentProviderHolder holder = null; 8838 8839 try { 8840 holder = getContentProviderExternalUnchecked(name, null, userId); 8841 if (holder != null) { 8842 return holder.provider.getType(uri); 8843 } 8844 } catch (RemoteException e) { 8845 Log.w(TAG, "Content provider dead retrieving " + uri, e); 8846 return null; 8847 } finally { 8848 if (holder != null) { 8849 removeContentProviderExternalUnchecked(name, null, userId); 8850 } 8851 Binder.restoreCallingIdentity(ident); 8852 } 8853 8854 return null; 8855 } 8856 8857 // ========================================================= 8858 // GLOBAL MANAGEMENT 8859 // ========================================================= 8860 8861 final ProcessRecord newProcessRecordLocked(ApplicationInfo info, String customProcess, 8862 boolean isolated) { 8863 String proc = customProcess != null ? customProcess : info.processName; 8864 BatteryStatsImpl.Uid.Proc ps = null; 8865 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 8866 int uid = info.uid; 8867 if (isolated) { 8868 int userId = UserHandle.getUserId(uid); 8869 int stepsLeft = Process.LAST_ISOLATED_UID - Process.FIRST_ISOLATED_UID + 1; 8870 while (true) { 8871 if (mNextIsolatedProcessUid < Process.FIRST_ISOLATED_UID 8872 || mNextIsolatedProcessUid > Process.LAST_ISOLATED_UID) { 8873 mNextIsolatedProcessUid = Process.FIRST_ISOLATED_UID; 8874 } 8875 uid = UserHandle.getUid(userId, mNextIsolatedProcessUid); 8876 mNextIsolatedProcessUid++; 8877 if (mIsolatedProcesses.indexOfKey(uid) < 0) { 8878 // No process for this uid, use it. 8879 break; 8880 } 8881 stepsLeft--; 8882 if (stepsLeft <= 0) { 8883 return null; 8884 } 8885 } 8886 } 8887 return new ProcessRecord(stats, info, proc, uid); 8888 } 8889 8890 final ProcessRecord addAppLocked(ApplicationInfo info, boolean isolated, 8891 String abiOverride) { 8892 ProcessRecord app; 8893 if (!isolated) { 8894 app = getProcessRecordLocked(info.processName, info.uid, true); 8895 } else { 8896 app = null; 8897 } 8898 8899 if (app == null) { 8900 app = newProcessRecordLocked(info, null, isolated); 8901 mProcessNames.put(info.processName, app.uid, app); 8902 if (isolated) { 8903 mIsolatedProcesses.put(app.uid, app); 8904 } 8905 updateLruProcessLocked(app, false, null); 8906 updateOomAdjLocked(); 8907 } 8908 8909 // This package really, really can not be stopped. 8910 try { 8911 AppGlobals.getPackageManager().setPackageStoppedState( 8912 info.packageName, false, UserHandle.getUserId(app.uid)); 8913 } catch (RemoteException e) { 8914 } catch (IllegalArgumentException e) { 8915 Slog.w(TAG, "Failed trying to unstop package " 8916 + info.packageName + ": " + e); 8917 } 8918 8919 if ((info.flags&(ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) 8920 == (ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) { 8921 app.persistent = true; 8922 app.maxAdj = ProcessList.PERSISTENT_PROC_ADJ; 8923 } 8924 if (app.thread == null && mPersistentStartingProcesses.indexOf(app) < 0) { 8925 mPersistentStartingProcesses.add(app); 8926 startProcessLocked(app, "added application", app.processName, 8927 abiOverride); 8928 } 8929 8930 return app; 8931 } 8932 8933 public void unhandledBack() { 8934 enforceCallingPermission(android.Manifest.permission.FORCE_BACK, 8935 "unhandledBack()"); 8936 8937 synchronized(this) { 8938 final long origId = Binder.clearCallingIdentity(); 8939 try { 8940 getFocusedStack().unhandledBackLocked(); 8941 } finally { 8942 Binder.restoreCallingIdentity(origId); 8943 } 8944 } 8945 } 8946 8947 public ParcelFileDescriptor openContentUri(Uri uri) throws RemoteException { 8948 enforceNotIsolatedCaller("openContentUri"); 8949 final int userId = UserHandle.getCallingUserId(); 8950 String name = uri.getAuthority(); 8951 ContentProviderHolder cph = getContentProviderExternalUnchecked(name, null, userId); 8952 ParcelFileDescriptor pfd = null; 8953 if (cph != null) { 8954 // We record the binder invoker's uid in thread-local storage before 8955 // going to the content provider to open the file. Later, in the code 8956 // that handles all permissions checks, we look for this uid and use 8957 // that rather than the Activity Manager's own uid. The effect is that 8958 // we do the check against the caller's permissions even though it looks 8959 // to the content provider like the Activity Manager itself is making 8960 // the request. 8961 sCallerIdentity.set(new Identity( 8962 Binder.getCallingPid(), Binder.getCallingUid())); 8963 try { 8964 pfd = cph.provider.openFile(null, uri, "r", null); 8965 } catch (FileNotFoundException e) { 8966 // do nothing; pfd will be returned null 8967 } finally { 8968 // Ensure that whatever happens, we clean up the identity state 8969 sCallerIdentity.remove(); 8970 } 8971 8972 // We've got the fd now, so we're done with the provider. 8973 removeContentProviderExternalUnchecked(name, null, userId); 8974 } else { 8975 Slog.d(TAG, "Failed to get provider for authority '" + name + "'"); 8976 } 8977 return pfd; 8978 } 8979 8980 // Actually is sleeping or shutting down or whatever else in the future 8981 // is an inactive state. 8982 public boolean isSleepingOrShuttingDown() { 8983 return mSleeping || mShuttingDown; 8984 } 8985 8986 public boolean isSleeping() { 8987 return mSleeping; 8988 } 8989 8990 void goingToSleep() { 8991 synchronized(this) { 8992 mWentToSleep = true; 8993 updateEventDispatchingLocked(); 8994 goToSleepIfNeededLocked(); 8995 } 8996 } 8997 8998 void finishRunningVoiceLocked() { 8999 if (mRunningVoice) { 9000 mRunningVoice = false; 9001 goToSleepIfNeededLocked(); 9002 } 9003 } 9004 9005 void goToSleepIfNeededLocked() { 9006 if (mWentToSleep && !mRunningVoice) { 9007 if (!mSleeping) { 9008 mSleeping = true; 9009 mStackSupervisor.goingToSleepLocked(); 9010 9011 // Initialize the wake times of all processes. 9012 checkExcessivePowerUsageLocked(false); 9013 mHandler.removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 9014 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 9015 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 9016 } 9017 } 9018 } 9019 9020 void notifyTaskPersisterLocked(TaskRecord task, boolean flush) { 9021 mTaskPersister.notify(task, flush); 9022 } 9023 9024 @Override 9025 public boolean shutdown(int timeout) { 9026 if (checkCallingPermission(android.Manifest.permission.SHUTDOWN) 9027 != PackageManager.PERMISSION_GRANTED) { 9028 throw new SecurityException("Requires permission " 9029 + android.Manifest.permission.SHUTDOWN); 9030 } 9031 9032 boolean timedout = false; 9033 9034 synchronized(this) { 9035 mShuttingDown = true; 9036 updateEventDispatchingLocked(); 9037 timedout = mStackSupervisor.shutdownLocked(timeout); 9038 } 9039 9040 mAppOpsService.shutdown(); 9041 mUsageStatsService.shutdown(); 9042 mBatteryStatsService.shutdown(); 9043 synchronized (this) { 9044 mProcessStats.shutdownLocked(); 9045 } 9046 notifyTaskPersisterLocked(null, true); 9047 9048 return timedout; 9049 } 9050 9051 public final void activitySlept(IBinder token) { 9052 if (localLOGV) Slog.v(TAG, "Activity slept: token=" + token); 9053 9054 final long origId = Binder.clearCallingIdentity(); 9055 9056 synchronized (this) { 9057 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9058 if (r != null) { 9059 mStackSupervisor.activitySleptLocked(r); 9060 } 9061 } 9062 9063 Binder.restoreCallingIdentity(origId); 9064 } 9065 9066 void logLockScreen(String msg) { 9067 if (DEBUG_LOCKSCREEN) Slog.d(TAG, Debug.getCallers(2) + ":" + msg + 9068 " mLockScreenShown=" + mLockScreenShown + " mWentToSleep=" + 9069 mWentToSleep + " mSleeping=" + mSleeping + " mDismissKeyguardOnNextActivity=" + 9070 mStackSupervisor.mDismissKeyguardOnNextActivity); 9071 } 9072 9073 private void comeOutOfSleepIfNeededLocked() { 9074 if ((!mWentToSleep && !mLockScreenShown) || mRunningVoice) { 9075 if (mSleeping) { 9076 mSleeping = false; 9077 mStackSupervisor.comeOutOfSleepIfNeededLocked(); 9078 } 9079 } 9080 } 9081 9082 void wakingUp() { 9083 synchronized(this) { 9084 mWentToSleep = false; 9085 updateEventDispatchingLocked(); 9086 comeOutOfSleepIfNeededLocked(); 9087 } 9088 } 9089 9090 void startRunningVoiceLocked() { 9091 if (!mRunningVoice) { 9092 mRunningVoice = true; 9093 comeOutOfSleepIfNeededLocked(); 9094 } 9095 } 9096 9097 private void updateEventDispatchingLocked() { 9098 mWindowManager.setEventDispatching(mBooted && !mWentToSleep && !mShuttingDown); 9099 } 9100 9101 public void setLockScreenShown(boolean shown) { 9102 if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER) 9103 != PackageManager.PERMISSION_GRANTED) { 9104 throw new SecurityException("Requires permission " 9105 + android.Manifest.permission.DEVICE_POWER); 9106 } 9107 9108 synchronized(this) { 9109 long ident = Binder.clearCallingIdentity(); 9110 try { 9111 if (DEBUG_LOCKSCREEN) logLockScreen(" shown=" + shown); 9112 mLockScreenShown = shown; 9113 comeOutOfSleepIfNeededLocked(); 9114 } finally { 9115 Binder.restoreCallingIdentity(ident); 9116 } 9117 } 9118 } 9119 9120 public void stopAppSwitches() { 9121 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 9122 != PackageManager.PERMISSION_GRANTED) { 9123 throw new SecurityException("Requires permission " 9124 + android.Manifest.permission.STOP_APP_SWITCHES); 9125 } 9126 9127 synchronized(this) { 9128 mAppSwitchesAllowedTime = SystemClock.uptimeMillis() 9129 + APP_SWITCH_DELAY_TIME; 9130 mDidAppSwitch = false; 9131 mHandler.removeMessages(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 9132 Message msg = mHandler.obtainMessage(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 9133 mHandler.sendMessageDelayed(msg, APP_SWITCH_DELAY_TIME); 9134 } 9135 } 9136 9137 public void resumeAppSwitches() { 9138 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 9139 != PackageManager.PERMISSION_GRANTED) { 9140 throw new SecurityException("Requires permission " 9141 + android.Manifest.permission.STOP_APP_SWITCHES); 9142 } 9143 9144 synchronized(this) { 9145 // Note that we don't execute any pending app switches... we will 9146 // let those wait until either the timeout, or the next start 9147 // activity request. 9148 mAppSwitchesAllowedTime = 0; 9149 } 9150 } 9151 9152 boolean checkAppSwitchAllowedLocked(int callingPid, int callingUid, 9153 String name) { 9154 if (mAppSwitchesAllowedTime < SystemClock.uptimeMillis()) { 9155 return true; 9156 } 9157 9158 final int perm = checkComponentPermission( 9159 android.Manifest.permission.STOP_APP_SWITCHES, callingPid, 9160 callingUid, -1, true); 9161 if (perm == PackageManager.PERMISSION_GRANTED) { 9162 return true; 9163 } 9164 9165 Slog.w(TAG, name + " request from " + callingUid + " stopped"); 9166 return false; 9167 } 9168 9169 public void setDebugApp(String packageName, boolean waitForDebugger, 9170 boolean persistent) { 9171 enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP, 9172 "setDebugApp()"); 9173 9174 long ident = Binder.clearCallingIdentity(); 9175 try { 9176 // Note that this is not really thread safe if there are multiple 9177 // callers into it at the same time, but that's not a situation we 9178 // care about. 9179 if (persistent) { 9180 final ContentResolver resolver = mContext.getContentResolver(); 9181 Settings.Global.putString( 9182 resolver, Settings.Global.DEBUG_APP, 9183 packageName); 9184 Settings.Global.putInt( 9185 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 9186 waitForDebugger ? 1 : 0); 9187 } 9188 9189 synchronized (this) { 9190 if (!persistent) { 9191 mOrigDebugApp = mDebugApp; 9192 mOrigWaitForDebugger = mWaitForDebugger; 9193 } 9194 mDebugApp = packageName; 9195 mWaitForDebugger = waitForDebugger; 9196 mDebugTransient = !persistent; 9197 if (packageName != null) { 9198 forceStopPackageLocked(packageName, -1, false, false, true, true, 9199 false, UserHandle.USER_ALL, "set debug app"); 9200 } 9201 } 9202 } finally { 9203 Binder.restoreCallingIdentity(ident); 9204 } 9205 } 9206 9207 void setOpenGlTraceApp(ApplicationInfo app, String processName) { 9208 synchronized (this) { 9209 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 9210 if (!isDebuggable) { 9211 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 9212 throw new SecurityException("Process not debuggable: " + app.packageName); 9213 } 9214 } 9215 9216 mOpenGlTraceApp = processName; 9217 } 9218 } 9219 9220 void setProfileApp(ApplicationInfo app, String processName, String profileFile, 9221 ParcelFileDescriptor profileFd, boolean autoStopProfiler) { 9222 synchronized (this) { 9223 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 9224 if (!isDebuggable) { 9225 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 9226 throw new SecurityException("Process not debuggable: " + app.packageName); 9227 } 9228 } 9229 mProfileApp = processName; 9230 mProfileFile = profileFile; 9231 if (mProfileFd != null) { 9232 try { 9233 mProfileFd.close(); 9234 } catch (IOException e) { 9235 } 9236 mProfileFd = null; 9237 } 9238 mProfileFd = profileFd; 9239 mProfileType = 0; 9240 mAutoStopProfiler = autoStopProfiler; 9241 } 9242 } 9243 9244 @Override 9245 public void setAlwaysFinish(boolean enabled) { 9246 enforceCallingPermission(android.Manifest.permission.SET_ALWAYS_FINISH, 9247 "setAlwaysFinish()"); 9248 9249 Settings.Global.putInt( 9250 mContext.getContentResolver(), 9251 Settings.Global.ALWAYS_FINISH_ACTIVITIES, enabled ? 1 : 0); 9252 9253 synchronized (this) { 9254 mAlwaysFinishActivities = enabled; 9255 } 9256 } 9257 9258 @Override 9259 public void setActivityController(IActivityController controller) { 9260 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 9261 "setActivityController()"); 9262 synchronized (this) { 9263 mController = controller; 9264 Watchdog.getInstance().setActivityController(controller); 9265 } 9266 } 9267 9268 @Override 9269 public void setUserIsMonkey(boolean userIsMonkey) { 9270 synchronized (this) { 9271 synchronized (mPidsSelfLocked) { 9272 final int callingPid = Binder.getCallingPid(); 9273 ProcessRecord precessRecord = mPidsSelfLocked.get(callingPid); 9274 if (precessRecord == null) { 9275 throw new SecurityException("Unknown process: " + callingPid); 9276 } 9277 if (precessRecord.instrumentationUiAutomationConnection == null) { 9278 throw new SecurityException("Only an instrumentation process " 9279 + "with a UiAutomation can call setUserIsMonkey"); 9280 } 9281 } 9282 mUserIsMonkey = userIsMonkey; 9283 } 9284 } 9285 9286 @Override 9287 public boolean isUserAMonkey() { 9288 synchronized (this) { 9289 // If there is a controller also implies the user is a monkey. 9290 return (mUserIsMonkey || mController != null); 9291 } 9292 } 9293 9294 public void requestBugReport() { 9295 enforceCallingPermission(android.Manifest.permission.DUMP, "requestBugReport"); 9296 SystemProperties.set("ctl.start", "bugreport"); 9297 } 9298 9299 public static long getInputDispatchingTimeoutLocked(ActivityRecord r) { 9300 return r != null ? getInputDispatchingTimeoutLocked(r.app) : KEY_DISPATCHING_TIMEOUT; 9301 } 9302 9303 public static long getInputDispatchingTimeoutLocked(ProcessRecord r) { 9304 if (r != null && (r.instrumentationClass != null || r.usingWrapper)) { 9305 return INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT; 9306 } 9307 return KEY_DISPATCHING_TIMEOUT; 9308 } 9309 9310 @Override 9311 public long inputDispatchingTimedOut(int pid, final boolean aboveSystem, String reason) { 9312 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 9313 != PackageManager.PERMISSION_GRANTED) { 9314 throw new SecurityException("Requires permission " 9315 + android.Manifest.permission.FILTER_EVENTS); 9316 } 9317 ProcessRecord proc; 9318 long timeout; 9319 synchronized (this) { 9320 synchronized (mPidsSelfLocked) { 9321 proc = mPidsSelfLocked.get(pid); 9322 } 9323 timeout = getInputDispatchingTimeoutLocked(proc); 9324 } 9325 9326 if (!inputDispatchingTimedOut(proc, null, null, aboveSystem, reason)) { 9327 return -1; 9328 } 9329 9330 return timeout; 9331 } 9332 9333 /** 9334 * Handle input dispatching timeouts. 9335 * Returns whether input dispatching should be aborted or not. 9336 */ 9337 public boolean inputDispatchingTimedOut(final ProcessRecord proc, 9338 final ActivityRecord activity, final ActivityRecord parent, 9339 final boolean aboveSystem, String reason) { 9340 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 9341 != PackageManager.PERMISSION_GRANTED) { 9342 throw new SecurityException("Requires permission " 9343 + android.Manifest.permission.FILTER_EVENTS); 9344 } 9345 9346 final String annotation; 9347 if (reason == null) { 9348 annotation = "Input dispatching timed out"; 9349 } else { 9350 annotation = "Input dispatching timed out (" + reason + ")"; 9351 } 9352 9353 if (proc != null) { 9354 synchronized (this) { 9355 if (proc.debugging) { 9356 return false; 9357 } 9358 9359 if (mDidDexOpt) { 9360 // Give more time since we were dexopting. 9361 mDidDexOpt = false; 9362 return false; 9363 } 9364 9365 if (proc.instrumentationClass != null) { 9366 Bundle info = new Bundle(); 9367 info.putString("shortMsg", "keyDispatchingTimedOut"); 9368 info.putString("longMsg", annotation); 9369 finishInstrumentationLocked(proc, Activity.RESULT_CANCELED, info); 9370 return true; 9371 } 9372 } 9373 mHandler.post(new Runnable() { 9374 @Override 9375 public void run() { 9376 appNotResponding(proc, activity, parent, aboveSystem, annotation); 9377 } 9378 }); 9379 } 9380 9381 return true; 9382 } 9383 9384 public Bundle getAssistContextExtras(int requestType) { 9385 enforceCallingPermission(android.Manifest.permission.GET_TOP_ACTIVITY_INFO, 9386 "getAssistContextExtras()"); 9387 PendingAssistExtras pae; 9388 Bundle extras = new Bundle(); 9389 synchronized (this) { 9390 ActivityRecord activity = getFocusedStack().mResumedActivity; 9391 if (activity == null) { 9392 Slog.w(TAG, "getAssistContextExtras failed: no resumed activity"); 9393 return null; 9394 } 9395 extras.putString(Intent.EXTRA_ASSIST_PACKAGE, activity.packageName); 9396 if (activity.app == null || activity.app.thread == null) { 9397 Slog.w(TAG, "getAssistContextExtras failed: no process for " + activity); 9398 return extras; 9399 } 9400 if (activity.app.pid == Binder.getCallingPid()) { 9401 Slog.w(TAG, "getAssistContextExtras failed: request process same as " + activity); 9402 return extras; 9403 } 9404 pae = new PendingAssistExtras(activity); 9405 try { 9406 activity.app.thread.requestAssistContextExtras(activity.appToken, pae, 9407 requestType); 9408 mPendingAssistExtras.add(pae); 9409 mHandler.postDelayed(pae, PENDING_ASSIST_EXTRAS_TIMEOUT); 9410 } catch (RemoteException e) { 9411 Slog.w(TAG, "getAssistContextExtras failed: crash calling " + activity); 9412 return extras; 9413 } 9414 } 9415 synchronized (pae) { 9416 while (!pae.haveResult) { 9417 try { 9418 pae.wait(); 9419 } catch (InterruptedException e) { 9420 } 9421 } 9422 if (pae.result != null) { 9423 extras.putBundle(Intent.EXTRA_ASSIST_CONTEXT, pae.result); 9424 } 9425 } 9426 synchronized (this) { 9427 mPendingAssistExtras.remove(pae); 9428 mHandler.removeCallbacks(pae); 9429 } 9430 return extras; 9431 } 9432 9433 public void reportAssistContextExtras(IBinder token, Bundle extras) { 9434 PendingAssistExtras pae = (PendingAssistExtras)token; 9435 synchronized (pae) { 9436 pae.result = extras; 9437 pae.haveResult = true; 9438 pae.notifyAll(); 9439 } 9440 } 9441 9442 public void registerProcessObserver(IProcessObserver observer) { 9443 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 9444 "registerProcessObserver()"); 9445 synchronized (this) { 9446 mProcessObservers.register(observer); 9447 } 9448 } 9449 9450 @Override 9451 public void unregisterProcessObserver(IProcessObserver observer) { 9452 synchronized (this) { 9453 mProcessObservers.unregister(observer); 9454 } 9455 } 9456 9457 @Override 9458 public boolean convertFromTranslucent(IBinder token) { 9459 final long origId = Binder.clearCallingIdentity(); 9460 try { 9461 synchronized (this) { 9462 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9463 if (r == null) { 9464 return false; 9465 } 9466 if (r.changeWindowTranslucency(true)) { 9467 mWindowManager.setAppFullscreen(token, true); 9468 r.task.stack.releaseMediaResources(); 9469 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9470 return true; 9471 } 9472 return false; 9473 } 9474 } finally { 9475 Binder.restoreCallingIdentity(origId); 9476 } 9477 } 9478 9479 @Override 9480 public boolean convertToTranslucent(IBinder token, ActivityOptions options) { 9481 final long origId = Binder.clearCallingIdentity(); 9482 try { 9483 synchronized (this) { 9484 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9485 if (r == null) { 9486 return false; 9487 } 9488 if (r.changeWindowTranslucency(false)) { 9489 r.task.stack.convertToTranslucent(r, options); 9490 mWindowManager.setAppFullscreen(token, false); 9491 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9492 return true; 9493 } else { 9494 r.task.stack.mReturningActivityOptions = options; 9495 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9496 return false; 9497 } 9498 } 9499 } finally { 9500 Binder.restoreCallingIdentity(origId); 9501 } 9502 } 9503 9504 @Override 9505 public boolean setMediaPlaying(IBinder token, boolean playing) { 9506 final long origId = Binder.clearCallingIdentity(); 9507 try { 9508 synchronized (this) { 9509 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9510 if (r != null) { 9511 return mStackSupervisor.setMediaPlayingLocked(r, playing); 9512 } 9513 } 9514 return false; 9515 } finally { 9516 Binder.restoreCallingIdentity(origId); 9517 } 9518 } 9519 9520 @Override 9521 public boolean isBackgroundMediaPlaying(IBinder token) { 9522 final long origId = Binder.clearCallingIdentity(); 9523 try { 9524 synchronized (this) { 9525 final ActivityStack stack = ActivityRecord.getStackLocked(token); 9526 final boolean playing = stack == null ? false : stack.isMediaPlaying(); 9527 if (ActivityStackSupervisor.DEBUG_MEDIA_VISIBILITY) Slog.d(TAG, 9528 "isBackgroundMediaPlaying: stack=" + stack + " playing=" + playing); 9529 return playing; 9530 } 9531 } finally { 9532 Binder.restoreCallingIdentity(origId); 9533 } 9534 } 9535 9536 @Override 9537 public ActivityOptions getActivityOptions(IBinder token) { 9538 final long origId = Binder.clearCallingIdentity(); 9539 try { 9540 synchronized (this) { 9541 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9542 if (r != null) { 9543 final ActivityOptions activityOptions = r.pendingOptions; 9544 r.pendingOptions = null; 9545 return activityOptions; 9546 } 9547 return null; 9548 } 9549 } finally { 9550 Binder.restoreCallingIdentity(origId); 9551 } 9552 } 9553 9554 @Override 9555 public void setImmersive(IBinder token, boolean immersive) { 9556 synchronized(this) { 9557 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9558 if (r == null) { 9559 throw new IllegalArgumentException(); 9560 } 9561 r.immersive = immersive; 9562 9563 // update associated state if we're frontmost 9564 if (r == mFocusedActivity) { 9565 if (DEBUG_IMMERSIVE) { 9566 Slog.d(TAG, "Frontmost changed immersion: "+ r); 9567 } 9568 applyUpdateLockStateLocked(r); 9569 } 9570 } 9571 } 9572 9573 @Override 9574 public boolean isImmersive(IBinder token) { 9575 synchronized (this) { 9576 ActivityRecord r = ActivityRecord.isInStackLocked(token); 9577 if (r == null) { 9578 throw new IllegalArgumentException(); 9579 } 9580 return r.immersive; 9581 } 9582 } 9583 9584 public boolean isTopActivityImmersive() { 9585 enforceNotIsolatedCaller("startActivity"); 9586 synchronized (this) { 9587 ActivityRecord r = getFocusedStack().topRunningActivityLocked(null); 9588 return (r != null) ? r.immersive : false; 9589 } 9590 } 9591 9592 @Override 9593 public boolean isTopOfTask(IBinder token) { 9594 synchronized (this) { 9595 ActivityRecord r = ActivityRecord.isInStackLocked(token); 9596 if (r == null) { 9597 throw new IllegalArgumentException(); 9598 } 9599 return r.task.getTopActivity() == r; 9600 } 9601 } 9602 9603 public final void enterSafeMode() { 9604 synchronized(this) { 9605 // It only makes sense to do this before the system is ready 9606 // and started launching other packages. 9607 if (!mSystemReady) { 9608 try { 9609 AppGlobals.getPackageManager().enterSafeMode(); 9610 } catch (RemoteException e) { 9611 } 9612 } 9613 9614 mSafeMode = true; 9615 } 9616 } 9617 9618 public final void showSafeModeOverlay() { 9619 View v = LayoutInflater.from(mContext).inflate( 9620 com.android.internal.R.layout.safe_mode, null); 9621 WindowManager.LayoutParams lp = new WindowManager.LayoutParams(); 9622 lp.type = WindowManager.LayoutParams.TYPE_SECURE_SYSTEM_OVERLAY; 9623 lp.width = WindowManager.LayoutParams.WRAP_CONTENT; 9624 lp.height = WindowManager.LayoutParams.WRAP_CONTENT; 9625 lp.gravity = Gravity.BOTTOM | Gravity.START; 9626 lp.format = v.getBackground().getOpacity(); 9627 lp.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE 9628 | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE; 9629 lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; 9630 ((WindowManager)mContext.getSystemService( 9631 Context.WINDOW_SERVICE)).addView(v, lp); 9632 } 9633 9634 public void noteWakeupAlarm(IIntentSender sender, int sourceUid, String sourcePkg) { 9635 if (!(sender instanceof PendingIntentRecord)) { 9636 return; 9637 } 9638 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 9639 synchronized (stats) { 9640 if (mBatteryStatsService.isOnBattery()) { 9641 mBatteryStatsService.enforceCallingPermission(); 9642 PendingIntentRecord rec = (PendingIntentRecord)sender; 9643 int MY_UID = Binder.getCallingUid(); 9644 int uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid; 9645 BatteryStatsImpl.Uid.Pkg pkg = 9646 stats.getPackageStatsLocked(sourceUid >= 0 ? sourceUid : uid, 9647 sourcePkg != null ? sourcePkg : rec.key.packageName); 9648 pkg.incWakeupsLocked(); 9649 } 9650 } 9651 } 9652 9653 public boolean killPids(int[] pids, String pReason, boolean secure) { 9654 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9655 throw new SecurityException("killPids only available to the system"); 9656 } 9657 String reason = (pReason == null) ? "Unknown" : pReason; 9658 // XXX Note: don't acquire main activity lock here, because the window 9659 // manager calls in with its locks held. 9660 9661 boolean killed = false; 9662 synchronized (mPidsSelfLocked) { 9663 int[] types = new int[pids.length]; 9664 int worstType = 0; 9665 for (int i=0; i<pids.length; i++) { 9666 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 9667 if (proc != null) { 9668 int type = proc.setAdj; 9669 types[i] = type; 9670 if (type > worstType) { 9671 worstType = type; 9672 } 9673 } 9674 } 9675 9676 // If the worst oom_adj is somewhere in the cached proc LRU range, 9677 // then constrain it so we will kill all cached procs. 9678 if (worstType < ProcessList.CACHED_APP_MAX_ADJ 9679 && worstType > ProcessList.CACHED_APP_MIN_ADJ) { 9680 worstType = ProcessList.CACHED_APP_MIN_ADJ; 9681 } 9682 9683 // If this is not a secure call, don't let it kill processes that 9684 // are important. 9685 if (!secure && worstType < ProcessList.SERVICE_ADJ) { 9686 worstType = ProcessList.SERVICE_ADJ; 9687 } 9688 9689 Slog.w(TAG, "Killing processes " + reason + " at adjustment " + worstType); 9690 for (int i=0; i<pids.length; i++) { 9691 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 9692 if (proc == null) { 9693 continue; 9694 } 9695 int adj = proc.setAdj; 9696 if (adj >= worstType && !proc.killedByAm) { 9697 killUnneededProcessLocked(proc, reason); 9698 killed = true; 9699 } 9700 } 9701 } 9702 return killed; 9703 } 9704 9705 @Override 9706 public void killUid(int uid, String reason) { 9707 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9708 throw new SecurityException("killUid only available to the system"); 9709 } 9710 synchronized (this) { 9711 killPackageProcessesLocked(null, UserHandle.getAppId(uid), UserHandle.getUserId(uid), 9712 ProcessList.FOREGROUND_APP_ADJ-1, false, true, true, false, 9713 reason != null ? reason : "kill uid"); 9714 } 9715 } 9716 9717 @Override 9718 public boolean killProcessesBelowForeground(String reason) { 9719 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9720 throw new SecurityException("killProcessesBelowForeground() only available to system"); 9721 } 9722 9723 return killProcessesBelowAdj(ProcessList.FOREGROUND_APP_ADJ, reason); 9724 } 9725 9726 private boolean killProcessesBelowAdj(int belowAdj, String reason) { 9727 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9728 throw new SecurityException("killProcessesBelowAdj() only available to system"); 9729 } 9730 9731 boolean killed = false; 9732 synchronized (mPidsSelfLocked) { 9733 final int size = mPidsSelfLocked.size(); 9734 for (int i = 0; i < size; i++) { 9735 final int pid = mPidsSelfLocked.keyAt(i); 9736 final ProcessRecord proc = mPidsSelfLocked.valueAt(i); 9737 if (proc == null) continue; 9738 9739 final int adj = proc.setAdj; 9740 if (adj > belowAdj && !proc.killedByAm) { 9741 killUnneededProcessLocked(proc, reason); 9742 killed = true; 9743 } 9744 } 9745 } 9746 return killed; 9747 } 9748 9749 @Override 9750 public void hang(final IBinder who, boolean allowRestart) { 9751 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9752 != PackageManager.PERMISSION_GRANTED) { 9753 throw new SecurityException("Requires permission " 9754 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9755 } 9756 9757 final IBinder.DeathRecipient death = new DeathRecipient() { 9758 @Override 9759 public void binderDied() { 9760 synchronized (this) { 9761 notifyAll(); 9762 } 9763 } 9764 }; 9765 9766 try { 9767 who.linkToDeath(death, 0); 9768 } catch (RemoteException e) { 9769 Slog.w(TAG, "hang: given caller IBinder is already dead."); 9770 return; 9771 } 9772 9773 synchronized (this) { 9774 Watchdog.getInstance().setAllowRestart(allowRestart); 9775 Slog.i(TAG, "Hanging system process at request of pid " + Binder.getCallingPid()); 9776 synchronized (death) { 9777 while (who.isBinderAlive()) { 9778 try { 9779 death.wait(); 9780 } catch (InterruptedException e) { 9781 } 9782 } 9783 } 9784 Watchdog.getInstance().setAllowRestart(true); 9785 } 9786 } 9787 9788 @Override 9789 public void restart() { 9790 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9791 != PackageManager.PERMISSION_GRANTED) { 9792 throw new SecurityException("Requires permission " 9793 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9794 } 9795 9796 Log.i(TAG, "Sending shutdown broadcast..."); 9797 9798 BroadcastReceiver br = new BroadcastReceiver() { 9799 @Override public void onReceive(Context context, Intent intent) { 9800 // Now the broadcast is done, finish up the low-level shutdown. 9801 Log.i(TAG, "Shutting down activity manager..."); 9802 shutdown(10000); 9803 Log.i(TAG, "Shutdown complete, restarting!"); 9804 Process.killProcess(Process.myPid()); 9805 System.exit(10); 9806 } 9807 }; 9808 9809 // First send the high-level shut down broadcast. 9810 Intent intent = new Intent(Intent.ACTION_SHUTDOWN); 9811 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 9812 intent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 9813 /* For now we are not doing a clean shutdown, because things seem to get unhappy. 9814 mContext.sendOrderedBroadcastAsUser(intent, 9815 UserHandle.ALL, null, br, mHandler, 0, null, null); 9816 */ 9817 br.onReceive(mContext, intent); 9818 } 9819 9820 private long getLowRamTimeSinceIdle(long now) { 9821 return mLowRamTimeSinceLastIdle + (mLowRamStartTime > 0 ? (now-mLowRamStartTime) : 0); 9822 } 9823 9824 @Override 9825 public void performIdleMaintenance() { 9826 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9827 != PackageManager.PERMISSION_GRANTED) { 9828 throw new SecurityException("Requires permission " 9829 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9830 } 9831 9832 synchronized (this) { 9833 final long now = SystemClock.uptimeMillis(); 9834 final long timeSinceLastIdle = now - mLastIdleTime; 9835 final long lowRamSinceLastIdle = getLowRamTimeSinceIdle(now); 9836 mLastIdleTime = now; 9837 mLowRamTimeSinceLastIdle = 0; 9838 if (mLowRamStartTime != 0) { 9839 mLowRamStartTime = now; 9840 } 9841 9842 StringBuilder sb = new StringBuilder(128); 9843 sb.append("Idle maintenance over "); 9844 TimeUtils.formatDuration(timeSinceLastIdle, sb); 9845 sb.append(" low RAM for "); 9846 TimeUtils.formatDuration(lowRamSinceLastIdle, sb); 9847 Slog.i(TAG, sb.toString()); 9848 9849 // If at least 1/3 of our time since the last idle period has been spent 9850 // with RAM low, then we want to kill processes. 9851 boolean doKilling = lowRamSinceLastIdle > (timeSinceLastIdle/3); 9852 9853 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 9854 ProcessRecord proc = mLruProcesses.get(i); 9855 if (proc.notCachedSinceIdle) { 9856 if (proc.setProcState > ActivityManager.PROCESS_STATE_TOP 9857 && proc.setProcState <= ActivityManager.PROCESS_STATE_SERVICE) { 9858 if (doKilling && proc.initialIdlePss != 0 9859 && proc.lastPss > ((proc.initialIdlePss*3)/2)) { 9860 killUnneededProcessLocked(proc, "idle maint (pss " + proc.lastPss 9861 + " from " + proc.initialIdlePss + ")"); 9862 } 9863 } 9864 } else if (proc.setProcState < ActivityManager.PROCESS_STATE_HOME) { 9865 proc.notCachedSinceIdle = true; 9866 proc.initialIdlePss = 0; 9867 proc.nextPssTime = ProcessList.computeNextPssTime(proc.curProcState, true, 9868 isSleeping(), now); 9869 } 9870 } 9871 9872 mHandler.removeMessages(REQUEST_ALL_PSS_MSG); 9873 mHandler.sendEmptyMessageDelayed(REQUEST_ALL_PSS_MSG, 2*60*1000); 9874 } 9875 } 9876 9877 private void retrieveSettings() { 9878 final ContentResolver resolver = mContext.getContentResolver(); 9879 String debugApp = Settings.Global.getString( 9880 resolver, Settings.Global.DEBUG_APP); 9881 boolean waitForDebugger = Settings.Global.getInt( 9882 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 0) != 0; 9883 boolean alwaysFinishActivities = Settings.Global.getInt( 9884 resolver, Settings.Global.ALWAYS_FINISH_ACTIVITIES, 0) != 0; 9885 boolean forceRtl = Settings.Global.getInt( 9886 resolver, Settings.Global.DEVELOPMENT_FORCE_RTL, 0) != 0; 9887 // Transfer any global setting for forcing RTL layout, into a System Property 9888 SystemProperties.set(Settings.Global.DEVELOPMENT_FORCE_RTL, forceRtl ? "1":"0"); 9889 9890 Configuration configuration = new Configuration(); 9891 Settings.System.getConfiguration(resolver, configuration); 9892 if (forceRtl) { 9893 // This will take care of setting the correct layout direction flags 9894 configuration.setLayoutDirection(configuration.locale); 9895 } 9896 9897 synchronized (this) { 9898 mDebugApp = mOrigDebugApp = debugApp; 9899 mWaitForDebugger = mOrigWaitForDebugger = waitForDebugger; 9900 mAlwaysFinishActivities = alwaysFinishActivities; 9901 // This happens before any activities are started, so we can 9902 // change mConfiguration in-place. 9903 updateConfigurationLocked(configuration, null, false, true); 9904 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Initial config: " + mConfiguration); 9905 } 9906 } 9907 9908 public boolean testIsSystemReady() { 9909 // no need to synchronize(this) just to read & return the value 9910 return mSystemReady; 9911 } 9912 9913 private static File getCalledPreBootReceiversFile() { 9914 File dataDir = Environment.getDataDirectory(); 9915 File systemDir = new File(dataDir, "system"); 9916 File fname = new File(systemDir, "called_pre_boots.dat"); 9917 return fname; 9918 } 9919 9920 static final int LAST_DONE_VERSION = 10000; 9921 9922 private static ArrayList<ComponentName> readLastDonePreBootReceivers() { 9923 ArrayList<ComponentName> lastDoneReceivers = new ArrayList<ComponentName>(); 9924 File file = getCalledPreBootReceiversFile(); 9925 FileInputStream fis = null; 9926 try { 9927 fis = new FileInputStream(file); 9928 DataInputStream dis = new DataInputStream(new BufferedInputStream(fis, 2048)); 9929 int fvers = dis.readInt(); 9930 if (fvers == LAST_DONE_VERSION) { 9931 String vers = dis.readUTF(); 9932 String codename = dis.readUTF(); 9933 String build = dis.readUTF(); 9934 if (android.os.Build.VERSION.RELEASE.equals(vers) 9935 && android.os.Build.VERSION.CODENAME.equals(codename) 9936 && android.os.Build.VERSION.INCREMENTAL.equals(build)) { 9937 int num = dis.readInt(); 9938 while (num > 0) { 9939 num--; 9940 String pkg = dis.readUTF(); 9941 String cls = dis.readUTF(); 9942 lastDoneReceivers.add(new ComponentName(pkg, cls)); 9943 } 9944 } 9945 } 9946 } catch (FileNotFoundException e) { 9947 } catch (IOException e) { 9948 Slog.w(TAG, "Failure reading last done pre-boot receivers", e); 9949 } finally { 9950 if (fis != null) { 9951 try { 9952 fis.close(); 9953 } catch (IOException e) { 9954 } 9955 } 9956 } 9957 return lastDoneReceivers; 9958 } 9959 9960 private static void writeLastDonePreBootReceivers(ArrayList<ComponentName> list) { 9961 File file = getCalledPreBootReceiversFile(); 9962 FileOutputStream fos = null; 9963 DataOutputStream dos = null; 9964 try { 9965 Slog.i(TAG, "Writing new set of last done pre-boot receivers..."); 9966 fos = new FileOutputStream(file); 9967 dos = new DataOutputStream(new BufferedOutputStream(fos, 2048)); 9968 dos.writeInt(LAST_DONE_VERSION); 9969 dos.writeUTF(android.os.Build.VERSION.RELEASE); 9970 dos.writeUTF(android.os.Build.VERSION.CODENAME); 9971 dos.writeUTF(android.os.Build.VERSION.INCREMENTAL); 9972 dos.writeInt(list.size()); 9973 for (int i=0; i<list.size(); i++) { 9974 dos.writeUTF(list.get(i).getPackageName()); 9975 dos.writeUTF(list.get(i).getClassName()); 9976 } 9977 } catch (IOException e) { 9978 Slog.w(TAG, "Failure writing last done pre-boot receivers", e); 9979 file.delete(); 9980 } finally { 9981 FileUtils.sync(fos); 9982 if (dos != null) { 9983 try { 9984 dos.close(); 9985 } catch (IOException e) { 9986 // TODO Auto-generated catch block 9987 e.printStackTrace(); 9988 } 9989 } 9990 } 9991 } 9992 9993 public void systemReady(final Runnable goingCallback) { 9994 synchronized(this) { 9995 if (mSystemReady) { 9996 if (goingCallback != null) goingCallback.run(); 9997 return; 9998 } 9999 10000 // Make sure we have the current profile info, since it is needed for 10001 // security checks. 10002 updateCurrentProfileIdsLocked(); 10003 10004 if (mRecentTasks == null) { 10005 mRecentTasks = mTaskPersister.restoreTasksLocked(); 10006 if (!mRecentTasks.isEmpty()) { 10007 mStackSupervisor.createStackForRestoredTaskHistory(mRecentTasks); 10008 } 10009 mTaskPersister.startPersisting(); 10010 } 10011 10012 // Check to see if there are any update receivers to run. 10013 if (!mDidUpdate) { 10014 if (mWaitingUpdate) { 10015 return; 10016 } 10017 Intent intent = new Intent(Intent.ACTION_PRE_BOOT_COMPLETED); 10018 List<ResolveInfo> ris = null; 10019 try { 10020 ris = AppGlobals.getPackageManager().queryIntentReceivers( 10021 intent, null, 0, 0); 10022 } catch (RemoteException e) { 10023 } 10024 if (ris != null) { 10025 for (int i=ris.size()-1; i>=0; i--) { 10026 if ((ris.get(i).activityInfo.applicationInfo.flags 10027 &ApplicationInfo.FLAG_SYSTEM) == 0) { 10028 ris.remove(i); 10029 } 10030 } 10031 intent.addFlags(Intent.FLAG_RECEIVER_BOOT_UPGRADE); 10032 10033 ArrayList<ComponentName> lastDoneReceivers = readLastDonePreBootReceivers(); 10034 10035 final ArrayList<ComponentName> doneReceivers = new ArrayList<ComponentName>(); 10036 for (int i=0; i<ris.size(); i++) { 10037 ActivityInfo ai = ris.get(i).activityInfo; 10038 ComponentName comp = new ComponentName(ai.packageName, ai.name); 10039 if (lastDoneReceivers.contains(comp)) { 10040 // We already did the pre boot receiver for this app with the current 10041 // platform version, so don't do it again... 10042 ris.remove(i); 10043 i--; 10044 // ...however, do keep it as one that has been done, so we don't 10045 // forget about it when rewriting the file of last done receivers. 10046 doneReceivers.add(comp); 10047 } 10048 } 10049 10050 final int[] users = getUsersLocked(); 10051 for (int i=0; i<ris.size(); i++) { 10052 ActivityInfo ai = ris.get(i).activityInfo; 10053 ComponentName comp = new ComponentName(ai.packageName, ai.name); 10054 doneReceivers.add(comp); 10055 intent.setComponent(comp); 10056 for (int j=0; j<users.length; j++) { 10057 IIntentReceiver finisher = null; 10058 if (i == ris.size()-1 && j == users.length-1) { 10059 finisher = new IIntentReceiver.Stub() { 10060 public void performReceive(Intent intent, int resultCode, 10061 String data, Bundle extras, boolean ordered, 10062 boolean sticky, int sendingUser) { 10063 // The raw IIntentReceiver interface is called 10064 // with the AM lock held, so redispatch to 10065 // execute our code without the lock. 10066 mHandler.post(new Runnable() { 10067 public void run() { 10068 synchronized (ActivityManagerService.this) { 10069 mDidUpdate = true; 10070 } 10071 writeLastDonePreBootReceivers(doneReceivers); 10072 showBootMessage(mContext.getText( 10073 R.string.android_upgrading_complete), 10074 false); 10075 systemReady(goingCallback); 10076 } 10077 }); 10078 } 10079 }; 10080 } 10081 Slog.i(TAG, "Sending system update to " + intent.getComponent() 10082 + " for user " + users[j]); 10083 broadcastIntentLocked(null, null, intent, null, finisher, 10084 0, null, null, null, AppOpsManager.OP_NONE, 10085 true, false, MY_PID, Process.SYSTEM_UID, 10086 users[j]); 10087 if (finisher != null) { 10088 mWaitingUpdate = true; 10089 } 10090 } 10091 } 10092 } 10093 if (mWaitingUpdate) { 10094 return; 10095 } 10096 mDidUpdate = true; 10097 } 10098 10099 mAppOpsService.systemReady(); 10100 mUsageStatsService.systemReady(); 10101 mSystemReady = true; 10102 } 10103 10104 ArrayList<ProcessRecord> procsToKill = null; 10105 synchronized(mPidsSelfLocked) { 10106 for (int i=mPidsSelfLocked.size()-1; i>=0; i--) { 10107 ProcessRecord proc = mPidsSelfLocked.valueAt(i); 10108 if (!isAllowedWhileBooting(proc.info)){ 10109 if (procsToKill == null) { 10110 procsToKill = new ArrayList<ProcessRecord>(); 10111 } 10112 procsToKill.add(proc); 10113 } 10114 } 10115 } 10116 10117 synchronized(this) { 10118 if (procsToKill != null) { 10119 for (int i=procsToKill.size()-1; i>=0; i--) { 10120 ProcessRecord proc = procsToKill.get(i); 10121 Slog.i(TAG, "Removing system update proc: " + proc); 10122 removeProcessLocked(proc, true, false, "system update done"); 10123 } 10124 } 10125 10126 // Now that we have cleaned up any update processes, we 10127 // are ready to start launching real processes and know that 10128 // we won't trample on them any more. 10129 mProcessesReady = true; 10130 } 10131 10132 Slog.i(TAG, "System now ready"); 10133 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_AMS_READY, 10134 SystemClock.uptimeMillis()); 10135 10136 synchronized(this) { 10137 // Make sure we have no pre-ready processes sitting around. 10138 10139 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) { 10140 ResolveInfo ri = mContext.getPackageManager() 10141 .resolveActivity(new Intent(Intent.ACTION_FACTORY_TEST), 10142 STOCK_PM_FLAGS); 10143 CharSequence errorMsg = null; 10144 if (ri != null) { 10145 ActivityInfo ai = ri.activityInfo; 10146 ApplicationInfo app = ai.applicationInfo; 10147 if ((app.flags&ApplicationInfo.FLAG_SYSTEM) != 0) { 10148 mTopAction = Intent.ACTION_FACTORY_TEST; 10149 mTopData = null; 10150 mTopComponent = new ComponentName(app.packageName, 10151 ai.name); 10152 } else { 10153 errorMsg = mContext.getResources().getText( 10154 com.android.internal.R.string.factorytest_not_system); 10155 } 10156 } else { 10157 errorMsg = mContext.getResources().getText( 10158 com.android.internal.R.string.factorytest_no_action); 10159 } 10160 if (errorMsg != null) { 10161 mTopAction = null; 10162 mTopData = null; 10163 mTopComponent = null; 10164 Message msg = Message.obtain(); 10165 msg.what = SHOW_FACTORY_ERROR_MSG; 10166 msg.getData().putCharSequence("msg", errorMsg); 10167 mHandler.sendMessage(msg); 10168 } 10169 } 10170 } 10171 10172 retrieveSettings(); 10173 10174 synchronized (this) { 10175 readGrantedUriPermissionsLocked(); 10176 } 10177 10178 if (goingCallback != null) goingCallback.run(); 10179 10180 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 10181 Integer.toString(mCurrentUserId), mCurrentUserId); 10182 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 10183 Integer.toString(mCurrentUserId), mCurrentUserId); 10184 mSystemServiceManager.startUser(mCurrentUserId); 10185 10186 synchronized (this) { 10187 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 10188 try { 10189 List apps = AppGlobals.getPackageManager(). 10190 getPersistentApplications(STOCK_PM_FLAGS); 10191 if (apps != null) { 10192 int N = apps.size(); 10193 int i; 10194 for (i=0; i<N; i++) { 10195 ApplicationInfo info 10196 = (ApplicationInfo)apps.get(i); 10197 if (info != null && 10198 !info.packageName.equals("android")) { 10199 addAppLocked(info, false, null /* ABI override */); 10200 } 10201 } 10202 } 10203 } catch (RemoteException ex) { 10204 // pm is in same process, this will never happen. 10205 } 10206 } 10207 10208 // Start up initial activity. 10209 mBooting = true; 10210 10211 try { 10212 if (AppGlobals.getPackageManager().hasSystemUidErrors()) { 10213 Message msg = Message.obtain(); 10214 msg.what = SHOW_UID_ERROR_MSG; 10215 mHandler.sendMessage(msg); 10216 } 10217 } catch (RemoteException e) { 10218 } 10219 10220 long ident = Binder.clearCallingIdentity(); 10221 try { 10222 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 10223 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 10224 | Intent.FLAG_RECEIVER_FOREGROUND); 10225 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 10226 broadcastIntentLocked(null, null, intent, 10227 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 10228 false, false, MY_PID, Process.SYSTEM_UID, mCurrentUserId); 10229 intent = new Intent(Intent.ACTION_USER_STARTING); 10230 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 10231 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 10232 broadcastIntentLocked(null, null, intent, 10233 null, new IIntentReceiver.Stub() { 10234 @Override 10235 public void performReceive(Intent intent, int resultCode, String data, 10236 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 10237 throws RemoteException { 10238 } 10239 }, 0, null, null, 10240 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 10241 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 10242 } catch (Throwable t) { 10243 Slog.wtf(TAG, "Failed sending first user broadcasts", t); 10244 } finally { 10245 Binder.restoreCallingIdentity(ident); 10246 } 10247 mStackSupervisor.resumeTopActivitiesLocked(); 10248 sendUserSwitchBroadcastsLocked(-1, mCurrentUserId); 10249 } 10250 } 10251 10252 private boolean makeAppCrashingLocked(ProcessRecord app, 10253 String shortMsg, String longMsg, String stackTrace) { 10254 app.crashing = true; 10255 app.crashingReport = generateProcessError(app, 10256 ActivityManager.ProcessErrorStateInfo.CRASHED, null, shortMsg, longMsg, stackTrace); 10257 startAppProblemLocked(app); 10258 app.stopFreezingAllLocked(); 10259 return handleAppCrashLocked(app, shortMsg, longMsg, stackTrace); 10260 } 10261 10262 private void makeAppNotRespondingLocked(ProcessRecord app, 10263 String activity, String shortMsg, String longMsg) { 10264 app.notResponding = true; 10265 app.notRespondingReport = generateProcessError(app, 10266 ActivityManager.ProcessErrorStateInfo.NOT_RESPONDING, 10267 activity, shortMsg, longMsg, null); 10268 startAppProblemLocked(app); 10269 app.stopFreezingAllLocked(); 10270 } 10271 10272 /** 10273 * Generate a process error record, suitable for attachment to a ProcessRecord. 10274 * 10275 * @param app The ProcessRecord in which the error occurred. 10276 * @param condition Crashing, Application Not Responding, etc. Values are defined in 10277 * ActivityManager.AppErrorStateInfo 10278 * @param activity The activity associated with the crash, if known. 10279 * @param shortMsg Short message describing the crash. 10280 * @param longMsg Long message describing the crash. 10281 * @param stackTrace Full crash stack trace, may be null. 10282 * 10283 * @return Returns a fully-formed AppErrorStateInfo record. 10284 */ 10285 private ActivityManager.ProcessErrorStateInfo generateProcessError(ProcessRecord app, 10286 int condition, String activity, String shortMsg, String longMsg, String stackTrace) { 10287 ActivityManager.ProcessErrorStateInfo report = new ActivityManager.ProcessErrorStateInfo(); 10288 10289 report.condition = condition; 10290 report.processName = app.processName; 10291 report.pid = app.pid; 10292 report.uid = app.info.uid; 10293 report.tag = activity; 10294 report.shortMsg = shortMsg; 10295 report.longMsg = longMsg; 10296 report.stackTrace = stackTrace; 10297 10298 return report; 10299 } 10300 10301 void killAppAtUsersRequest(ProcessRecord app, Dialog fromDialog) { 10302 synchronized (this) { 10303 app.crashing = false; 10304 app.crashingReport = null; 10305 app.notResponding = false; 10306 app.notRespondingReport = null; 10307 if (app.anrDialog == fromDialog) { 10308 app.anrDialog = null; 10309 } 10310 if (app.waitDialog == fromDialog) { 10311 app.waitDialog = null; 10312 } 10313 if (app.pid > 0 && app.pid != MY_PID) { 10314 handleAppCrashLocked(app, null, null, null); 10315 killUnneededProcessLocked(app, "user request after error"); 10316 } 10317 } 10318 } 10319 10320 private boolean handleAppCrashLocked(ProcessRecord app, String shortMsg, String longMsg, 10321 String stackTrace) { 10322 long now = SystemClock.uptimeMillis(); 10323 10324 Long crashTime; 10325 if (!app.isolated) { 10326 crashTime = mProcessCrashTimes.get(app.info.processName, app.uid); 10327 } else { 10328 crashTime = null; 10329 } 10330 if (crashTime != null && now < crashTime+ProcessList.MIN_CRASH_INTERVAL) { 10331 // This process loses! 10332 Slog.w(TAG, "Process " + app.info.processName 10333 + " has crashed too many times: killing!"); 10334 EventLog.writeEvent(EventLogTags.AM_PROCESS_CRASHED_TOO_MUCH, 10335 app.userId, app.info.processName, app.uid); 10336 mStackSupervisor.handleAppCrashLocked(app); 10337 if (!app.persistent) { 10338 // We don't want to start this process again until the user 10339 // explicitly does so... but for persistent process, we really 10340 // need to keep it running. If a persistent process is actually 10341 // repeatedly crashing, then badness for everyone. 10342 EventLog.writeEvent(EventLogTags.AM_PROC_BAD, app.userId, app.uid, 10343 app.info.processName); 10344 if (!app.isolated) { 10345 // XXX We don't have a way to mark isolated processes 10346 // as bad, since they don't have a peristent identity. 10347 mBadProcesses.put(app.info.processName, app.uid, 10348 new BadProcessInfo(now, shortMsg, longMsg, stackTrace)); 10349 mProcessCrashTimes.remove(app.info.processName, app.uid); 10350 } 10351 app.bad = true; 10352 app.removed = true; 10353 // Don't let services in this process be restarted and potentially 10354 // annoy the user repeatedly. Unless it is persistent, since those 10355 // processes run critical code. 10356 removeProcessLocked(app, false, false, "crash"); 10357 mStackSupervisor.resumeTopActivitiesLocked(); 10358 return false; 10359 } 10360 mStackSupervisor.resumeTopActivitiesLocked(); 10361 } else { 10362 mStackSupervisor.finishTopRunningActivityLocked(app); 10363 } 10364 10365 // Bump up the crash count of any services currently running in the proc. 10366 for (int i=app.services.size()-1; i>=0; i--) { 10367 // Any services running in the application need to be placed 10368 // back in the pending list. 10369 ServiceRecord sr = app.services.valueAt(i); 10370 sr.crashCount++; 10371 } 10372 10373 // If the crashing process is what we consider to be the "home process" and it has been 10374 // replaced by a third-party app, clear the package preferred activities from packages 10375 // with a home activity running in the process to prevent a repeatedly crashing app 10376 // from blocking the user to manually clear the list. 10377 final ArrayList<ActivityRecord> activities = app.activities; 10378 if (app == mHomeProcess && activities.size() > 0 10379 && (mHomeProcess.info.flags & ApplicationInfo.FLAG_SYSTEM) == 0) { 10380 for (int activityNdx = activities.size() - 1; activityNdx >= 0; --activityNdx) { 10381 final ActivityRecord r = activities.get(activityNdx); 10382 if (r.isHomeActivity()) { 10383 Log.i(TAG, "Clearing package preferred activities from " + r.packageName); 10384 try { 10385 ActivityThread.getPackageManager() 10386 .clearPackagePreferredActivities(r.packageName); 10387 } catch (RemoteException c) { 10388 // pm is in same process, this will never happen. 10389 } 10390 } 10391 } 10392 } 10393 10394 if (!app.isolated) { 10395 // XXX Can't keep track of crash times for isolated processes, 10396 // because they don't have a perisistent identity. 10397 mProcessCrashTimes.put(app.info.processName, app.uid, now); 10398 } 10399 10400 return true; 10401 } 10402 10403 void startAppProblemLocked(ProcessRecord app) { 10404 if (app.userId == mCurrentUserId) { 10405 app.errorReportReceiver = ApplicationErrorReport.getErrorReportReceiver( 10406 mContext, app.info.packageName, app.info.flags); 10407 } else { 10408 // If this app is not running under the current user, then we 10409 // can't give it a report button because that would require 10410 // launching the report UI under a different user. 10411 app.errorReportReceiver = null; 10412 } 10413 skipCurrentReceiverLocked(app); 10414 } 10415 10416 void skipCurrentReceiverLocked(ProcessRecord app) { 10417 for (BroadcastQueue queue : mBroadcastQueues) { 10418 queue.skipCurrentReceiverLocked(app); 10419 } 10420 } 10421 10422 /** 10423 * Used by {@link com.android.internal.os.RuntimeInit} to report when an application crashes. 10424 * The application process will exit immediately after this call returns. 10425 * @param app object of the crashing app, null for the system server 10426 * @param crashInfo describing the exception 10427 */ 10428 public void handleApplicationCrash(IBinder app, ApplicationErrorReport.CrashInfo crashInfo) { 10429 ProcessRecord r = findAppProcess(app, "Crash"); 10430 final String processName = app == null ? "system_server" 10431 : (r == null ? "unknown" : r.processName); 10432 10433 handleApplicationCrashInner("crash", r, processName, crashInfo); 10434 } 10435 10436 /* Native crash reporting uses this inner version because it needs to be somewhat 10437 * decoupled from the AM-managed cleanup lifecycle 10438 */ 10439 void handleApplicationCrashInner(String eventType, ProcessRecord r, String processName, 10440 ApplicationErrorReport.CrashInfo crashInfo) { 10441 EventLog.writeEvent(EventLogTags.AM_CRASH, Binder.getCallingPid(), 10442 UserHandle.getUserId(Binder.getCallingUid()), processName, 10443 r == null ? -1 : r.info.flags, 10444 crashInfo.exceptionClassName, 10445 crashInfo.exceptionMessage, 10446 crashInfo.throwFileName, 10447 crashInfo.throwLineNumber); 10448 10449 addErrorToDropBox(eventType, r, processName, null, null, null, null, null, crashInfo); 10450 10451 crashApplication(r, crashInfo); 10452 } 10453 10454 public void handleApplicationStrictModeViolation( 10455 IBinder app, 10456 int violationMask, 10457 StrictMode.ViolationInfo info) { 10458 ProcessRecord r = findAppProcess(app, "StrictMode"); 10459 if (r == null) { 10460 return; 10461 } 10462 10463 if ((violationMask & StrictMode.PENALTY_DROPBOX) != 0) { 10464 Integer stackFingerprint = info.hashCode(); 10465 boolean logIt = true; 10466 synchronized (mAlreadyLoggedViolatedStacks) { 10467 if (mAlreadyLoggedViolatedStacks.contains(stackFingerprint)) { 10468 logIt = false; 10469 // TODO: sub-sample into EventLog for these, with 10470 // the info.durationMillis? Then we'd get 10471 // the relative pain numbers, without logging all 10472 // the stack traces repeatedly. We'd want to do 10473 // likewise in the client code, which also does 10474 // dup suppression, before the Binder call. 10475 } else { 10476 if (mAlreadyLoggedViolatedStacks.size() >= MAX_DUP_SUPPRESSED_STACKS) { 10477 mAlreadyLoggedViolatedStacks.clear(); 10478 } 10479 mAlreadyLoggedViolatedStacks.add(stackFingerprint); 10480 } 10481 } 10482 if (logIt) { 10483 logStrictModeViolationToDropBox(r, info); 10484 } 10485 } 10486 10487 if ((violationMask & StrictMode.PENALTY_DIALOG) != 0) { 10488 AppErrorResult result = new AppErrorResult(); 10489 synchronized (this) { 10490 final long origId = Binder.clearCallingIdentity(); 10491 10492 Message msg = Message.obtain(); 10493 msg.what = SHOW_STRICT_MODE_VIOLATION_MSG; 10494 HashMap<String, Object> data = new HashMap<String, Object>(); 10495 data.put("result", result); 10496 data.put("app", r); 10497 data.put("violationMask", violationMask); 10498 data.put("info", info); 10499 msg.obj = data; 10500 mHandler.sendMessage(msg); 10501 10502 Binder.restoreCallingIdentity(origId); 10503 } 10504 int res = result.get(); 10505 Slog.w(TAG, "handleApplicationStrictModeViolation; res=" + res); 10506 } 10507 } 10508 10509 // Depending on the policy in effect, there could be a bunch of 10510 // these in quick succession so we try to batch these together to 10511 // minimize disk writes, number of dropbox entries, and maximize 10512 // compression, by having more fewer, larger records. 10513 private void logStrictModeViolationToDropBox( 10514 ProcessRecord process, 10515 StrictMode.ViolationInfo info) { 10516 if (info == null) { 10517 return; 10518 } 10519 final boolean isSystemApp = process == null || 10520 (process.info.flags & (ApplicationInfo.FLAG_SYSTEM | 10521 ApplicationInfo.FLAG_UPDATED_SYSTEM_APP)) != 0; 10522 final String processName = process == null ? "unknown" : process.processName; 10523 final String dropboxTag = isSystemApp ? "system_app_strictmode" : "data_app_strictmode"; 10524 final DropBoxManager dbox = (DropBoxManager) 10525 mContext.getSystemService(Context.DROPBOX_SERVICE); 10526 10527 // Exit early if the dropbox isn't configured to accept this report type. 10528 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 10529 10530 boolean bufferWasEmpty; 10531 boolean needsFlush; 10532 final StringBuilder sb = isSystemApp ? mStrictModeBuffer : new StringBuilder(1024); 10533 synchronized (sb) { 10534 bufferWasEmpty = sb.length() == 0; 10535 appendDropBoxProcessHeaders(process, processName, sb); 10536 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 10537 sb.append("System-App: ").append(isSystemApp).append("\n"); 10538 sb.append("Uptime-Millis: ").append(info.violationUptimeMillis).append("\n"); 10539 if (info.violationNumThisLoop != 0) { 10540 sb.append("Loop-Violation-Number: ").append(info.violationNumThisLoop).append("\n"); 10541 } 10542 if (info.numAnimationsRunning != 0) { 10543 sb.append("Animations-Running: ").append(info.numAnimationsRunning).append("\n"); 10544 } 10545 if (info.broadcastIntentAction != null) { 10546 sb.append("Broadcast-Intent-Action: ").append(info.broadcastIntentAction).append("\n"); 10547 } 10548 if (info.durationMillis != -1) { 10549 sb.append("Duration-Millis: ").append(info.durationMillis).append("\n"); 10550 } 10551 if (info.numInstances != -1) { 10552 sb.append("Instance-Count: ").append(info.numInstances).append("\n"); 10553 } 10554 if (info.tags != null) { 10555 for (String tag : info.tags) { 10556 sb.append("Span-Tag: ").append(tag).append("\n"); 10557 } 10558 } 10559 sb.append("\n"); 10560 if (info.crashInfo != null && info.crashInfo.stackTrace != null) { 10561 sb.append(info.crashInfo.stackTrace); 10562 } 10563 sb.append("\n"); 10564 10565 // Only buffer up to ~64k. Various logging bits truncate 10566 // things at 128k. 10567 needsFlush = (sb.length() > 64 * 1024); 10568 } 10569 10570 // Flush immediately if the buffer's grown too large, or this 10571 // is a non-system app. Non-system apps are isolated with a 10572 // different tag & policy and not batched. 10573 // 10574 // Batching is useful during internal testing with 10575 // StrictMode settings turned up high. Without batching, 10576 // thousands of separate files could be created on boot. 10577 if (!isSystemApp || needsFlush) { 10578 new Thread("Error dump: " + dropboxTag) { 10579 @Override 10580 public void run() { 10581 String report; 10582 synchronized (sb) { 10583 report = sb.toString(); 10584 sb.delete(0, sb.length()); 10585 sb.trimToSize(); 10586 } 10587 if (report.length() != 0) { 10588 dbox.addText(dropboxTag, report); 10589 } 10590 } 10591 }.start(); 10592 return; 10593 } 10594 10595 // System app batching: 10596 if (!bufferWasEmpty) { 10597 // An existing dropbox-writing thread is outstanding, so 10598 // we don't need to start it up. The existing thread will 10599 // catch the buffer appends we just did. 10600 return; 10601 } 10602 10603 // Worker thread to both batch writes and to avoid blocking the caller on I/O. 10604 // (After this point, we shouldn't access AMS internal data structures.) 10605 new Thread("Error dump: " + dropboxTag) { 10606 @Override 10607 public void run() { 10608 // 5 second sleep to let stacks arrive and be batched together 10609 try { 10610 Thread.sleep(5000); // 5 seconds 10611 } catch (InterruptedException e) {} 10612 10613 String errorReport; 10614 synchronized (mStrictModeBuffer) { 10615 errorReport = mStrictModeBuffer.toString(); 10616 if (errorReport.length() == 0) { 10617 return; 10618 } 10619 mStrictModeBuffer.delete(0, mStrictModeBuffer.length()); 10620 mStrictModeBuffer.trimToSize(); 10621 } 10622 dbox.addText(dropboxTag, errorReport); 10623 } 10624 }.start(); 10625 } 10626 10627 /** 10628 * Used by {@link Log} via {@link com.android.internal.os.RuntimeInit} to report serious errors. 10629 * @param app object of the crashing app, null for the system server 10630 * @param tag reported by the caller 10631 * @param crashInfo describing the context of the error 10632 * @return true if the process should exit immediately (WTF is fatal) 10633 */ 10634 public boolean handleApplicationWtf(IBinder app, String tag, 10635 ApplicationErrorReport.CrashInfo crashInfo) { 10636 ProcessRecord r = findAppProcess(app, "WTF"); 10637 final String processName = app == null ? "system_server" 10638 : (r == null ? "unknown" : r.processName); 10639 10640 EventLog.writeEvent(EventLogTags.AM_WTF, 10641 UserHandle.getUserId(Binder.getCallingUid()), Binder.getCallingPid(), 10642 processName, 10643 r == null ? -1 : r.info.flags, 10644 tag, crashInfo.exceptionMessage); 10645 10646 addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, crashInfo); 10647 10648 if (r != null && r.pid != Process.myPid() && 10649 Settings.Global.getInt(mContext.getContentResolver(), 10650 Settings.Global.WTF_IS_FATAL, 0) != 0) { 10651 crashApplication(r, crashInfo); 10652 return true; 10653 } else { 10654 return false; 10655 } 10656 } 10657 10658 /** 10659 * @param app object of some object (as stored in {@link com.android.internal.os.RuntimeInit}) 10660 * @return the corresponding {@link ProcessRecord} object, or null if none could be found 10661 */ 10662 private ProcessRecord findAppProcess(IBinder app, String reason) { 10663 if (app == null) { 10664 return null; 10665 } 10666 10667 synchronized (this) { 10668 final int NP = mProcessNames.getMap().size(); 10669 for (int ip=0; ip<NP; ip++) { 10670 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 10671 final int NA = apps.size(); 10672 for (int ia=0; ia<NA; ia++) { 10673 ProcessRecord p = apps.valueAt(ia); 10674 if (p.thread != null && p.thread.asBinder() == app) { 10675 return p; 10676 } 10677 } 10678 } 10679 10680 Slog.w(TAG, "Can't find mystery application for " + reason 10681 + " from pid=" + Binder.getCallingPid() 10682 + " uid=" + Binder.getCallingUid() + ": " + app); 10683 return null; 10684 } 10685 } 10686 10687 /** 10688 * Utility function for addErrorToDropBox and handleStrictModeViolation's logging 10689 * to append various headers to the dropbox log text. 10690 */ 10691 private void appendDropBoxProcessHeaders(ProcessRecord process, String processName, 10692 StringBuilder sb) { 10693 // Watchdog thread ends up invoking this function (with 10694 // a null ProcessRecord) to add the stack file to dropbox. 10695 // Do not acquire a lock on this (am) in such cases, as it 10696 // could cause a potential deadlock, if and when watchdog 10697 // is invoked due to unavailability of lock on am and it 10698 // would prevent watchdog from killing system_server. 10699 if (process == null) { 10700 sb.append("Process: ").append(processName).append("\n"); 10701 return; 10702 } 10703 // Note: ProcessRecord 'process' is guarded by the service 10704 // instance. (notably process.pkgList, which could otherwise change 10705 // concurrently during execution of this method) 10706 synchronized (this) { 10707 sb.append("Process: ").append(processName).append("\n"); 10708 int flags = process.info.flags; 10709 IPackageManager pm = AppGlobals.getPackageManager(); 10710 sb.append("Flags: 0x").append(Integer.toString(flags, 16)).append("\n"); 10711 for (int ip=0; ip<process.pkgList.size(); ip++) { 10712 String pkg = process.pkgList.keyAt(ip); 10713 sb.append("Package: ").append(pkg); 10714 try { 10715 PackageInfo pi = pm.getPackageInfo(pkg, 0, UserHandle.getCallingUserId()); 10716 if (pi != null) { 10717 sb.append(" v").append(pi.versionCode); 10718 if (pi.versionName != null) { 10719 sb.append(" (").append(pi.versionName).append(")"); 10720 } 10721 } 10722 } catch (RemoteException e) { 10723 Slog.e(TAG, "Error getting package info: " + pkg, e); 10724 } 10725 sb.append("\n"); 10726 } 10727 } 10728 } 10729 10730 private static String processClass(ProcessRecord process) { 10731 if (process == null || process.pid == MY_PID) { 10732 return "system_server"; 10733 } else if ((process.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 10734 return "system_app"; 10735 } else { 10736 return "data_app"; 10737 } 10738 } 10739 10740 /** 10741 * Write a description of an error (crash, WTF, ANR) to the drop box. 10742 * @param eventType to include in the drop box tag ("crash", "wtf", etc.) 10743 * @param process which caused the error, null means the system server 10744 * @param activity which triggered the error, null if unknown 10745 * @param parent activity related to the error, null if unknown 10746 * @param subject line related to the error, null if absent 10747 * @param report in long form describing the error, null if absent 10748 * @param logFile to include in the report, null if none 10749 * @param crashInfo giving an application stack trace, null if absent 10750 */ 10751 public void addErrorToDropBox(String eventType, 10752 ProcessRecord process, String processName, ActivityRecord activity, 10753 ActivityRecord parent, String subject, 10754 final String report, final File logFile, 10755 final ApplicationErrorReport.CrashInfo crashInfo) { 10756 // NOTE -- this must never acquire the ActivityManagerService lock, 10757 // otherwise the watchdog may be prevented from resetting the system. 10758 10759 final String dropboxTag = processClass(process) + "_" + eventType; 10760 final DropBoxManager dbox = (DropBoxManager) 10761 mContext.getSystemService(Context.DROPBOX_SERVICE); 10762 10763 // Exit early if the dropbox isn't configured to accept this report type. 10764 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 10765 10766 final StringBuilder sb = new StringBuilder(1024); 10767 appendDropBoxProcessHeaders(process, processName, sb); 10768 if (activity != null) { 10769 sb.append("Activity: ").append(activity.shortComponentName).append("\n"); 10770 } 10771 if (parent != null && parent.app != null && parent.app.pid != process.pid) { 10772 sb.append("Parent-Process: ").append(parent.app.processName).append("\n"); 10773 } 10774 if (parent != null && parent != activity) { 10775 sb.append("Parent-Activity: ").append(parent.shortComponentName).append("\n"); 10776 } 10777 if (subject != null) { 10778 sb.append("Subject: ").append(subject).append("\n"); 10779 } 10780 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 10781 if (Debug.isDebuggerConnected()) { 10782 sb.append("Debugger: Connected\n"); 10783 } 10784 sb.append("\n"); 10785 10786 // Do the rest in a worker thread to avoid blocking the caller on I/O 10787 // (After this point, we shouldn't access AMS internal data structures.) 10788 Thread worker = new Thread("Error dump: " + dropboxTag) { 10789 @Override 10790 public void run() { 10791 if (report != null) { 10792 sb.append(report); 10793 } 10794 if (logFile != null) { 10795 try { 10796 sb.append(FileUtils.readTextFile(logFile, DROPBOX_MAX_SIZE, 10797 "\n\n[[TRUNCATED]]")); 10798 } catch (IOException e) { 10799 Slog.e(TAG, "Error reading " + logFile, e); 10800 } 10801 } 10802 if (crashInfo != null && crashInfo.stackTrace != null) { 10803 sb.append(crashInfo.stackTrace); 10804 } 10805 10806 String setting = Settings.Global.ERROR_LOGCAT_PREFIX + dropboxTag; 10807 int lines = Settings.Global.getInt(mContext.getContentResolver(), setting, 0); 10808 if (lines > 0) { 10809 sb.append("\n"); 10810 10811 // Merge several logcat streams, and take the last N lines 10812 InputStreamReader input = null; 10813 try { 10814 java.lang.Process logcat = new ProcessBuilder("/system/bin/logcat", 10815 "-v", "time", "-b", "events", "-b", "system", "-b", "main", 10816 "-t", String.valueOf(lines)).redirectErrorStream(true).start(); 10817 10818 try { logcat.getOutputStream().close(); } catch (IOException e) {} 10819 try { logcat.getErrorStream().close(); } catch (IOException e) {} 10820 input = new InputStreamReader(logcat.getInputStream()); 10821 10822 int num; 10823 char[] buf = new char[8192]; 10824 while ((num = input.read(buf)) > 0) sb.append(buf, 0, num); 10825 } catch (IOException e) { 10826 Slog.e(TAG, "Error running logcat", e); 10827 } finally { 10828 if (input != null) try { input.close(); } catch (IOException e) {} 10829 } 10830 } 10831 10832 dbox.addText(dropboxTag, sb.toString()); 10833 } 10834 }; 10835 10836 if (process == null) { 10837 // If process is null, we are being called from some internal code 10838 // and may be about to die -- run this synchronously. 10839 worker.run(); 10840 } else { 10841 worker.start(); 10842 } 10843 } 10844 10845 /** 10846 * Bring up the "unexpected error" dialog box for a crashing app. 10847 * Deal with edge cases (intercepts from instrumented applications, 10848 * ActivityController, error intent receivers, that sort of thing). 10849 * @param r the application crashing 10850 * @param crashInfo describing the failure 10851 */ 10852 private void crashApplication(ProcessRecord r, ApplicationErrorReport.CrashInfo crashInfo) { 10853 long timeMillis = System.currentTimeMillis(); 10854 String shortMsg = crashInfo.exceptionClassName; 10855 String longMsg = crashInfo.exceptionMessage; 10856 String stackTrace = crashInfo.stackTrace; 10857 if (shortMsg != null && longMsg != null) { 10858 longMsg = shortMsg + ": " + longMsg; 10859 } else if (shortMsg != null) { 10860 longMsg = shortMsg; 10861 } 10862 10863 AppErrorResult result = new AppErrorResult(); 10864 synchronized (this) { 10865 if (mController != null) { 10866 try { 10867 String name = r != null ? r.processName : null; 10868 int pid = r != null ? r.pid : Binder.getCallingPid(); 10869 int uid = r != null ? r.info.uid : Binder.getCallingUid(); 10870 if (!mController.appCrashed(name, pid, 10871 shortMsg, longMsg, timeMillis, crashInfo.stackTrace)) { 10872 Slog.w(TAG, "Force-killing crashed app " + name 10873 + " at watcher's request"); 10874 Process.killProcess(pid); 10875 if (r != null) { 10876 Process.killProcessGroup(uid, pid); 10877 } 10878 return; 10879 } 10880 } catch (RemoteException e) { 10881 mController = null; 10882 Watchdog.getInstance().setActivityController(null); 10883 } 10884 } 10885 10886 final long origId = Binder.clearCallingIdentity(); 10887 10888 // If this process is running instrumentation, finish it. 10889 if (r != null && r.instrumentationClass != null) { 10890 Slog.w(TAG, "Error in app " + r.processName 10891 + " running instrumentation " + r.instrumentationClass + ":"); 10892 if (shortMsg != null) Slog.w(TAG, " " + shortMsg); 10893 if (longMsg != null) Slog.w(TAG, " " + longMsg); 10894 Bundle info = new Bundle(); 10895 info.putString("shortMsg", shortMsg); 10896 info.putString("longMsg", longMsg); 10897 finishInstrumentationLocked(r, Activity.RESULT_CANCELED, info); 10898 Binder.restoreCallingIdentity(origId); 10899 return; 10900 } 10901 10902 // If we can't identify the process or it's already exceeded its crash quota, 10903 // quit right away without showing a crash dialog. 10904 if (r == null || !makeAppCrashingLocked(r, shortMsg, longMsg, stackTrace)) { 10905 Binder.restoreCallingIdentity(origId); 10906 return; 10907 } 10908 10909 Message msg = Message.obtain(); 10910 msg.what = SHOW_ERROR_MSG; 10911 HashMap data = new HashMap(); 10912 data.put("result", result); 10913 data.put("app", r); 10914 msg.obj = data; 10915 mHandler.sendMessage(msg); 10916 10917 Binder.restoreCallingIdentity(origId); 10918 } 10919 10920 int res = result.get(); 10921 10922 Intent appErrorIntent = null; 10923 synchronized (this) { 10924 if (r != null && !r.isolated) { 10925 // XXX Can't keep track of crash time for isolated processes, 10926 // since they don't have a persistent identity. 10927 mProcessCrashTimes.put(r.info.processName, r.uid, 10928 SystemClock.uptimeMillis()); 10929 } 10930 if (res == AppErrorDialog.FORCE_QUIT_AND_REPORT) { 10931 appErrorIntent = createAppErrorIntentLocked(r, timeMillis, crashInfo); 10932 } 10933 } 10934 10935 if (appErrorIntent != null) { 10936 try { 10937 mContext.startActivityAsUser(appErrorIntent, new UserHandle(r.userId)); 10938 } catch (ActivityNotFoundException e) { 10939 Slog.w(TAG, "bug report receiver dissappeared", e); 10940 } 10941 } 10942 } 10943 10944 Intent createAppErrorIntentLocked(ProcessRecord r, 10945 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 10946 ApplicationErrorReport report = createAppErrorReportLocked(r, timeMillis, crashInfo); 10947 if (report == null) { 10948 return null; 10949 } 10950 Intent result = new Intent(Intent.ACTION_APP_ERROR); 10951 result.setComponent(r.errorReportReceiver); 10952 result.putExtra(Intent.EXTRA_BUG_REPORT, report); 10953 result.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 10954 return result; 10955 } 10956 10957 private ApplicationErrorReport createAppErrorReportLocked(ProcessRecord r, 10958 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 10959 if (r.errorReportReceiver == null) { 10960 return null; 10961 } 10962 10963 if (!r.crashing && !r.notResponding && !r.forceCrashReport) { 10964 return null; 10965 } 10966 10967 ApplicationErrorReport report = new ApplicationErrorReport(); 10968 report.packageName = r.info.packageName; 10969 report.installerPackageName = r.errorReportReceiver.getPackageName(); 10970 report.processName = r.processName; 10971 report.time = timeMillis; 10972 report.systemApp = (r.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0; 10973 10974 if (r.crashing || r.forceCrashReport) { 10975 report.type = ApplicationErrorReport.TYPE_CRASH; 10976 report.crashInfo = crashInfo; 10977 } else if (r.notResponding) { 10978 report.type = ApplicationErrorReport.TYPE_ANR; 10979 report.anrInfo = new ApplicationErrorReport.AnrInfo(); 10980 10981 report.anrInfo.activity = r.notRespondingReport.tag; 10982 report.anrInfo.cause = r.notRespondingReport.shortMsg; 10983 report.anrInfo.info = r.notRespondingReport.longMsg; 10984 } 10985 10986 return report; 10987 } 10988 10989 public List<ActivityManager.ProcessErrorStateInfo> getProcessesInErrorState() { 10990 enforceNotIsolatedCaller("getProcessesInErrorState"); 10991 // assume our apps are happy - lazy create the list 10992 List<ActivityManager.ProcessErrorStateInfo> errList = null; 10993 10994 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 10995 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 10996 int userId = UserHandle.getUserId(Binder.getCallingUid()); 10997 10998 synchronized (this) { 10999 11000 // iterate across all processes 11001 for (int i=mLruProcesses.size()-1; i>=0; i--) { 11002 ProcessRecord app = mLruProcesses.get(i); 11003 if (!allUsers && app.userId != userId) { 11004 continue; 11005 } 11006 if ((app.thread != null) && (app.crashing || app.notResponding)) { 11007 // This one's in trouble, so we'll generate a report for it 11008 // crashes are higher priority (in case there's a crash *and* an anr) 11009 ActivityManager.ProcessErrorStateInfo report = null; 11010 if (app.crashing) { 11011 report = app.crashingReport; 11012 } else if (app.notResponding) { 11013 report = app.notRespondingReport; 11014 } 11015 11016 if (report != null) { 11017 if (errList == null) { 11018 errList = new ArrayList<ActivityManager.ProcessErrorStateInfo>(1); 11019 } 11020 errList.add(report); 11021 } else { 11022 Slog.w(TAG, "Missing app error report, app = " + app.processName + 11023 " crashing = " + app.crashing + 11024 " notResponding = " + app.notResponding); 11025 } 11026 } 11027 } 11028 } 11029 11030 return errList; 11031 } 11032 11033 static int oomAdjToImportance(int adj, ActivityManager.RunningAppProcessInfo currApp) { 11034 if (adj >= ProcessList.CACHED_APP_MIN_ADJ) { 11035 if (currApp != null) { 11036 currApp.lru = adj - ProcessList.CACHED_APP_MIN_ADJ + 1; 11037 } 11038 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND; 11039 } else if (adj >= ProcessList.SERVICE_B_ADJ) { 11040 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_SERVICE; 11041 } else if (adj >= ProcessList.HOME_APP_ADJ) { 11042 if (currApp != null) { 11043 currApp.lru = 0; 11044 } 11045 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND; 11046 } else if (adj >= ProcessList.SERVICE_ADJ) { 11047 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_SERVICE; 11048 } else if (adj >= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 11049 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_CANT_SAVE_STATE; 11050 } else if (adj >= ProcessList.PERCEPTIBLE_APP_ADJ) { 11051 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_PERCEPTIBLE; 11052 } else if (adj >= ProcessList.VISIBLE_APP_ADJ) { 11053 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_VISIBLE; 11054 } else { 11055 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND; 11056 } 11057 } 11058 11059 private void fillInProcMemInfo(ProcessRecord app, 11060 ActivityManager.RunningAppProcessInfo outInfo) { 11061 outInfo.pid = app.pid; 11062 outInfo.uid = app.info.uid; 11063 if (mHeavyWeightProcess == app) { 11064 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_CANT_SAVE_STATE; 11065 } 11066 if (app.persistent) { 11067 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_PERSISTENT; 11068 } 11069 if (app.activities.size() > 0) { 11070 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_HAS_ACTIVITIES; 11071 } 11072 outInfo.lastTrimLevel = app.trimMemoryLevel; 11073 int adj = app.curAdj; 11074 outInfo.importance = oomAdjToImportance(adj, outInfo); 11075 outInfo.importanceReasonCode = app.adjTypeCode; 11076 outInfo.processState = app.curProcState; 11077 } 11078 11079 public List<ActivityManager.RunningAppProcessInfo> getRunningAppProcesses() { 11080 enforceNotIsolatedCaller("getRunningAppProcesses"); 11081 // Lazy instantiation of list 11082 List<ActivityManager.RunningAppProcessInfo> runList = null; 11083 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 11084 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 11085 int userId = UserHandle.getUserId(Binder.getCallingUid()); 11086 synchronized (this) { 11087 // Iterate across all processes 11088 for (int i=mLruProcesses.size()-1; i>=0; i--) { 11089 ProcessRecord app = mLruProcesses.get(i); 11090 if (!allUsers && app.userId != userId) { 11091 continue; 11092 } 11093 if ((app.thread != null) && (!app.crashing && !app.notResponding)) { 11094 // Generate process state info for running application 11095 ActivityManager.RunningAppProcessInfo currApp = 11096 new ActivityManager.RunningAppProcessInfo(app.processName, 11097 app.pid, app.getPackageList()); 11098 fillInProcMemInfo(app, currApp); 11099 if (app.adjSource instanceof ProcessRecord) { 11100 currApp.importanceReasonPid = ((ProcessRecord)app.adjSource).pid; 11101 currApp.importanceReasonImportance = oomAdjToImportance( 11102 app.adjSourceOom, null); 11103 } else if (app.adjSource instanceof ActivityRecord) { 11104 ActivityRecord r = (ActivityRecord)app.adjSource; 11105 if (r.app != null) currApp.importanceReasonPid = r.app.pid; 11106 } 11107 if (app.adjTarget instanceof ComponentName) { 11108 currApp.importanceReasonComponent = (ComponentName)app.adjTarget; 11109 } 11110 //Slog.v(TAG, "Proc " + app.processName + ": imp=" + currApp.importance 11111 // + " lru=" + currApp.lru); 11112 if (runList == null) { 11113 runList = new ArrayList<ActivityManager.RunningAppProcessInfo>(); 11114 } 11115 runList.add(currApp); 11116 } 11117 } 11118 } 11119 return runList; 11120 } 11121 11122 public List<ApplicationInfo> getRunningExternalApplications() { 11123 enforceNotIsolatedCaller("getRunningExternalApplications"); 11124 List<ActivityManager.RunningAppProcessInfo> runningApps = getRunningAppProcesses(); 11125 List<ApplicationInfo> retList = new ArrayList<ApplicationInfo>(); 11126 if (runningApps != null && runningApps.size() > 0) { 11127 Set<String> extList = new HashSet<String>(); 11128 for (ActivityManager.RunningAppProcessInfo app : runningApps) { 11129 if (app.pkgList != null) { 11130 for (String pkg : app.pkgList) { 11131 extList.add(pkg); 11132 } 11133 } 11134 } 11135 IPackageManager pm = AppGlobals.getPackageManager(); 11136 for (String pkg : extList) { 11137 try { 11138 ApplicationInfo info = pm.getApplicationInfo(pkg, 0, UserHandle.getCallingUserId()); 11139 if ((info.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0) { 11140 retList.add(info); 11141 } 11142 } catch (RemoteException e) { 11143 } 11144 } 11145 } 11146 return retList; 11147 } 11148 11149 @Override 11150 public void getMyMemoryState(ActivityManager.RunningAppProcessInfo outInfo) { 11151 enforceNotIsolatedCaller("getMyMemoryState"); 11152 synchronized (this) { 11153 ProcessRecord proc; 11154 synchronized (mPidsSelfLocked) { 11155 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 11156 } 11157 fillInProcMemInfo(proc, outInfo); 11158 } 11159 } 11160 11161 @Override 11162 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 11163 if (checkCallingPermission(android.Manifest.permission.DUMP) 11164 != PackageManager.PERMISSION_GRANTED) { 11165 pw.println("Permission Denial: can't dump ActivityManager from from pid=" 11166 + Binder.getCallingPid() 11167 + ", uid=" + Binder.getCallingUid() 11168 + " without permission " 11169 + android.Manifest.permission.DUMP); 11170 return; 11171 } 11172 11173 boolean dumpAll = false; 11174 boolean dumpClient = false; 11175 String dumpPackage = null; 11176 11177 int opti = 0; 11178 while (opti < args.length) { 11179 String opt = args[opti]; 11180 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 11181 break; 11182 } 11183 opti++; 11184 if ("-a".equals(opt)) { 11185 dumpAll = true; 11186 } else if ("-c".equals(opt)) { 11187 dumpClient = true; 11188 } else if ("-h".equals(opt)) { 11189 pw.println("Activity manager dump options:"); 11190 pw.println(" [-a] [-c] [-h] [cmd] ..."); 11191 pw.println(" cmd may be one of:"); 11192 pw.println(" a[ctivities]: activity stack state"); 11193 pw.println(" b[roadcasts] [PACKAGE_NAME] [history [-s]]: broadcast state"); 11194 pw.println(" i[ntents] [PACKAGE_NAME]: pending intent state"); 11195 pw.println(" p[rocesses] [PACKAGE_NAME]: process state"); 11196 pw.println(" o[om]: out of memory management"); 11197 pw.println(" prov[iders] [COMP_SPEC ...]: content provider state"); 11198 pw.println(" provider [COMP_SPEC]: provider client-side state"); 11199 pw.println(" s[ervices] [COMP_SPEC ...]: service state"); 11200 pw.println(" service [COMP_SPEC]: service client-side state"); 11201 pw.println(" package [PACKAGE_NAME]: all state related to given package"); 11202 pw.println(" all: dump all activities"); 11203 pw.println(" top: dump the top activity"); 11204 pw.println(" cmd may also be a COMP_SPEC to dump activities."); 11205 pw.println(" COMP_SPEC may be a component name (com.foo/.myApp),"); 11206 pw.println(" a partial substring in a component name, a"); 11207 pw.println(" hex object identifier."); 11208 pw.println(" -a: include all available server state."); 11209 pw.println(" -c: include client state."); 11210 return; 11211 } else { 11212 pw.println("Unknown argument: " + opt + "; use -h for help"); 11213 } 11214 } 11215 11216 long origId = Binder.clearCallingIdentity(); 11217 boolean more = false; 11218 // Is the caller requesting to dump a particular piece of data? 11219 if (opti < args.length) { 11220 String cmd = args[opti]; 11221 opti++; 11222 if ("activities".equals(cmd) || "a".equals(cmd)) { 11223 synchronized (this) { 11224 dumpActivitiesLocked(fd, pw, args, opti, true, dumpClient, null); 11225 } 11226 } else if ("broadcasts".equals(cmd) || "b".equals(cmd)) { 11227 String[] newArgs; 11228 String name; 11229 if (opti >= args.length) { 11230 name = null; 11231 newArgs = EMPTY_STRING_ARRAY; 11232 } else { 11233 name = args[opti]; 11234 opti++; 11235 newArgs = new String[args.length - opti]; 11236 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11237 args.length - opti); 11238 } 11239 synchronized (this) { 11240 dumpBroadcastsLocked(fd, pw, args, opti, true, name); 11241 } 11242 } else if ("intents".equals(cmd) || "i".equals(cmd)) { 11243 String[] newArgs; 11244 String name; 11245 if (opti >= args.length) { 11246 name = null; 11247 newArgs = EMPTY_STRING_ARRAY; 11248 } else { 11249 name = args[opti]; 11250 opti++; 11251 newArgs = new String[args.length - opti]; 11252 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11253 args.length - opti); 11254 } 11255 synchronized (this) { 11256 dumpPendingIntentsLocked(fd, pw, args, opti, true, name); 11257 } 11258 } else if ("processes".equals(cmd) || "p".equals(cmd)) { 11259 String[] newArgs; 11260 String name; 11261 if (opti >= args.length) { 11262 name = null; 11263 newArgs = EMPTY_STRING_ARRAY; 11264 } else { 11265 name = args[opti]; 11266 opti++; 11267 newArgs = new String[args.length - opti]; 11268 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11269 args.length - opti); 11270 } 11271 synchronized (this) { 11272 dumpProcessesLocked(fd, pw, args, opti, true, name); 11273 } 11274 } else if ("oom".equals(cmd) || "o".equals(cmd)) { 11275 synchronized (this) { 11276 dumpOomLocked(fd, pw, args, opti, true); 11277 } 11278 } else if ("provider".equals(cmd)) { 11279 String[] newArgs; 11280 String name; 11281 if (opti >= args.length) { 11282 name = null; 11283 newArgs = EMPTY_STRING_ARRAY; 11284 } else { 11285 name = args[opti]; 11286 opti++; 11287 newArgs = new String[args.length - opti]; 11288 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, args.length - opti); 11289 } 11290 if (!dumpProvider(fd, pw, name, newArgs, 0, dumpAll)) { 11291 pw.println("No providers match: " + name); 11292 pw.println("Use -h for help."); 11293 } 11294 } else if ("providers".equals(cmd) || "prov".equals(cmd)) { 11295 synchronized (this) { 11296 dumpProvidersLocked(fd, pw, args, opti, true, null); 11297 } 11298 } else if ("service".equals(cmd)) { 11299 String[] newArgs; 11300 String name; 11301 if (opti >= args.length) { 11302 name = null; 11303 newArgs = EMPTY_STRING_ARRAY; 11304 } else { 11305 name = args[opti]; 11306 opti++; 11307 newArgs = new String[args.length - opti]; 11308 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11309 args.length - opti); 11310 } 11311 if (!mServices.dumpService(fd, pw, name, newArgs, 0, dumpAll)) { 11312 pw.println("No services match: " + name); 11313 pw.println("Use -h for help."); 11314 } 11315 } else if ("package".equals(cmd)) { 11316 String[] newArgs; 11317 if (opti >= args.length) { 11318 pw.println("package: no package name specified"); 11319 pw.println("Use -h for help."); 11320 } else { 11321 dumpPackage = args[opti]; 11322 opti++; 11323 newArgs = new String[args.length - opti]; 11324 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11325 args.length - opti); 11326 args = newArgs; 11327 opti = 0; 11328 more = true; 11329 } 11330 } else if ("services".equals(cmd) || "s".equals(cmd)) { 11331 synchronized (this) { 11332 mServices.dumpServicesLocked(fd, pw, args, opti, true, dumpClient, null); 11333 } 11334 } else { 11335 // Dumping a single activity? 11336 if (!dumpActivity(fd, pw, cmd, args, opti, dumpAll)) { 11337 pw.println("Bad activity command, or no activities match: " + cmd); 11338 pw.println("Use -h for help."); 11339 } 11340 } 11341 if (!more) { 11342 Binder.restoreCallingIdentity(origId); 11343 return; 11344 } 11345 } 11346 11347 // No piece of data specified, dump everything. 11348 synchronized (this) { 11349 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11350 pw.println(); 11351 if (dumpAll) { 11352 pw.println("-------------------------------------------------------------------------------"); 11353 } 11354 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11355 pw.println(); 11356 if (dumpAll) { 11357 pw.println("-------------------------------------------------------------------------------"); 11358 } 11359 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11360 pw.println(); 11361 if (dumpAll) { 11362 pw.println("-------------------------------------------------------------------------------"); 11363 } 11364 mServices.dumpServicesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 11365 pw.println(); 11366 if (dumpAll) { 11367 pw.println("-------------------------------------------------------------------------------"); 11368 } 11369 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 11370 pw.println(); 11371 if (dumpAll) { 11372 pw.println("-------------------------------------------------------------------------------"); 11373 } 11374 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11375 } 11376 Binder.restoreCallingIdentity(origId); 11377 } 11378 11379 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11380 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) { 11381 pw.println("ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)"); 11382 11383 boolean printedAnything = mStackSupervisor.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient, 11384 dumpPackage); 11385 boolean needSep = printedAnything; 11386 11387 boolean printed = ActivityStackSupervisor.printThisActivity(pw, mFocusedActivity, 11388 dumpPackage, needSep, " mFocusedActivity: "); 11389 if (printed) { 11390 printedAnything = true; 11391 needSep = false; 11392 } 11393 11394 if (dumpPackage == null) { 11395 if (needSep) { 11396 pw.println(); 11397 } 11398 needSep = true; 11399 printedAnything = true; 11400 mStackSupervisor.dump(pw, " "); 11401 } 11402 11403 if (mRecentTasks.size() > 0) { 11404 boolean printedHeader = false; 11405 11406 final int N = mRecentTasks.size(); 11407 for (int i=0; i<N; i++) { 11408 TaskRecord tr = mRecentTasks.get(i); 11409 if (dumpPackage != null) { 11410 if (tr.realActivity == null || 11411 !dumpPackage.equals(tr.realActivity)) { 11412 continue; 11413 } 11414 } 11415 if (!printedHeader) { 11416 if (needSep) { 11417 pw.println(); 11418 } 11419 pw.println(" Recent tasks:"); 11420 printedHeader = true; 11421 printedAnything = true; 11422 } 11423 pw.print(" * Recent #"); pw.print(i); pw.print(": "); 11424 pw.println(tr); 11425 if (dumpAll) { 11426 mRecentTasks.get(i).dump(pw, " "); 11427 } 11428 } 11429 } 11430 11431 if (!printedAnything) { 11432 pw.println(" (nothing)"); 11433 } 11434 } 11435 11436 void dumpProcessesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11437 int opti, boolean dumpAll, String dumpPackage) { 11438 boolean needSep = false; 11439 boolean printedAnything = false; 11440 int numPers = 0; 11441 11442 pw.println("ACTIVITY MANAGER RUNNING PROCESSES (dumpsys activity processes)"); 11443 11444 if (dumpAll) { 11445 final int NP = mProcessNames.getMap().size(); 11446 for (int ip=0; ip<NP; ip++) { 11447 SparseArray<ProcessRecord> procs = mProcessNames.getMap().valueAt(ip); 11448 final int NA = procs.size(); 11449 for (int ia=0; ia<NA; ia++) { 11450 ProcessRecord r = procs.valueAt(ia); 11451 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11452 continue; 11453 } 11454 if (!needSep) { 11455 pw.println(" All known processes:"); 11456 needSep = true; 11457 printedAnything = true; 11458 } 11459 pw.print(r.persistent ? " *PERS*" : " *APP*"); 11460 pw.print(" UID "); pw.print(procs.keyAt(ia)); 11461 pw.print(" "); pw.println(r); 11462 r.dump(pw, " "); 11463 if (r.persistent) { 11464 numPers++; 11465 } 11466 } 11467 } 11468 } 11469 11470 if (mIsolatedProcesses.size() > 0) { 11471 boolean printed = false; 11472 for (int i=0; i<mIsolatedProcesses.size(); i++) { 11473 ProcessRecord r = mIsolatedProcesses.valueAt(i); 11474 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11475 continue; 11476 } 11477 if (!printed) { 11478 if (needSep) { 11479 pw.println(); 11480 } 11481 pw.println(" Isolated process list (sorted by uid):"); 11482 printedAnything = true; 11483 printed = true; 11484 needSep = true; 11485 } 11486 pw.println(String.format("%sIsolated #%2d: %s", 11487 " ", i, r.toString())); 11488 } 11489 } 11490 11491 if (mLruProcesses.size() > 0) { 11492 if (needSep) { 11493 pw.println(); 11494 } 11495 pw.print(" Process LRU list (sorted by oom_adj, "); pw.print(mLruProcesses.size()); 11496 pw.print(" total, non-act at "); 11497 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 11498 pw.print(", non-svc at "); 11499 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 11500 pw.println("):"); 11501 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", false, dumpPackage); 11502 needSep = true; 11503 printedAnything = true; 11504 } 11505 11506 if (dumpAll || dumpPackage != null) { 11507 synchronized (mPidsSelfLocked) { 11508 boolean printed = false; 11509 for (int i=0; i<mPidsSelfLocked.size(); i++) { 11510 ProcessRecord r = mPidsSelfLocked.valueAt(i); 11511 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11512 continue; 11513 } 11514 if (!printed) { 11515 if (needSep) pw.println(); 11516 needSep = true; 11517 pw.println(" PID mappings:"); 11518 printed = true; 11519 printedAnything = true; 11520 } 11521 pw.print(" PID #"); pw.print(mPidsSelfLocked.keyAt(i)); 11522 pw.print(": "); pw.println(mPidsSelfLocked.valueAt(i)); 11523 } 11524 } 11525 } 11526 11527 if (mForegroundProcesses.size() > 0) { 11528 synchronized (mPidsSelfLocked) { 11529 boolean printed = false; 11530 for (int i=0; i<mForegroundProcesses.size(); i++) { 11531 ProcessRecord r = mPidsSelfLocked.get( 11532 mForegroundProcesses.valueAt(i).pid); 11533 if (dumpPackage != null && (r == null 11534 || !r.pkgList.containsKey(dumpPackage))) { 11535 continue; 11536 } 11537 if (!printed) { 11538 if (needSep) pw.println(); 11539 needSep = true; 11540 pw.println(" Foreground Processes:"); 11541 printed = true; 11542 printedAnything = true; 11543 } 11544 pw.print(" PID #"); pw.print(mForegroundProcesses.keyAt(i)); 11545 pw.print(": "); pw.println(mForegroundProcesses.valueAt(i)); 11546 } 11547 } 11548 } 11549 11550 if (mPersistentStartingProcesses.size() > 0) { 11551 if (needSep) pw.println(); 11552 needSep = true; 11553 printedAnything = true; 11554 pw.println(" Persisent processes that are starting:"); 11555 dumpProcessList(pw, this, mPersistentStartingProcesses, " ", 11556 "Starting Norm", "Restarting PERS", dumpPackage); 11557 } 11558 11559 if (mRemovedProcesses.size() > 0) { 11560 if (needSep) pw.println(); 11561 needSep = true; 11562 printedAnything = true; 11563 pw.println(" Processes that are being removed:"); 11564 dumpProcessList(pw, this, mRemovedProcesses, " ", 11565 "Removed Norm", "Removed PERS", dumpPackage); 11566 } 11567 11568 if (mProcessesOnHold.size() > 0) { 11569 if (needSep) pw.println(); 11570 needSep = true; 11571 printedAnything = true; 11572 pw.println(" Processes that are on old until the system is ready:"); 11573 dumpProcessList(pw, this, mProcessesOnHold, " ", 11574 "OnHold Norm", "OnHold PERS", dumpPackage); 11575 } 11576 11577 needSep = dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, dumpPackage); 11578 11579 if (mProcessCrashTimes.getMap().size() > 0) { 11580 boolean printed = false; 11581 long now = SystemClock.uptimeMillis(); 11582 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 11583 final int NP = pmap.size(); 11584 for (int ip=0; ip<NP; ip++) { 11585 String pname = pmap.keyAt(ip); 11586 SparseArray<Long> uids = pmap.valueAt(ip); 11587 final int N = uids.size(); 11588 for (int i=0; i<N; i++) { 11589 int puid = uids.keyAt(i); 11590 ProcessRecord r = mProcessNames.get(pname, puid); 11591 if (dumpPackage != null && (r == null 11592 || !r.pkgList.containsKey(dumpPackage))) { 11593 continue; 11594 } 11595 if (!printed) { 11596 if (needSep) pw.println(); 11597 needSep = true; 11598 pw.println(" Time since processes crashed:"); 11599 printed = true; 11600 printedAnything = true; 11601 } 11602 pw.print(" Process "); pw.print(pname); 11603 pw.print(" uid "); pw.print(puid); 11604 pw.print(": last crashed "); 11605 TimeUtils.formatDuration(now-uids.valueAt(i), pw); 11606 pw.println(" ago"); 11607 } 11608 } 11609 } 11610 11611 if (mBadProcesses.getMap().size() > 0) { 11612 boolean printed = false; 11613 final ArrayMap<String, SparseArray<BadProcessInfo>> pmap = mBadProcesses.getMap(); 11614 final int NP = pmap.size(); 11615 for (int ip=0; ip<NP; ip++) { 11616 String pname = pmap.keyAt(ip); 11617 SparseArray<BadProcessInfo> uids = pmap.valueAt(ip); 11618 final int N = uids.size(); 11619 for (int i=0; i<N; i++) { 11620 int puid = uids.keyAt(i); 11621 ProcessRecord r = mProcessNames.get(pname, puid); 11622 if (dumpPackage != null && (r == null 11623 || !r.pkgList.containsKey(dumpPackage))) { 11624 continue; 11625 } 11626 if (!printed) { 11627 if (needSep) pw.println(); 11628 needSep = true; 11629 pw.println(" Bad processes:"); 11630 printedAnything = true; 11631 } 11632 BadProcessInfo info = uids.valueAt(i); 11633 pw.print(" Bad process "); pw.print(pname); 11634 pw.print(" uid "); pw.print(puid); 11635 pw.print(": crashed at time "); pw.println(info.time); 11636 if (info.shortMsg != null) { 11637 pw.print(" Short msg: "); pw.println(info.shortMsg); 11638 } 11639 if (info.longMsg != null) { 11640 pw.print(" Long msg: "); pw.println(info.longMsg); 11641 } 11642 if (info.stack != null) { 11643 pw.println(" Stack:"); 11644 int lastPos = 0; 11645 for (int pos=0; pos<info.stack.length(); pos++) { 11646 if (info.stack.charAt(pos) == '\n') { 11647 pw.print(" "); 11648 pw.write(info.stack, lastPos, pos-lastPos); 11649 pw.println(); 11650 lastPos = pos+1; 11651 } 11652 } 11653 if (lastPos < info.stack.length()) { 11654 pw.print(" "); 11655 pw.write(info.stack, lastPos, info.stack.length()-lastPos); 11656 pw.println(); 11657 } 11658 } 11659 } 11660 } 11661 } 11662 11663 if (dumpPackage == null) { 11664 pw.println(); 11665 needSep = false; 11666 pw.println(" mStartedUsers:"); 11667 for (int i=0; i<mStartedUsers.size(); i++) { 11668 UserStartedState uss = mStartedUsers.valueAt(i); 11669 pw.print(" User #"); pw.print(uss.mHandle.getIdentifier()); 11670 pw.print(": "); uss.dump("", pw); 11671 } 11672 pw.print(" mStartedUserArray: ["); 11673 for (int i=0; i<mStartedUserArray.length; i++) { 11674 if (i > 0) pw.print(", "); 11675 pw.print(mStartedUserArray[i]); 11676 } 11677 pw.println("]"); 11678 pw.print(" mUserLru: ["); 11679 for (int i=0; i<mUserLru.size(); i++) { 11680 if (i > 0) pw.print(", "); 11681 pw.print(mUserLru.get(i)); 11682 } 11683 pw.println("]"); 11684 if (dumpAll) { 11685 pw.print(" mStartedUserArray: "); pw.println(Arrays.toString(mStartedUserArray)); 11686 } 11687 synchronized (mUserProfileGroupIdsSelfLocked) { 11688 if (mUserProfileGroupIdsSelfLocked.size() > 0) { 11689 pw.println(" mUserProfileGroupIds:"); 11690 for (int i=0; i<mUserProfileGroupIdsSelfLocked.size(); i++) { 11691 pw.print(" User #"); 11692 pw.print(mUserProfileGroupIdsSelfLocked.keyAt(i)); 11693 pw.print(" -> profile #"); 11694 pw.println(mUserProfileGroupIdsSelfLocked.valueAt(i)); 11695 } 11696 } 11697 } 11698 } 11699 if (mHomeProcess != null && (dumpPackage == null 11700 || mHomeProcess.pkgList.containsKey(dumpPackage))) { 11701 if (needSep) { 11702 pw.println(); 11703 needSep = false; 11704 } 11705 pw.println(" mHomeProcess: " + mHomeProcess); 11706 } 11707 if (mPreviousProcess != null && (dumpPackage == null 11708 || mPreviousProcess.pkgList.containsKey(dumpPackage))) { 11709 if (needSep) { 11710 pw.println(); 11711 needSep = false; 11712 } 11713 pw.println(" mPreviousProcess: " + mPreviousProcess); 11714 } 11715 if (dumpAll) { 11716 StringBuilder sb = new StringBuilder(128); 11717 sb.append(" mPreviousProcessVisibleTime: "); 11718 TimeUtils.formatDuration(mPreviousProcessVisibleTime, sb); 11719 pw.println(sb); 11720 } 11721 if (mHeavyWeightProcess != null && (dumpPackage == null 11722 || mHeavyWeightProcess.pkgList.containsKey(dumpPackage))) { 11723 if (needSep) { 11724 pw.println(); 11725 needSep = false; 11726 } 11727 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 11728 } 11729 if (dumpPackage == null) { 11730 pw.println(" mConfiguration: " + mConfiguration); 11731 } 11732 if (dumpAll) { 11733 pw.println(" mConfigWillChange: " + getFocusedStack().mConfigWillChange); 11734 if (mCompatModePackages.getPackages().size() > 0) { 11735 boolean printed = false; 11736 for (Map.Entry<String, Integer> entry 11737 : mCompatModePackages.getPackages().entrySet()) { 11738 String pkg = entry.getKey(); 11739 int mode = entry.getValue(); 11740 if (dumpPackage != null && !dumpPackage.equals(pkg)) { 11741 continue; 11742 } 11743 if (!printed) { 11744 pw.println(" mScreenCompatPackages:"); 11745 printed = true; 11746 } 11747 pw.print(" "); pw.print(pkg); pw.print(": "); 11748 pw.print(mode); pw.println(); 11749 } 11750 } 11751 } 11752 if (dumpPackage == null) { 11753 if (mSleeping || mWentToSleep || mLockScreenShown) { 11754 pw.println(" mSleeping=" + mSleeping + " mWentToSleep=" + mWentToSleep 11755 + " mLockScreenShown " + mLockScreenShown); 11756 } 11757 if (mShuttingDown || mRunningVoice) { 11758 pw.print(" mShuttingDown=" + mShuttingDown + " mRunningVoice=" + mRunningVoice); 11759 } 11760 } 11761 if (mDebugApp != null || mOrigDebugApp != null || mDebugTransient 11762 || mOrigWaitForDebugger) { 11763 if (dumpPackage == null || dumpPackage.equals(mDebugApp) 11764 || dumpPackage.equals(mOrigDebugApp)) { 11765 if (needSep) { 11766 pw.println(); 11767 needSep = false; 11768 } 11769 pw.println(" mDebugApp=" + mDebugApp + "/orig=" + mOrigDebugApp 11770 + " mDebugTransient=" + mDebugTransient 11771 + " mOrigWaitForDebugger=" + mOrigWaitForDebugger); 11772 } 11773 } 11774 if (mOpenGlTraceApp != null) { 11775 if (dumpPackage == null || dumpPackage.equals(mOpenGlTraceApp)) { 11776 if (needSep) { 11777 pw.println(); 11778 needSep = false; 11779 } 11780 pw.println(" mOpenGlTraceApp=" + mOpenGlTraceApp); 11781 } 11782 } 11783 if (mProfileApp != null || mProfileProc != null || mProfileFile != null 11784 || mProfileFd != null) { 11785 if (dumpPackage == null || dumpPackage.equals(mProfileApp)) { 11786 if (needSep) { 11787 pw.println(); 11788 needSep = false; 11789 } 11790 pw.println(" mProfileApp=" + mProfileApp + " mProfileProc=" + mProfileProc); 11791 pw.println(" mProfileFile=" + mProfileFile + " mProfileFd=" + mProfileFd); 11792 pw.println(" mProfileType=" + mProfileType + " mAutoStopProfiler=" 11793 + mAutoStopProfiler); 11794 } 11795 } 11796 if (dumpPackage == null) { 11797 if (mAlwaysFinishActivities || mController != null) { 11798 pw.println(" mAlwaysFinishActivities=" + mAlwaysFinishActivities 11799 + " mController=" + mController); 11800 } 11801 if (dumpAll) { 11802 pw.println(" Total persistent processes: " + numPers); 11803 pw.println(" mProcessesReady=" + mProcessesReady 11804 + " mSystemReady=" + mSystemReady); 11805 pw.println(" mBooting=" + mBooting 11806 + " mBooted=" + mBooted 11807 + " mFactoryTest=" + mFactoryTest); 11808 pw.print(" mLastPowerCheckRealtime="); 11809 TimeUtils.formatDuration(mLastPowerCheckRealtime, pw); 11810 pw.println(""); 11811 pw.print(" mLastPowerCheckUptime="); 11812 TimeUtils.formatDuration(mLastPowerCheckUptime, pw); 11813 pw.println(""); 11814 pw.println(" mGoingToSleep=" + mStackSupervisor.mGoingToSleep); 11815 pw.println(" mLaunchingActivity=" + mStackSupervisor.mLaunchingActivity); 11816 pw.println(" mAdjSeq=" + mAdjSeq + " mLruSeq=" + mLruSeq); 11817 pw.println(" mNumNonCachedProcs=" + mNumNonCachedProcs 11818 + " (" + mLruProcesses.size() + " total)" 11819 + " mNumCachedHiddenProcs=" + mNumCachedHiddenProcs 11820 + " mNumServiceProcs=" + mNumServiceProcs 11821 + " mNewNumServiceProcs=" + mNewNumServiceProcs); 11822 pw.println(" mAllowLowerMemLevel=" + mAllowLowerMemLevel 11823 + " mLastMemoryLevel" + mLastMemoryLevel 11824 + " mLastNumProcesses" + mLastNumProcesses); 11825 long now = SystemClock.uptimeMillis(); 11826 pw.print(" mLastIdleTime="); 11827 TimeUtils.formatDuration(now, mLastIdleTime, pw); 11828 pw.print(" mLowRamSinceLastIdle="); 11829 TimeUtils.formatDuration(getLowRamTimeSinceIdle(now), pw); 11830 pw.println(); 11831 } 11832 } 11833 11834 if (!printedAnything) { 11835 pw.println(" (nothing)"); 11836 } 11837 } 11838 11839 boolean dumpProcessesToGc(FileDescriptor fd, PrintWriter pw, String[] args, 11840 int opti, boolean needSep, boolean dumpAll, String dumpPackage) { 11841 if (mProcessesToGc.size() > 0) { 11842 boolean printed = false; 11843 long now = SystemClock.uptimeMillis(); 11844 for (int i=0; i<mProcessesToGc.size(); i++) { 11845 ProcessRecord proc = mProcessesToGc.get(i); 11846 if (dumpPackage != null && !dumpPackage.equals(proc.info.packageName)) { 11847 continue; 11848 } 11849 if (!printed) { 11850 if (needSep) pw.println(); 11851 needSep = true; 11852 pw.println(" Processes that are waiting to GC:"); 11853 printed = true; 11854 } 11855 pw.print(" Process "); pw.println(proc); 11856 pw.print(" lowMem="); pw.print(proc.reportLowMemory); 11857 pw.print(", last gced="); 11858 pw.print(now-proc.lastRequestedGc); 11859 pw.print(" ms ago, last lowMem="); 11860 pw.print(now-proc.lastLowMemory); 11861 pw.println(" ms ago"); 11862 11863 } 11864 } 11865 return needSep; 11866 } 11867 11868 void printOomLevel(PrintWriter pw, String name, int adj) { 11869 pw.print(" "); 11870 if (adj >= 0) { 11871 pw.print(' '); 11872 if (adj < 10) pw.print(' '); 11873 } else { 11874 if (adj > -10) pw.print(' '); 11875 } 11876 pw.print(adj); 11877 pw.print(": "); 11878 pw.print(name); 11879 pw.print(" ("); 11880 pw.print(mProcessList.getMemLevel(adj)/1024); 11881 pw.println(" kB)"); 11882 } 11883 11884 boolean dumpOomLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11885 int opti, boolean dumpAll) { 11886 boolean needSep = false; 11887 11888 if (mLruProcesses.size() > 0) { 11889 if (needSep) pw.println(); 11890 needSep = true; 11891 pw.println(" OOM levels:"); 11892 printOomLevel(pw, "SYSTEM_ADJ", ProcessList.SYSTEM_ADJ); 11893 printOomLevel(pw, "PERSISTENT_PROC_ADJ", ProcessList.PERSISTENT_PROC_ADJ); 11894 printOomLevel(pw, "FOREGROUND_APP_ADJ", ProcessList.FOREGROUND_APP_ADJ); 11895 printOomLevel(pw, "VISIBLE_APP_ADJ", ProcessList.VISIBLE_APP_ADJ); 11896 printOomLevel(pw, "PERCEPTIBLE_APP_ADJ", ProcessList.PERCEPTIBLE_APP_ADJ); 11897 printOomLevel(pw, "BACKUP_APP_ADJ", ProcessList.BACKUP_APP_ADJ); 11898 printOomLevel(pw, "HEAVY_WEIGHT_APP_ADJ", ProcessList.HEAVY_WEIGHT_APP_ADJ); 11899 printOomLevel(pw, "SERVICE_ADJ", ProcessList.SERVICE_ADJ); 11900 printOomLevel(pw, "HOME_APP_ADJ", ProcessList.HOME_APP_ADJ); 11901 printOomLevel(pw, "PREVIOUS_APP_ADJ", ProcessList.PREVIOUS_APP_ADJ); 11902 printOomLevel(pw, "SERVICE_B_ADJ", ProcessList.SERVICE_B_ADJ); 11903 printOomLevel(pw, "CACHED_APP_MIN_ADJ", ProcessList.CACHED_APP_MIN_ADJ); 11904 printOomLevel(pw, "CACHED_APP_MAX_ADJ", ProcessList.CACHED_APP_MAX_ADJ); 11905 11906 if (needSep) pw.println(); 11907 pw.print(" Process OOM control ("); pw.print(mLruProcesses.size()); 11908 pw.print(" total, non-act at "); 11909 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 11910 pw.print(", non-svc at "); 11911 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 11912 pw.println("):"); 11913 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", true, null); 11914 needSep = true; 11915 } 11916 11917 dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, null); 11918 11919 pw.println(); 11920 pw.println(" mHomeProcess: " + mHomeProcess); 11921 pw.println(" mPreviousProcess: " + mPreviousProcess); 11922 if (mHeavyWeightProcess != null) { 11923 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 11924 } 11925 11926 return true; 11927 } 11928 11929 /** 11930 * There are three ways to call this: 11931 * - no provider specified: dump all the providers 11932 * - a flattened component name that matched an existing provider was specified as the 11933 * first arg: dump that one provider 11934 * - the first arg isn't the flattened component name of an existing provider: 11935 * dump all providers whose component contains the first arg as a substring 11936 */ 11937 protected boolean dumpProvider(FileDescriptor fd, PrintWriter pw, String name, String[] args, 11938 int opti, boolean dumpAll) { 11939 return mProviderMap.dumpProvider(fd, pw, name, args, opti, dumpAll); 11940 } 11941 11942 static class ItemMatcher { 11943 ArrayList<ComponentName> components; 11944 ArrayList<String> strings; 11945 ArrayList<Integer> objects; 11946 boolean all; 11947 11948 ItemMatcher() { 11949 all = true; 11950 } 11951 11952 void build(String name) { 11953 ComponentName componentName = ComponentName.unflattenFromString(name); 11954 if (componentName != null) { 11955 if (components == null) { 11956 components = new ArrayList<ComponentName>(); 11957 } 11958 components.add(componentName); 11959 all = false; 11960 } else { 11961 int objectId = 0; 11962 // Not a '/' separated full component name; maybe an object ID? 11963 try { 11964 objectId = Integer.parseInt(name, 16); 11965 if (objects == null) { 11966 objects = new ArrayList<Integer>(); 11967 } 11968 objects.add(objectId); 11969 all = false; 11970 } catch (RuntimeException e) { 11971 // Not an integer; just do string match. 11972 if (strings == null) { 11973 strings = new ArrayList<String>(); 11974 } 11975 strings.add(name); 11976 all = false; 11977 } 11978 } 11979 } 11980 11981 int build(String[] args, int opti) { 11982 for (; opti<args.length; opti++) { 11983 String name = args[opti]; 11984 if ("--".equals(name)) { 11985 return opti+1; 11986 } 11987 build(name); 11988 } 11989 return opti; 11990 } 11991 11992 boolean match(Object object, ComponentName comp) { 11993 if (all) { 11994 return true; 11995 } 11996 if (components != null) { 11997 for (int i=0; i<components.size(); i++) { 11998 if (components.get(i).equals(comp)) { 11999 return true; 12000 } 12001 } 12002 } 12003 if (objects != null) { 12004 for (int i=0; i<objects.size(); i++) { 12005 if (System.identityHashCode(object) == objects.get(i)) { 12006 return true; 12007 } 12008 } 12009 } 12010 if (strings != null) { 12011 String flat = comp.flattenToString(); 12012 for (int i=0; i<strings.size(); i++) { 12013 if (flat.contains(strings.get(i))) { 12014 return true; 12015 } 12016 } 12017 } 12018 return false; 12019 } 12020 } 12021 12022 /** 12023 * There are three things that cmd can be: 12024 * - a flattened component name that matches an existing activity 12025 * - the cmd arg isn't the flattened component name of an existing activity: 12026 * dump all activity whose component contains the cmd as a substring 12027 * - A hex number of the ActivityRecord object instance. 12028 */ 12029 protected boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name, String[] args, 12030 int opti, boolean dumpAll) { 12031 ArrayList<ActivityRecord> activities; 12032 12033 synchronized (this) { 12034 activities = mStackSupervisor.getDumpActivitiesLocked(name); 12035 } 12036 12037 if (activities.size() <= 0) { 12038 return false; 12039 } 12040 12041 String[] newArgs = new String[args.length - opti]; 12042 System.arraycopy(args, opti, newArgs, 0, args.length - opti); 12043 12044 TaskRecord lastTask = null; 12045 boolean needSep = false; 12046 for (int i=activities.size()-1; i>=0; i--) { 12047 ActivityRecord r = activities.get(i); 12048 if (needSep) { 12049 pw.println(); 12050 } 12051 needSep = true; 12052 synchronized (this) { 12053 if (lastTask != r.task) { 12054 lastTask = r.task; 12055 pw.print("TASK "); pw.print(lastTask.affinity); 12056 pw.print(" id="); pw.println(lastTask.taskId); 12057 if (dumpAll) { 12058 lastTask.dump(pw, " "); 12059 } 12060 } 12061 } 12062 dumpActivity(" ", fd, pw, activities.get(i), newArgs, dumpAll); 12063 } 12064 return true; 12065 } 12066 12067 /** 12068 * Invokes IApplicationThread.dumpActivity() on the thread of the specified activity if 12069 * there is a thread associated with the activity. 12070 */ 12071 private void dumpActivity(String prefix, FileDescriptor fd, PrintWriter pw, 12072 final ActivityRecord r, String[] args, boolean dumpAll) { 12073 String innerPrefix = prefix + " "; 12074 synchronized (this) { 12075 pw.print(prefix); pw.print("ACTIVITY "); pw.print(r.shortComponentName); 12076 pw.print(" "); pw.print(Integer.toHexString(System.identityHashCode(r))); 12077 pw.print(" pid="); 12078 if (r.app != null) pw.println(r.app.pid); 12079 else pw.println("(not running)"); 12080 if (dumpAll) { 12081 r.dump(pw, innerPrefix); 12082 } 12083 } 12084 if (r.app != null && r.app.thread != null) { 12085 // flush anything that is already in the PrintWriter since the thread is going 12086 // to write to the file descriptor directly 12087 pw.flush(); 12088 try { 12089 TransferPipe tp = new TransferPipe(); 12090 try { 12091 r.app.thread.dumpActivity(tp.getWriteFd().getFileDescriptor(), 12092 r.appToken, innerPrefix, args); 12093 tp.go(fd); 12094 } finally { 12095 tp.kill(); 12096 } 12097 } catch (IOException e) { 12098 pw.println(innerPrefix + "Failure while dumping the activity: " + e); 12099 } catch (RemoteException e) { 12100 pw.println(innerPrefix + "Got a RemoteException while dumping the activity"); 12101 } 12102 } 12103 } 12104 12105 void dumpBroadcastsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12106 int opti, boolean dumpAll, String dumpPackage) { 12107 boolean needSep = false; 12108 boolean onlyHistory = false; 12109 boolean printedAnything = false; 12110 12111 if ("history".equals(dumpPackage)) { 12112 if (opti < args.length && "-s".equals(args[opti])) { 12113 dumpAll = false; 12114 } 12115 onlyHistory = true; 12116 dumpPackage = null; 12117 } 12118 12119 pw.println("ACTIVITY MANAGER BROADCAST STATE (dumpsys activity broadcasts)"); 12120 if (!onlyHistory && dumpAll) { 12121 if (mRegisteredReceivers.size() > 0) { 12122 boolean printed = false; 12123 Iterator it = mRegisteredReceivers.values().iterator(); 12124 while (it.hasNext()) { 12125 ReceiverList r = (ReceiverList)it.next(); 12126 if (dumpPackage != null && (r.app == null || 12127 !dumpPackage.equals(r.app.info.packageName))) { 12128 continue; 12129 } 12130 if (!printed) { 12131 pw.println(" Registered Receivers:"); 12132 needSep = true; 12133 printed = true; 12134 printedAnything = true; 12135 } 12136 pw.print(" * "); pw.println(r); 12137 r.dump(pw, " "); 12138 } 12139 } 12140 12141 if (mReceiverResolver.dump(pw, needSep ? 12142 "\n Receiver Resolver Table:" : " Receiver Resolver Table:", 12143 " ", dumpPackage, false)) { 12144 needSep = true; 12145 printedAnything = true; 12146 } 12147 } 12148 12149 for (BroadcastQueue q : mBroadcastQueues) { 12150 needSep = q.dumpLocked(fd, pw, args, opti, dumpAll, dumpPackage, needSep); 12151 printedAnything |= needSep; 12152 } 12153 12154 needSep = true; 12155 12156 if (!onlyHistory && mStickyBroadcasts != null && dumpPackage == null) { 12157 for (int user=0; user<mStickyBroadcasts.size(); user++) { 12158 if (needSep) { 12159 pw.println(); 12160 } 12161 needSep = true; 12162 printedAnything = true; 12163 pw.print(" Sticky broadcasts for user "); 12164 pw.print(mStickyBroadcasts.keyAt(user)); pw.println(":"); 12165 StringBuilder sb = new StringBuilder(128); 12166 for (Map.Entry<String, ArrayList<Intent>> ent 12167 : mStickyBroadcasts.valueAt(user).entrySet()) { 12168 pw.print(" * Sticky action "); pw.print(ent.getKey()); 12169 if (dumpAll) { 12170 pw.println(":"); 12171 ArrayList<Intent> intents = ent.getValue(); 12172 final int N = intents.size(); 12173 for (int i=0; i<N; i++) { 12174 sb.setLength(0); 12175 sb.append(" Intent: "); 12176 intents.get(i).toShortString(sb, false, true, false, false); 12177 pw.println(sb.toString()); 12178 Bundle bundle = intents.get(i).getExtras(); 12179 if (bundle != null) { 12180 pw.print(" "); 12181 pw.println(bundle.toString()); 12182 } 12183 } 12184 } else { 12185 pw.println(""); 12186 } 12187 } 12188 } 12189 } 12190 12191 if (!onlyHistory && dumpAll) { 12192 pw.println(); 12193 for (BroadcastQueue queue : mBroadcastQueues) { 12194 pw.println(" mBroadcastsScheduled [" + queue.mQueueName + "]=" 12195 + queue.mBroadcastsScheduled); 12196 } 12197 pw.println(" mHandler:"); 12198 mHandler.dump(new PrintWriterPrinter(pw), " "); 12199 needSep = true; 12200 printedAnything = true; 12201 } 12202 12203 if (!printedAnything) { 12204 pw.println(" (nothing)"); 12205 } 12206 } 12207 12208 void dumpProvidersLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12209 int opti, boolean dumpAll, String dumpPackage) { 12210 boolean needSep; 12211 boolean printedAnything = false; 12212 12213 ItemMatcher matcher = new ItemMatcher(); 12214 matcher.build(args, opti); 12215 12216 pw.println("ACTIVITY MANAGER CONTENT PROVIDERS (dumpsys activity providers)"); 12217 12218 needSep = mProviderMap.dumpProvidersLocked(pw, dumpAll, dumpPackage); 12219 printedAnything |= needSep; 12220 12221 if (mLaunchingProviders.size() > 0) { 12222 boolean printed = false; 12223 for (int i=mLaunchingProviders.size()-1; i>=0; i--) { 12224 ContentProviderRecord r = mLaunchingProviders.get(i); 12225 if (dumpPackage != null && !dumpPackage.equals(r.name.getPackageName())) { 12226 continue; 12227 } 12228 if (!printed) { 12229 if (needSep) pw.println(); 12230 needSep = true; 12231 pw.println(" Launching content providers:"); 12232 printed = true; 12233 printedAnything = true; 12234 } 12235 pw.print(" Launching #"); pw.print(i); pw.print(": "); 12236 pw.println(r); 12237 } 12238 } 12239 12240 if (mGrantedUriPermissions.size() > 0) { 12241 boolean printed = false; 12242 int dumpUid = -2; 12243 if (dumpPackage != null) { 12244 try { 12245 dumpUid = mContext.getPackageManager().getPackageUid(dumpPackage, 0); 12246 } catch (NameNotFoundException e) { 12247 dumpUid = -1; 12248 } 12249 } 12250 for (int i=0; i<mGrantedUriPermissions.size(); i++) { 12251 int uid = mGrantedUriPermissions.keyAt(i); 12252 if (dumpUid >= -1 && UserHandle.getAppId(uid) != dumpUid) { 12253 continue; 12254 } 12255 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 12256 if (!printed) { 12257 if (needSep) pw.println(); 12258 needSep = true; 12259 pw.println(" Granted Uri Permissions:"); 12260 printed = true; 12261 printedAnything = true; 12262 } 12263 pw.print(" * UID "); pw.print(uid); pw.println(" holds:"); 12264 for (UriPermission perm : perms.values()) { 12265 pw.print(" "); pw.println(perm); 12266 if (dumpAll) { 12267 perm.dump(pw, " "); 12268 } 12269 } 12270 } 12271 } 12272 12273 if (!printedAnything) { 12274 pw.println(" (nothing)"); 12275 } 12276 } 12277 12278 void dumpPendingIntentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12279 int opti, boolean dumpAll, String dumpPackage) { 12280 boolean printed = false; 12281 12282 pw.println("ACTIVITY MANAGER PENDING INTENTS (dumpsys activity intents)"); 12283 12284 if (mIntentSenderRecords.size() > 0) { 12285 Iterator<WeakReference<PendingIntentRecord>> it 12286 = mIntentSenderRecords.values().iterator(); 12287 while (it.hasNext()) { 12288 WeakReference<PendingIntentRecord> ref = it.next(); 12289 PendingIntentRecord rec = ref != null ? ref.get(): null; 12290 if (dumpPackage != null && (rec == null 12291 || !dumpPackage.equals(rec.key.packageName))) { 12292 continue; 12293 } 12294 printed = true; 12295 if (rec != null) { 12296 pw.print(" * "); pw.println(rec); 12297 if (dumpAll) { 12298 rec.dump(pw, " "); 12299 } 12300 } else { 12301 pw.print(" * "); pw.println(ref); 12302 } 12303 } 12304 } 12305 12306 if (!printed) { 12307 pw.println(" (nothing)"); 12308 } 12309 } 12310 12311 private static final int dumpProcessList(PrintWriter pw, 12312 ActivityManagerService service, List list, 12313 String prefix, String normalLabel, String persistentLabel, 12314 String dumpPackage) { 12315 int numPers = 0; 12316 final int N = list.size()-1; 12317 for (int i=N; i>=0; i--) { 12318 ProcessRecord r = (ProcessRecord)list.get(i); 12319 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 12320 continue; 12321 } 12322 pw.println(String.format("%s%s #%2d: %s", 12323 prefix, (r.persistent ? persistentLabel : normalLabel), 12324 i, r.toString())); 12325 if (r.persistent) { 12326 numPers++; 12327 } 12328 } 12329 return numPers; 12330 } 12331 12332 private static final boolean dumpProcessOomList(PrintWriter pw, 12333 ActivityManagerService service, List<ProcessRecord> origList, 12334 String prefix, String normalLabel, String persistentLabel, 12335 boolean inclDetails, String dumpPackage) { 12336 12337 ArrayList<Pair<ProcessRecord, Integer>> list 12338 = new ArrayList<Pair<ProcessRecord, Integer>>(origList.size()); 12339 for (int i=0; i<origList.size(); i++) { 12340 ProcessRecord r = origList.get(i); 12341 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 12342 continue; 12343 } 12344 list.add(new Pair<ProcessRecord, Integer>(origList.get(i), i)); 12345 } 12346 12347 if (list.size() <= 0) { 12348 return false; 12349 } 12350 12351 Comparator<Pair<ProcessRecord, Integer>> comparator 12352 = new Comparator<Pair<ProcessRecord, Integer>>() { 12353 @Override 12354 public int compare(Pair<ProcessRecord, Integer> object1, 12355 Pair<ProcessRecord, Integer> object2) { 12356 if (object1.first.setAdj != object2.first.setAdj) { 12357 return object1.first.setAdj > object2.first.setAdj ? -1 : 1; 12358 } 12359 if (object1.second.intValue() != object2.second.intValue()) { 12360 return object1.second.intValue() > object2.second.intValue() ? -1 : 1; 12361 } 12362 return 0; 12363 } 12364 }; 12365 12366 Collections.sort(list, comparator); 12367 12368 final long curRealtime = SystemClock.elapsedRealtime(); 12369 final long realtimeSince = curRealtime - service.mLastPowerCheckRealtime; 12370 final long curUptime = SystemClock.uptimeMillis(); 12371 final long uptimeSince = curUptime - service.mLastPowerCheckUptime; 12372 12373 for (int i=list.size()-1; i>=0; i--) { 12374 ProcessRecord r = list.get(i).first; 12375 String oomAdj = ProcessList.makeOomAdjString(r.setAdj); 12376 char schedGroup; 12377 switch (r.setSchedGroup) { 12378 case Process.THREAD_GROUP_BG_NONINTERACTIVE: 12379 schedGroup = 'B'; 12380 break; 12381 case Process.THREAD_GROUP_DEFAULT: 12382 schedGroup = 'F'; 12383 break; 12384 default: 12385 schedGroup = '?'; 12386 break; 12387 } 12388 char foreground; 12389 if (r.foregroundActivities) { 12390 foreground = 'A'; 12391 } else if (r.foregroundServices) { 12392 foreground = 'S'; 12393 } else { 12394 foreground = ' '; 12395 } 12396 String procState = ProcessList.makeProcStateString(r.curProcState); 12397 pw.print(prefix); 12398 pw.print(r.persistent ? persistentLabel : normalLabel); 12399 pw.print(" #"); 12400 int num = (origList.size()-1)-list.get(i).second; 12401 if (num < 10) pw.print(' '); 12402 pw.print(num); 12403 pw.print(": "); 12404 pw.print(oomAdj); 12405 pw.print(' '); 12406 pw.print(schedGroup); 12407 pw.print('/'); 12408 pw.print(foreground); 12409 pw.print('/'); 12410 pw.print(procState); 12411 pw.print(" trm:"); 12412 if (r.trimMemoryLevel < 10) pw.print(' '); 12413 pw.print(r.trimMemoryLevel); 12414 pw.print(' '); 12415 pw.print(r.toShortString()); 12416 pw.print(" ("); 12417 pw.print(r.adjType); 12418 pw.println(')'); 12419 if (r.adjSource != null || r.adjTarget != null) { 12420 pw.print(prefix); 12421 pw.print(" "); 12422 if (r.adjTarget instanceof ComponentName) { 12423 pw.print(((ComponentName)r.adjTarget).flattenToShortString()); 12424 } else if (r.adjTarget != null) { 12425 pw.print(r.adjTarget.toString()); 12426 } else { 12427 pw.print("{null}"); 12428 } 12429 pw.print("<="); 12430 if (r.adjSource instanceof ProcessRecord) { 12431 pw.print("Proc{"); 12432 pw.print(((ProcessRecord)r.adjSource).toShortString()); 12433 pw.println("}"); 12434 } else if (r.adjSource != null) { 12435 pw.println(r.adjSource.toString()); 12436 } else { 12437 pw.println("{null}"); 12438 } 12439 } 12440 if (inclDetails) { 12441 pw.print(prefix); 12442 pw.print(" "); 12443 pw.print("oom: max="); pw.print(r.maxAdj); 12444 pw.print(" curRaw="); pw.print(r.curRawAdj); 12445 pw.print(" setRaw="); pw.print(r.setRawAdj); 12446 pw.print(" cur="); pw.print(r.curAdj); 12447 pw.print(" set="); pw.println(r.setAdj); 12448 pw.print(prefix); 12449 pw.print(" "); 12450 pw.print("state: cur="); pw.print(ProcessList.makeProcStateString(r.curProcState)); 12451 pw.print(" set="); pw.print(ProcessList.makeProcStateString(r.setProcState)); 12452 pw.print(" lastPss="); pw.print(r.lastPss); 12453 pw.print(" lastCachedPss="); pw.println(r.lastCachedPss); 12454 pw.print(prefix); 12455 pw.print(" "); 12456 pw.print("cached="); pw.print(r.cached); 12457 pw.print(" empty="); pw.print(r.empty); 12458 pw.print(" hasAboveClient="); pw.println(r.hasAboveClient); 12459 12460 if (r.setProcState >= ActivityManager.PROCESS_STATE_SERVICE) { 12461 if (r.lastWakeTime != 0) { 12462 long wtime; 12463 BatteryStatsImpl stats = service.mBatteryStatsService.getActiveStatistics(); 12464 synchronized (stats) { 12465 wtime = stats.getProcessWakeTime(r.info.uid, 12466 r.pid, curRealtime); 12467 } 12468 long timeUsed = wtime - r.lastWakeTime; 12469 pw.print(prefix); 12470 pw.print(" "); 12471 pw.print("keep awake over "); 12472 TimeUtils.formatDuration(realtimeSince, pw); 12473 pw.print(" used "); 12474 TimeUtils.formatDuration(timeUsed, pw); 12475 pw.print(" ("); 12476 pw.print((timeUsed*100)/realtimeSince); 12477 pw.println("%)"); 12478 } 12479 if (r.lastCpuTime != 0) { 12480 long timeUsed = r.curCpuTime - r.lastCpuTime; 12481 pw.print(prefix); 12482 pw.print(" "); 12483 pw.print("run cpu over "); 12484 TimeUtils.formatDuration(uptimeSince, pw); 12485 pw.print(" used "); 12486 TimeUtils.formatDuration(timeUsed, pw); 12487 pw.print(" ("); 12488 pw.print((timeUsed*100)/uptimeSince); 12489 pw.println("%)"); 12490 } 12491 } 12492 } 12493 } 12494 return true; 12495 } 12496 12497 ArrayList<ProcessRecord> collectProcesses(PrintWriter pw, int start, String[] args) { 12498 ArrayList<ProcessRecord> procs; 12499 synchronized (this) { 12500 if (args != null && args.length > start 12501 && args[start].charAt(0) != '-') { 12502 procs = new ArrayList<ProcessRecord>(); 12503 int pid = -1; 12504 try { 12505 pid = Integer.parseInt(args[start]); 12506 } catch (NumberFormatException e) { 12507 } 12508 for (int i=mLruProcesses.size()-1; i>=0; i--) { 12509 ProcessRecord proc = mLruProcesses.get(i); 12510 if (proc.pid == pid) { 12511 procs.add(proc); 12512 } else if (proc.processName.equals(args[start])) { 12513 procs.add(proc); 12514 } 12515 } 12516 if (procs.size() <= 0) { 12517 return null; 12518 } 12519 } else { 12520 procs = new ArrayList<ProcessRecord>(mLruProcesses); 12521 } 12522 } 12523 return procs; 12524 } 12525 12526 final void dumpGraphicsHardwareUsage(FileDescriptor fd, 12527 PrintWriter pw, String[] args) { 12528 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 12529 if (procs == null) { 12530 pw.println("No process found for: " + args[0]); 12531 return; 12532 } 12533 12534 long uptime = SystemClock.uptimeMillis(); 12535 long realtime = SystemClock.elapsedRealtime(); 12536 pw.println("Applications Graphics Acceleration Info:"); 12537 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 12538 12539 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12540 ProcessRecord r = procs.get(i); 12541 if (r.thread != null) { 12542 pw.println("\n** Graphics info for pid " + r.pid + " [" + r.processName + "] **"); 12543 pw.flush(); 12544 try { 12545 TransferPipe tp = new TransferPipe(); 12546 try { 12547 r.thread.dumpGfxInfo(tp.getWriteFd().getFileDescriptor(), args); 12548 tp.go(fd); 12549 } finally { 12550 tp.kill(); 12551 } 12552 } catch (IOException e) { 12553 pw.println("Failure while dumping the app: " + r); 12554 pw.flush(); 12555 } catch (RemoteException e) { 12556 pw.println("Got a RemoteException while dumping the app " + r); 12557 pw.flush(); 12558 } 12559 } 12560 } 12561 } 12562 12563 final void dumpDbInfo(FileDescriptor fd, PrintWriter pw, String[] args) { 12564 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 12565 if (procs == null) { 12566 pw.println("No process found for: " + args[0]); 12567 return; 12568 } 12569 12570 pw.println("Applications Database Info:"); 12571 12572 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12573 ProcessRecord r = procs.get(i); 12574 if (r.thread != null) { 12575 pw.println("\n** Database info for pid " + r.pid + " [" + r.processName + "] **"); 12576 pw.flush(); 12577 try { 12578 TransferPipe tp = new TransferPipe(); 12579 try { 12580 r.thread.dumpDbInfo(tp.getWriteFd().getFileDescriptor(), args); 12581 tp.go(fd); 12582 } finally { 12583 tp.kill(); 12584 } 12585 } catch (IOException e) { 12586 pw.println("Failure while dumping the app: " + r); 12587 pw.flush(); 12588 } catch (RemoteException e) { 12589 pw.println("Got a RemoteException while dumping the app " + r); 12590 pw.flush(); 12591 } 12592 } 12593 } 12594 } 12595 12596 final static class MemItem { 12597 final boolean isProc; 12598 final String label; 12599 final String shortLabel; 12600 final long pss; 12601 final int id; 12602 final boolean hasActivities; 12603 ArrayList<MemItem> subitems; 12604 12605 public MemItem(String _label, String _shortLabel, long _pss, int _id, 12606 boolean _hasActivities) { 12607 isProc = true; 12608 label = _label; 12609 shortLabel = _shortLabel; 12610 pss = _pss; 12611 id = _id; 12612 hasActivities = _hasActivities; 12613 } 12614 12615 public MemItem(String _label, String _shortLabel, long _pss, int _id) { 12616 isProc = false; 12617 label = _label; 12618 shortLabel = _shortLabel; 12619 pss = _pss; 12620 id = _id; 12621 hasActivities = false; 12622 } 12623 } 12624 12625 static final void dumpMemItems(PrintWriter pw, String prefix, String tag, 12626 ArrayList<MemItem> items, boolean sort, boolean isCompact) { 12627 if (sort && !isCompact) { 12628 Collections.sort(items, new Comparator<MemItem>() { 12629 @Override 12630 public int compare(MemItem lhs, MemItem rhs) { 12631 if (lhs.pss < rhs.pss) { 12632 return 1; 12633 } else if (lhs.pss > rhs.pss) { 12634 return -1; 12635 } 12636 return 0; 12637 } 12638 }); 12639 } 12640 12641 for (int i=0; i<items.size(); i++) { 12642 MemItem mi = items.get(i); 12643 if (!isCompact) { 12644 pw.print(prefix); pw.printf("%7d kB: ", mi.pss); pw.println(mi.label); 12645 } else if (mi.isProc) { 12646 pw.print("proc,"); pw.print(tag); pw.print(","); pw.print(mi.shortLabel); 12647 pw.print(","); pw.print(mi.id); pw.print(","); pw.print(mi.pss); 12648 pw.println(mi.hasActivities ? ",a" : ",e"); 12649 } else { 12650 pw.print(tag); pw.print(","); pw.print(mi.shortLabel); pw.print(","); 12651 pw.println(mi.pss); 12652 } 12653 if (mi.subitems != null) { 12654 dumpMemItems(pw, prefix + " ", mi.shortLabel, mi.subitems, 12655 true, isCompact); 12656 } 12657 } 12658 } 12659 12660 // These are in KB. 12661 static final long[] DUMP_MEM_BUCKETS = new long[] { 12662 5*1024, 7*1024, 10*1024, 15*1024, 20*1024, 30*1024, 40*1024, 80*1024, 12663 120*1024, 160*1024, 200*1024, 12664 250*1024, 300*1024, 350*1024, 400*1024, 500*1024, 600*1024, 800*1024, 12665 1*1024*1024, 2*1024*1024, 5*1024*1024, 10*1024*1024, 20*1024*1024 12666 }; 12667 12668 static final void appendMemBucket(StringBuilder out, long memKB, String label, 12669 boolean stackLike) { 12670 int start = label.lastIndexOf('.'); 12671 if (start >= 0) start++; 12672 else start = 0; 12673 int end = label.length(); 12674 for (int i=0; i<DUMP_MEM_BUCKETS.length; i++) { 12675 if (DUMP_MEM_BUCKETS[i] >= memKB) { 12676 long bucket = DUMP_MEM_BUCKETS[i]/1024; 12677 out.append(bucket); 12678 out.append(stackLike ? "MB." : "MB "); 12679 out.append(label, start, end); 12680 return; 12681 } 12682 } 12683 out.append(memKB/1024); 12684 out.append(stackLike ? "MB." : "MB "); 12685 out.append(label, start, end); 12686 } 12687 12688 static final int[] DUMP_MEM_OOM_ADJ = new int[] { 12689 ProcessList.NATIVE_ADJ, 12690 ProcessList.SYSTEM_ADJ, ProcessList.PERSISTENT_PROC_ADJ, ProcessList.FOREGROUND_APP_ADJ, 12691 ProcessList.VISIBLE_APP_ADJ, ProcessList.PERCEPTIBLE_APP_ADJ, 12692 ProcessList.BACKUP_APP_ADJ, ProcessList.HEAVY_WEIGHT_APP_ADJ, 12693 ProcessList.SERVICE_ADJ, ProcessList.HOME_APP_ADJ, 12694 ProcessList.PREVIOUS_APP_ADJ, ProcessList.SERVICE_B_ADJ, ProcessList.CACHED_APP_MAX_ADJ 12695 }; 12696 static final String[] DUMP_MEM_OOM_LABEL = new String[] { 12697 "Native", 12698 "System", "Persistent", "Foreground", 12699 "Visible", "Perceptible", 12700 "Heavy Weight", "Backup", 12701 "A Services", "Home", 12702 "Previous", "B Services", "Cached" 12703 }; 12704 static final String[] DUMP_MEM_OOM_COMPACT_LABEL = new String[] { 12705 "native", 12706 "sys", "pers", "fore", 12707 "vis", "percept", 12708 "heavy", "backup", 12709 "servicea", "home", 12710 "prev", "serviceb", "cached" 12711 }; 12712 12713 private final void dumpApplicationMemoryUsageHeader(PrintWriter pw, long uptime, 12714 long realtime, boolean isCheckinRequest, boolean isCompact) { 12715 if (isCheckinRequest || isCompact) { 12716 // short checkin version 12717 pw.print("time,"); pw.print(uptime); pw.print(","); pw.println(realtime); 12718 } else { 12719 pw.println("Applications Memory Usage (kB):"); 12720 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 12721 } 12722 } 12723 12724 final void dumpApplicationMemoryUsage(FileDescriptor fd, 12725 PrintWriter pw, String prefix, String[] args, boolean brief, PrintWriter categoryPw) { 12726 boolean dumpDetails = false; 12727 boolean dumpFullDetails = false; 12728 boolean dumpDalvik = false; 12729 boolean oomOnly = false; 12730 boolean isCompact = false; 12731 boolean localOnly = false; 12732 12733 int opti = 0; 12734 while (opti < args.length) { 12735 String opt = args[opti]; 12736 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 12737 break; 12738 } 12739 opti++; 12740 if ("-a".equals(opt)) { 12741 dumpDetails = true; 12742 dumpFullDetails = true; 12743 dumpDalvik = true; 12744 } else if ("-d".equals(opt)) { 12745 dumpDalvik = true; 12746 } else if ("-c".equals(opt)) { 12747 isCompact = true; 12748 } else if ("--oom".equals(opt)) { 12749 oomOnly = true; 12750 } else if ("--local".equals(opt)) { 12751 localOnly = true; 12752 } else if ("-h".equals(opt)) { 12753 pw.println("meminfo dump options: [-a] [-d] [-c] [--oom] [process]"); 12754 pw.println(" -a: include all available information for each process."); 12755 pw.println(" -d: include dalvik details when dumping process details."); 12756 pw.println(" -c: dump in a compact machine-parseable representation."); 12757 pw.println(" --oom: only show processes organized by oom adj."); 12758 pw.println(" --local: only collect details locally, don't call process."); 12759 pw.println("If [process] is specified it can be the name or "); 12760 pw.println("pid of a specific process to dump."); 12761 return; 12762 } else { 12763 pw.println("Unknown argument: " + opt + "; use -h for help"); 12764 } 12765 } 12766 12767 final boolean isCheckinRequest = scanArgs(args, "--checkin"); 12768 long uptime = SystemClock.uptimeMillis(); 12769 long realtime = SystemClock.elapsedRealtime(); 12770 final long[] tmpLong = new long[1]; 12771 12772 ArrayList<ProcessRecord> procs = collectProcesses(pw, opti, args); 12773 if (procs == null) { 12774 // No Java processes. Maybe they want to print a native process. 12775 if (args != null && args.length > opti 12776 && args[opti].charAt(0) != '-') { 12777 ArrayList<ProcessCpuTracker.Stats> nativeProcs 12778 = new ArrayList<ProcessCpuTracker.Stats>(); 12779 updateCpuStatsNow(); 12780 int findPid = -1; 12781 try { 12782 findPid = Integer.parseInt(args[opti]); 12783 } catch (NumberFormatException e) { 12784 } 12785 synchronized (mProcessCpuThread) { 12786 final int N = mProcessCpuTracker.countStats(); 12787 for (int i=0; i<N; i++) { 12788 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 12789 if (st.pid == findPid || (st.baseName != null 12790 && st.baseName.equals(args[opti]))) { 12791 nativeProcs.add(st); 12792 } 12793 } 12794 } 12795 if (nativeProcs.size() > 0) { 12796 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, 12797 isCompact); 12798 Debug.MemoryInfo mi = null; 12799 for (int i = nativeProcs.size() - 1 ; i >= 0 ; i--) { 12800 final ProcessCpuTracker.Stats r = nativeProcs.get(i); 12801 final int pid = r.pid; 12802 if (!isCheckinRequest && dumpDetails) { 12803 pw.println("\n** MEMINFO in pid " + pid + " [" + r.baseName + "] **"); 12804 } 12805 if (mi == null) { 12806 mi = new Debug.MemoryInfo(); 12807 } 12808 if (dumpDetails || (!brief && !oomOnly)) { 12809 Debug.getMemoryInfo(pid, mi); 12810 } else { 12811 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 12812 mi.dalvikPrivateDirty = (int)tmpLong[0]; 12813 } 12814 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 12815 dumpDalvik, pid, r.baseName, 0, 0, 0, 0, 0, 0); 12816 if (isCheckinRequest) { 12817 pw.println(); 12818 } 12819 } 12820 return; 12821 } 12822 } 12823 pw.println("No process found for: " + args[opti]); 12824 return; 12825 } 12826 12827 if (!brief && !oomOnly && (procs.size() == 1 || isCheckinRequest)) { 12828 dumpDetails = true; 12829 } 12830 12831 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, isCompact); 12832 12833 String[] innerArgs = new String[args.length-opti]; 12834 System.arraycopy(args, opti, innerArgs, 0, args.length-opti); 12835 12836 ArrayList<MemItem> procMems = new ArrayList<MemItem>(); 12837 final SparseArray<MemItem> procMemsMap = new SparseArray<MemItem>(); 12838 long nativePss=0, dalvikPss=0, otherPss=0; 12839 long[] miscPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 12840 12841 long oomPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 12842 ArrayList<MemItem>[] oomProcs = (ArrayList<MemItem>[]) 12843 new ArrayList[DUMP_MEM_OOM_LABEL.length]; 12844 12845 long totalPss = 0; 12846 long cachedPss = 0; 12847 12848 Debug.MemoryInfo mi = null; 12849 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12850 final ProcessRecord r = procs.get(i); 12851 final IApplicationThread thread; 12852 final int pid; 12853 final int oomAdj; 12854 final boolean hasActivities; 12855 synchronized (this) { 12856 thread = r.thread; 12857 pid = r.pid; 12858 oomAdj = r.getSetAdjWithServices(); 12859 hasActivities = r.activities.size() > 0; 12860 } 12861 if (thread != null) { 12862 if (!isCheckinRequest && dumpDetails) { 12863 pw.println("\n** MEMINFO in pid " + pid + " [" + r.processName + "] **"); 12864 } 12865 if (mi == null) { 12866 mi = new Debug.MemoryInfo(); 12867 } 12868 if (dumpDetails || (!brief && !oomOnly)) { 12869 Debug.getMemoryInfo(pid, mi); 12870 } else { 12871 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 12872 mi.dalvikPrivateDirty = (int)tmpLong[0]; 12873 } 12874 if (dumpDetails) { 12875 if (localOnly) { 12876 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 12877 dumpDalvik, pid, r.processName, 0, 0, 0, 0, 0, 0); 12878 if (isCheckinRequest) { 12879 pw.println(); 12880 } 12881 } else { 12882 try { 12883 pw.flush(); 12884 thread.dumpMemInfo(fd, mi, isCheckinRequest, dumpFullDetails, 12885 dumpDalvik, innerArgs); 12886 } catch (RemoteException e) { 12887 if (!isCheckinRequest) { 12888 pw.println("Got RemoteException!"); 12889 pw.flush(); 12890 } 12891 } 12892 } 12893 } 12894 12895 final long myTotalPss = mi.getTotalPss(); 12896 final long myTotalUss = mi.getTotalUss(); 12897 12898 synchronized (this) { 12899 if (r.thread != null && oomAdj == r.getSetAdjWithServices()) { 12900 // Record this for posterity if the process has been stable. 12901 r.baseProcessTracker.addPss(myTotalPss, myTotalUss, true, r.pkgList); 12902 } 12903 } 12904 12905 if (!isCheckinRequest && mi != null) { 12906 totalPss += myTotalPss; 12907 MemItem pssItem = new MemItem(r.processName + " (pid " + pid + 12908 (hasActivities ? " / activities)" : ")"), 12909 r.processName, myTotalPss, pid, hasActivities); 12910 procMems.add(pssItem); 12911 procMemsMap.put(pid, pssItem); 12912 12913 nativePss += mi.nativePss; 12914 dalvikPss += mi.dalvikPss; 12915 otherPss += mi.otherPss; 12916 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 12917 long mem = mi.getOtherPss(j); 12918 miscPss[j] += mem; 12919 otherPss -= mem; 12920 } 12921 12922 if (oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 12923 cachedPss += myTotalPss; 12924 } 12925 12926 for (int oomIndex=0; oomIndex<oomPss.length; oomIndex++) { 12927 if (oomAdj <= DUMP_MEM_OOM_ADJ[oomIndex] 12928 || oomIndex == (oomPss.length-1)) { 12929 oomPss[oomIndex] += myTotalPss; 12930 if (oomProcs[oomIndex] == null) { 12931 oomProcs[oomIndex] = new ArrayList<MemItem>(); 12932 } 12933 oomProcs[oomIndex].add(pssItem); 12934 break; 12935 } 12936 } 12937 } 12938 } 12939 } 12940 12941 long nativeProcTotalPss = 0; 12942 12943 if (!isCheckinRequest && procs.size() > 1) { 12944 // If we are showing aggregations, also look for native processes to 12945 // include so that our aggregations are more accurate. 12946 updateCpuStatsNow(); 12947 synchronized (mProcessCpuThread) { 12948 final int N = mProcessCpuTracker.countStats(); 12949 for (int i=0; i<N; i++) { 12950 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 12951 if (st.vsize > 0 && procMemsMap.indexOfKey(st.pid) < 0) { 12952 if (mi == null) { 12953 mi = new Debug.MemoryInfo(); 12954 } 12955 if (!brief && !oomOnly) { 12956 Debug.getMemoryInfo(st.pid, mi); 12957 } else { 12958 mi.nativePss = (int)Debug.getPss(st.pid, tmpLong); 12959 mi.nativePrivateDirty = (int)tmpLong[0]; 12960 } 12961 12962 final long myTotalPss = mi.getTotalPss(); 12963 totalPss += myTotalPss; 12964 nativeProcTotalPss += myTotalPss; 12965 12966 MemItem pssItem = new MemItem(st.name + " (pid " + st.pid + ")", 12967 st.name, myTotalPss, st.pid, false); 12968 procMems.add(pssItem); 12969 12970 nativePss += mi.nativePss; 12971 dalvikPss += mi.dalvikPss; 12972 otherPss += mi.otherPss; 12973 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 12974 long mem = mi.getOtherPss(j); 12975 miscPss[j] += mem; 12976 otherPss -= mem; 12977 } 12978 oomPss[0] += myTotalPss; 12979 if (oomProcs[0] == null) { 12980 oomProcs[0] = new ArrayList<MemItem>(); 12981 } 12982 oomProcs[0].add(pssItem); 12983 } 12984 } 12985 } 12986 12987 ArrayList<MemItem> catMems = new ArrayList<MemItem>(); 12988 12989 catMems.add(new MemItem("Native", "Native", nativePss, -1)); 12990 catMems.add(new MemItem("Dalvik", "Dalvik", dalvikPss, -2)); 12991 catMems.add(new MemItem("Unknown", "Unknown", otherPss, -3)); 12992 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 12993 String label = Debug.MemoryInfo.getOtherLabel(j); 12994 catMems.add(new MemItem(label, label, miscPss[j], j)); 12995 } 12996 12997 ArrayList<MemItem> oomMems = new ArrayList<MemItem>(); 12998 for (int j=0; j<oomPss.length; j++) { 12999 if (oomPss[j] != 0) { 13000 String label = isCompact ? DUMP_MEM_OOM_COMPACT_LABEL[j] 13001 : DUMP_MEM_OOM_LABEL[j]; 13002 MemItem item = new MemItem(label, label, oomPss[j], 13003 DUMP_MEM_OOM_ADJ[j]); 13004 item.subitems = oomProcs[j]; 13005 oomMems.add(item); 13006 } 13007 } 13008 13009 if (!brief && !oomOnly && !isCompact) { 13010 pw.println(); 13011 pw.println("Total PSS by process:"); 13012 dumpMemItems(pw, " ", "proc", procMems, true, isCompact); 13013 pw.println(); 13014 } 13015 if (!isCompact) { 13016 pw.println("Total PSS by OOM adjustment:"); 13017 } 13018 dumpMemItems(pw, " ", "oom", oomMems, false, isCompact); 13019 if (!brief && !oomOnly) { 13020 PrintWriter out = categoryPw != null ? categoryPw : pw; 13021 if (!isCompact) { 13022 out.println(); 13023 out.println("Total PSS by category:"); 13024 } 13025 dumpMemItems(out, " ", "cat", catMems, true, isCompact); 13026 } 13027 if (!isCompact) { 13028 pw.println(); 13029 } 13030 MemInfoReader memInfo = new MemInfoReader(); 13031 memInfo.readMemInfo(); 13032 if (nativeProcTotalPss > 0) { 13033 synchronized (this) { 13034 mProcessStats.addSysMemUsageLocked(memInfo.getCachedSizeKb(), 13035 memInfo.getFreeSizeKb(), memInfo.getZramTotalSizeKb(), 13036 memInfo.getBuffersSizeKb()+memInfo.getShmemSizeKb()+memInfo.getSlabSizeKb(), 13037 nativeProcTotalPss); 13038 } 13039 } 13040 if (!brief) { 13041 if (!isCompact) { 13042 pw.print("Total RAM: "); pw.print(memInfo.getTotalSizeKb()); 13043 pw.print(" kB (status "); 13044 switch (mLastMemoryLevel) { 13045 case ProcessStats.ADJ_MEM_FACTOR_NORMAL: 13046 pw.println("normal)"); 13047 break; 13048 case ProcessStats.ADJ_MEM_FACTOR_MODERATE: 13049 pw.println("moderate)"); 13050 break; 13051 case ProcessStats.ADJ_MEM_FACTOR_LOW: 13052 pw.println("low)"); 13053 break; 13054 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 13055 pw.println("critical)"); 13056 break; 13057 default: 13058 pw.print(mLastMemoryLevel); 13059 pw.println(")"); 13060 break; 13061 } 13062 pw.print(" Free RAM: "); pw.print(cachedPss + memInfo.getCachedSizeKb() 13063 + memInfo.getFreeSizeKb()); pw.print(" kB ("); 13064 pw.print(cachedPss); pw.print(" cached pss + "); 13065 pw.print(memInfo.getCachedSizeKb()); pw.print(" cached + "); 13066 pw.print(memInfo.getFreeSizeKb()); pw.println(" free)"); 13067 } else { 13068 pw.print("ram,"); pw.print(memInfo.getTotalSizeKb()); pw.print(","); 13069 pw.print(cachedPss + memInfo.getCachedSizeKb() 13070 + memInfo.getFreeSizeKb()); pw.print(","); 13071 pw.println(totalPss - cachedPss); 13072 } 13073 } 13074 if (!isCompact) { 13075 pw.print(" Used RAM: "); pw.print(totalPss - cachedPss 13076 + memInfo.getBuffersSizeKb() + memInfo.getShmemSizeKb() 13077 + memInfo.getSlabSizeKb()); pw.print(" kB ("); 13078 pw.print(totalPss - cachedPss); pw.print(" used pss + "); 13079 pw.print(memInfo.getBuffersSizeKb()); pw.print(" buffers + "); 13080 pw.print(memInfo.getShmemSizeKb()); pw.print(" shmem + "); 13081 pw.print(memInfo.getSlabSizeKb()); pw.println(" slab)"); 13082 pw.print(" Lost RAM: "); pw.print(memInfo.getTotalSizeKb() 13083 - totalPss - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 13084 - memInfo.getBuffersSizeKb() - memInfo.getShmemSizeKb() 13085 - memInfo.getSlabSizeKb()); pw.println(" kB"); 13086 } 13087 if (!brief) { 13088 if (memInfo.getZramTotalSizeKb() != 0) { 13089 if (!isCompact) { 13090 pw.print(" ZRAM: "); pw.print(memInfo.getZramTotalSizeKb()); 13091 pw.print(" kB physical used for "); 13092 pw.print(memInfo.getSwapTotalSizeKb() 13093 - memInfo.getSwapFreeSizeKb()); 13094 pw.print(" kB in swap ("); 13095 pw.print(memInfo.getSwapTotalSizeKb()); 13096 pw.println(" kB total swap)"); 13097 } else { 13098 pw.print("zram,"); pw.print(memInfo.getZramTotalSizeKb()); pw.print(","); 13099 pw.print(memInfo.getSwapTotalSizeKb()); pw.print(","); 13100 pw.println(memInfo.getSwapFreeSizeKb()); 13101 } 13102 } 13103 final int[] SINGLE_LONG_FORMAT = new int[] { 13104 Process.PROC_SPACE_TERM|Process.PROC_OUT_LONG 13105 }; 13106 long[] longOut = new long[1]; 13107 Process.readProcFile("/sys/kernel/mm/ksm/pages_shared", 13108 SINGLE_LONG_FORMAT, null, longOut, null); 13109 long shared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13110 longOut[0] = 0; 13111 Process.readProcFile("/sys/kernel/mm/ksm/pages_sharing", 13112 SINGLE_LONG_FORMAT, null, longOut, null); 13113 long sharing = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13114 longOut[0] = 0; 13115 Process.readProcFile("/sys/kernel/mm/ksm/pages_unshared", 13116 SINGLE_LONG_FORMAT, null, longOut, null); 13117 long unshared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13118 longOut[0] = 0; 13119 Process.readProcFile("/sys/kernel/mm/ksm/pages_volatile", 13120 SINGLE_LONG_FORMAT, null, longOut, null); 13121 long voltile = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13122 if (!isCompact) { 13123 if (sharing != 0 || shared != 0 || unshared != 0 || voltile != 0) { 13124 pw.print(" KSM: "); pw.print(sharing); 13125 pw.print(" kB saved from shared "); 13126 pw.print(shared); pw.println(" kB"); 13127 pw.print(" "); pw.print(unshared); pw.print(" kB unshared; "); 13128 pw.print(voltile); pw.println(" kB volatile"); 13129 } 13130 pw.print(" Tuning: "); 13131 pw.print(ActivityManager.staticGetMemoryClass()); 13132 pw.print(" (large "); 13133 pw.print(ActivityManager.staticGetLargeMemoryClass()); 13134 pw.print("), oom "); 13135 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 13136 pw.print(" kB"); 13137 pw.print(", restore limit "); 13138 pw.print(mProcessList.getCachedRestoreThresholdKb()); 13139 pw.print(" kB"); 13140 if (ActivityManager.isLowRamDeviceStatic()) { 13141 pw.print(" (low-ram)"); 13142 } 13143 if (ActivityManager.isHighEndGfx()) { 13144 pw.print(" (high-end-gfx)"); 13145 } 13146 pw.println(); 13147 } else { 13148 pw.print("ksm,"); pw.print(sharing); pw.print(","); 13149 pw.print(shared); pw.print(","); pw.print(unshared); pw.print(","); 13150 pw.println(voltile); 13151 pw.print("tuning,"); 13152 pw.print(ActivityManager.staticGetMemoryClass()); 13153 pw.print(','); 13154 pw.print(ActivityManager.staticGetLargeMemoryClass()); 13155 pw.print(','); 13156 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 13157 if (ActivityManager.isLowRamDeviceStatic()) { 13158 pw.print(",low-ram"); 13159 } 13160 if (ActivityManager.isHighEndGfx()) { 13161 pw.print(",high-end-gfx"); 13162 } 13163 pw.println(); 13164 } 13165 } 13166 } 13167 } 13168 13169 /** 13170 * Searches array of arguments for the specified string 13171 * @param args array of argument strings 13172 * @param value value to search for 13173 * @return true if the value is contained in the array 13174 */ 13175 private static boolean scanArgs(String[] args, String value) { 13176 if (args != null) { 13177 for (String arg : args) { 13178 if (value.equals(arg)) { 13179 return true; 13180 } 13181 } 13182 } 13183 return false; 13184 } 13185 13186 private final boolean removeDyingProviderLocked(ProcessRecord proc, 13187 ContentProviderRecord cpr, boolean always) { 13188 final boolean inLaunching = mLaunchingProviders.contains(cpr); 13189 13190 if (!inLaunching || always) { 13191 synchronized (cpr) { 13192 cpr.launchingApp = null; 13193 cpr.notifyAll(); 13194 } 13195 mProviderMap.removeProviderByClass(cpr.name, UserHandle.getUserId(cpr.uid)); 13196 String names[] = cpr.info.authority.split(";"); 13197 for (int j = 0; j < names.length; j++) { 13198 mProviderMap.removeProviderByName(names[j], UserHandle.getUserId(cpr.uid)); 13199 } 13200 } 13201 13202 for (int i=0; i<cpr.connections.size(); i++) { 13203 ContentProviderConnection conn = cpr.connections.get(i); 13204 if (conn.waiting) { 13205 // If this connection is waiting for the provider, then we don't 13206 // need to mess with its process unless we are always removing 13207 // or for some reason the provider is not currently launching. 13208 if (inLaunching && !always) { 13209 continue; 13210 } 13211 } 13212 ProcessRecord capp = conn.client; 13213 conn.dead = true; 13214 if (conn.stableCount > 0) { 13215 if (!capp.persistent && capp.thread != null 13216 && capp.pid != 0 13217 && capp.pid != MY_PID) { 13218 killUnneededProcessLocked(capp, "depends on provider " 13219 + cpr.name.flattenToShortString() 13220 + " in dying proc " + (proc != null ? proc.processName : "??")); 13221 } 13222 } else if (capp.thread != null && conn.provider.provider != null) { 13223 try { 13224 capp.thread.unstableProviderDied(conn.provider.provider.asBinder()); 13225 } catch (RemoteException e) { 13226 } 13227 // In the protocol here, we don't expect the client to correctly 13228 // clean up this connection, we'll just remove it. 13229 cpr.connections.remove(i); 13230 conn.client.conProviders.remove(conn); 13231 } 13232 } 13233 13234 if (inLaunching && always) { 13235 mLaunchingProviders.remove(cpr); 13236 } 13237 return inLaunching; 13238 } 13239 13240 /** 13241 * Main code for cleaning up a process when it has gone away. This is 13242 * called both as a result of the process dying, or directly when stopping 13243 * a process when running in single process mode. 13244 */ 13245 private final void cleanUpApplicationRecordLocked(ProcessRecord app, 13246 boolean restarting, boolean allowRestart, int index) { 13247 if (index >= 0) { 13248 removeLruProcessLocked(app); 13249 ProcessList.remove(app.pid); 13250 } 13251 13252 mProcessesToGc.remove(app); 13253 mPendingPssProcesses.remove(app); 13254 13255 // Dismiss any open dialogs. 13256 if (app.crashDialog != null && !app.forceCrashReport) { 13257 app.crashDialog.dismiss(); 13258 app.crashDialog = null; 13259 } 13260 if (app.anrDialog != null) { 13261 app.anrDialog.dismiss(); 13262 app.anrDialog = null; 13263 } 13264 if (app.waitDialog != null) { 13265 app.waitDialog.dismiss(); 13266 app.waitDialog = null; 13267 } 13268 13269 app.crashing = false; 13270 app.notResponding = false; 13271 13272 app.resetPackageList(mProcessStats); 13273 app.unlinkDeathRecipient(); 13274 app.makeInactive(mProcessStats); 13275 app.waitingToKill = null; 13276 app.forcingToForeground = null; 13277 updateProcessForegroundLocked(app, false, false); 13278 app.foregroundActivities = false; 13279 app.hasShownUi = false; 13280 app.treatLikeActivity = false; 13281 app.hasAboveClient = false; 13282 app.hasClientActivities = false; 13283 13284 mServices.killServicesLocked(app, allowRestart); 13285 13286 boolean restart = false; 13287 13288 // Remove published content providers. 13289 for (int i=app.pubProviders.size()-1; i>=0; i--) { 13290 ContentProviderRecord cpr = app.pubProviders.valueAt(i); 13291 final boolean always = app.bad || !allowRestart; 13292 if (removeDyingProviderLocked(app, cpr, always) || always) { 13293 // We left the provider in the launching list, need to 13294 // restart it. 13295 restart = true; 13296 } 13297 13298 cpr.provider = null; 13299 cpr.proc = null; 13300 } 13301 app.pubProviders.clear(); 13302 13303 // Take care of any launching providers waiting for this process. 13304 if (checkAppInLaunchingProvidersLocked(app, false)) { 13305 restart = true; 13306 } 13307 13308 // Unregister from connected content providers. 13309 if (!app.conProviders.isEmpty()) { 13310 for (int i=0; i<app.conProviders.size(); i++) { 13311 ContentProviderConnection conn = app.conProviders.get(i); 13312 conn.provider.connections.remove(conn); 13313 } 13314 app.conProviders.clear(); 13315 } 13316 13317 // At this point there may be remaining entries in mLaunchingProviders 13318 // where we were the only one waiting, so they are no longer of use. 13319 // Look for these and clean up if found. 13320 // XXX Commented out for now. Trying to figure out a way to reproduce 13321 // the actual situation to identify what is actually going on. 13322 if (false) { 13323 for (int i=0; i<mLaunchingProviders.size(); i++) { 13324 ContentProviderRecord cpr = (ContentProviderRecord) 13325 mLaunchingProviders.get(i); 13326 if (cpr.connections.size() <= 0 && !cpr.hasExternalProcessHandles()) { 13327 synchronized (cpr) { 13328 cpr.launchingApp = null; 13329 cpr.notifyAll(); 13330 } 13331 } 13332 } 13333 } 13334 13335 skipCurrentReceiverLocked(app); 13336 13337 // Unregister any receivers. 13338 for (int i=app.receivers.size()-1; i>=0; i--) { 13339 removeReceiverLocked(app.receivers.valueAt(i)); 13340 } 13341 app.receivers.clear(); 13342 13343 // If the app is undergoing backup, tell the backup manager about it 13344 if (mBackupTarget != null && app.pid == mBackupTarget.app.pid) { 13345 if (DEBUG_BACKUP || DEBUG_CLEANUP) Slog.d(TAG, "App " 13346 + mBackupTarget.appInfo + " died during backup"); 13347 try { 13348 IBackupManager bm = IBackupManager.Stub.asInterface( 13349 ServiceManager.getService(Context.BACKUP_SERVICE)); 13350 bm.agentDisconnected(app.info.packageName); 13351 } catch (RemoteException e) { 13352 // can't happen; backup manager is local 13353 } 13354 } 13355 13356 for (int i = mPendingProcessChanges.size()-1; i>=0; i--) { 13357 ProcessChangeItem item = mPendingProcessChanges.get(i); 13358 if (item.pid == app.pid) { 13359 mPendingProcessChanges.remove(i); 13360 mAvailProcessChanges.add(item); 13361 } 13362 } 13363 mHandler.obtainMessage(DISPATCH_PROCESS_DIED, app.pid, app.info.uid, null).sendToTarget(); 13364 13365 // If the caller is restarting this app, then leave it in its 13366 // current lists and let the caller take care of it. 13367 if (restarting) { 13368 return; 13369 } 13370 13371 if (!app.persistent || app.isolated) { 13372 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, 13373 "Removing non-persistent process during cleanup: " + app); 13374 mProcessNames.remove(app.processName, app.uid); 13375 mIsolatedProcesses.remove(app.uid); 13376 if (mHeavyWeightProcess == app) { 13377 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 13378 mHeavyWeightProcess.userId, 0)); 13379 mHeavyWeightProcess = null; 13380 } 13381 } else if (!app.removed) { 13382 // This app is persistent, so we need to keep its record around. 13383 // If it is not already on the pending app list, add it there 13384 // and start a new process for it. 13385 if (mPersistentStartingProcesses.indexOf(app) < 0) { 13386 mPersistentStartingProcesses.add(app); 13387 restart = true; 13388 } 13389 } 13390 if ((DEBUG_PROCESSES || DEBUG_CLEANUP) && mProcessesOnHold.contains(app)) Slog.v(TAG, 13391 "Clean-up removing on hold: " + app); 13392 mProcessesOnHold.remove(app); 13393 13394 if (app == mHomeProcess) { 13395 mHomeProcess = null; 13396 } 13397 if (app == mPreviousProcess) { 13398 mPreviousProcess = null; 13399 } 13400 13401 if (restart && !app.isolated) { 13402 // We have components that still need to be running in the 13403 // process, so re-launch it. 13404 mProcessNames.put(app.processName, app.uid, app); 13405 startProcessLocked(app, "restart", app.processName, null /* ABI override */); 13406 } else if (app.pid > 0 && app.pid != MY_PID) { 13407 // Goodbye! 13408 boolean removed; 13409 synchronized (mPidsSelfLocked) { 13410 mPidsSelfLocked.remove(app.pid); 13411 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 13412 } 13413 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 13414 if (app.isolated) { 13415 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 13416 } 13417 app.setPid(0); 13418 } 13419 } 13420 13421 boolean checkAppInLaunchingProvidersLocked(ProcessRecord app, boolean alwaysBad) { 13422 // Look through the content providers we are waiting to have launched, 13423 // and if any run in this process then either schedule a restart of 13424 // the process or kill the client waiting for it if this process has 13425 // gone bad. 13426 int NL = mLaunchingProviders.size(); 13427 boolean restart = false; 13428 for (int i=0; i<NL; i++) { 13429 ContentProviderRecord cpr = mLaunchingProviders.get(i); 13430 if (cpr.launchingApp == app) { 13431 if (!alwaysBad && !app.bad) { 13432 restart = true; 13433 } else { 13434 removeDyingProviderLocked(app, cpr, true); 13435 // cpr should have been removed from mLaunchingProviders 13436 NL = mLaunchingProviders.size(); 13437 i--; 13438 } 13439 } 13440 } 13441 return restart; 13442 } 13443 13444 // ========================================================= 13445 // SERVICES 13446 // ========================================================= 13447 13448 @Override 13449 public List<ActivityManager.RunningServiceInfo> getServices(int maxNum, 13450 int flags) { 13451 enforceNotIsolatedCaller("getServices"); 13452 synchronized (this) { 13453 return mServices.getRunningServiceInfoLocked(maxNum, flags); 13454 } 13455 } 13456 13457 @Override 13458 public PendingIntent getRunningServiceControlPanel(ComponentName name) { 13459 enforceNotIsolatedCaller("getRunningServiceControlPanel"); 13460 synchronized (this) { 13461 return mServices.getRunningServiceControlPanelLocked(name); 13462 } 13463 } 13464 13465 @Override 13466 public ComponentName startService(IApplicationThread caller, Intent service, 13467 String resolvedType, int userId) { 13468 enforceNotIsolatedCaller("startService"); 13469 // Refuse possible leaked file descriptors 13470 if (service != null && service.hasFileDescriptors() == true) { 13471 throw new IllegalArgumentException("File descriptors passed in Intent"); 13472 } 13473 13474 if (DEBUG_SERVICE) 13475 Slog.v(TAG, "startService: " + service + " type=" + resolvedType); 13476 synchronized(this) { 13477 final int callingPid = Binder.getCallingPid(); 13478 final int callingUid = Binder.getCallingUid(); 13479 final long origId = Binder.clearCallingIdentity(); 13480 ComponentName res = mServices.startServiceLocked(caller, service, 13481 resolvedType, callingPid, callingUid, userId); 13482 Binder.restoreCallingIdentity(origId); 13483 return res; 13484 } 13485 } 13486 13487 ComponentName startServiceInPackage(int uid, 13488 Intent service, String resolvedType, int userId) { 13489 synchronized(this) { 13490 if (DEBUG_SERVICE) 13491 Slog.v(TAG, "startServiceInPackage: " + service + " type=" + resolvedType); 13492 final long origId = Binder.clearCallingIdentity(); 13493 ComponentName res = mServices.startServiceLocked(null, service, 13494 resolvedType, -1, uid, userId); 13495 Binder.restoreCallingIdentity(origId); 13496 return res; 13497 } 13498 } 13499 13500 @Override 13501 public int stopService(IApplicationThread caller, Intent service, 13502 String resolvedType, int userId) { 13503 enforceNotIsolatedCaller("stopService"); 13504 // Refuse possible leaked file descriptors 13505 if (service != null && service.hasFileDescriptors() == true) { 13506 throw new IllegalArgumentException("File descriptors passed in Intent"); 13507 } 13508 13509 synchronized(this) { 13510 return mServices.stopServiceLocked(caller, service, resolvedType, userId); 13511 } 13512 } 13513 13514 @Override 13515 public IBinder peekService(Intent service, String resolvedType) { 13516 enforceNotIsolatedCaller("peekService"); 13517 // Refuse possible leaked file descriptors 13518 if (service != null && service.hasFileDescriptors() == true) { 13519 throw new IllegalArgumentException("File descriptors passed in Intent"); 13520 } 13521 synchronized(this) { 13522 return mServices.peekServiceLocked(service, resolvedType); 13523 } 13524 } 13525 13526 @Override 13527 public boolean stopServiceToken(ComponentName className, IBinder token, 13528 int startId) { 13529 synchronized(this) { 13530 return mServices.stopServiceTokenLocked(className, token, startId); 13531 } 13532 } 13533 13534 @Override 13535 public void setServiceForeground(ComponentName className, IBinder token, 13536 int id, Notification notification, boolean removeNotification) { 13537 synchronized(this) { 13538 mServices.setServiceForegroundLocked(className, token, id, notification, 13539 removeNotification); 13540 } 13541 } 13542 13543 @Override 13544 public int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 13545 boolean requireFull, String name, String callerPackage) { 13546 return handleIncomingUser(callingPid, callingUid, userId, allowAll, 13547 requireFull ? ALLOW_FULL_ONLY : ALLOW_NON_FULL, name, callerPackage); 13548 } 13549 13550 int unsafeConvertIncomingUser(int userId) { 13551 return (userId == UserHandle.USER_CURRENT || userId == UserHandle.USER_CURRENT_OR_SELF) 13552 ? mCurrentUserId : userId; 13553 } 13554 13555 int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 13556 int allowMode, String name, String callerPackage) { 13557 final int callingUserId = UserHandle.getUserId(callingUid); 13558 if (callingUserId == userId) { 13559 return userId; 13560 } 13561 13562 // Note that we may be accessing mCurrentUserId outside of a lock... 13563 // shouldn't be a big deal, if this is being called outside 13564 // of a locked context there is intrinsically a race with 13565 // the value the caller will receive and someone else changing it. 13566 // We assume that USER_CURRENT_OR_SELF will use the current user; later 13567 // we will switch to the calling user if access to the current user fails. 13568 int targetUserId = unsafeConvertIncomingUser(userId); 13569 13570 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 13571 final boolean allow; 13572 if (checkComponentPermission(INTERACT_ACROSS_USERS_FULL, callingPid, 13573 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED) { 13574 // If the caller has this permission, they always pass go. And collect $200. 13575 allow = true; 13576 } else if (allowMode == ALLOW_FULL_ONLY) { 13577 // We require full access, sucks to be you. 13578 allow = false; 13579 } else if (checkComponentPermission(INTERACT_ACROSS_USERS, callingPid, 13580 callingUid, -1, true) != PackageManager.PERMISSION_GRANTED) { 13581 // If the caller does not have either permission, they are always doomed. 13582 allow = false; 13583 } else if (allowMode == ALLOW_NON_FULL) { 13584 // We are blanket allowing non-full access, you lucky caller! 13585 allow = true; 13586 } else if (allowMode == ALLOW_NON_FULL_IN_PROFILE) { 13587 // We may or may not allow this depending on whether the two users are 13588 // in the same profile. 13589 synchronized (mUserProfileGroupIdsSelfLocked) { 13590 int callingProfile = mUserProfileGroupIdsSelfLocked.get(callingUserId, 13591 UserInfo.NO_PROFILE_GROUP_ID); 13592 int targetProfile = mUserProfileGroupIdsSelfLocked.get(targetUserId, 13593 UserInfo.NO_PROFILE_GROUP_ID); 13594 allow = callingProfile != UserInfo.NO_PROFILE_GROUP_ID 13595 && callingProfile == targetProfile; 13596 } 13597 } else { 13598 throw new IllegalArgumentException("Unknown mode: " + allowMode); 13599 } 13600 if (!allow) { 13601 if (userId == UserHandle.USER_CURRENT_OR_SELF) { 13602 // In this case, they would like to just execute as their 13603 // owner user instead of failing. 13604 targetUserId = callingUserId; 13605 } else { 13606 StringBuilder builder = new StringBuilder(128); 13607 builder.append("Permission Denial: "); 13608 builder.append(name); 13609 if (callerPackage != null) { 13610 builder.append(" from "); 13611 builder.append(callerPackage); 13612 } 13613 builder.append(" asks to run as user "); 13614 builder.append(userId); 13615 builder.append(" but is calling from user "); 13616 builder.append(UserHandle.getUserId(callingUid)); 13617 builder.append("; this requires "); 13618 builder.append(INTERACT_ACROSS_USERS_FULL); 13619 if (allowMode != ALLOW_FULL_ONLY) { 13620 builder.append(" or "); 13621 builder.append(INTERACT_ACROSS_USERS); 13622 } 13623 String msg = builder.toString(); 13624 Slog.w(TAG, msg); 13625 throw new SecurityException(msg); 13626 } 13627 } 13628 } 13629 if (!allowAll && targetUserId < 0) { 13630 throw new IllegalArgumentException( 13631 "Call does not support special user #" + targetUserId); 13632 } 13633 return targetUserId; 13634 } 13635 13636 boolean isSingleton(String componentProcessName, ApplicationInfo aInfo, 13637 String className, int flags) { 13638 boolean result = false; 13639 // For apps that don't have pre-defined UIDs, check for permission 13640 if (UserHandle.getAppId(aInfo.uid) >= Process.FIRST_APPLICATION_UID) { 13641 if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 13642 if (ActivityManager.checkUidPermission( 13643 INTERACT_ACROSS_USERS, 13644 aInfo.uid) != PackageManager.PERMISSION_GRANTED) { 13645 ComponentName comp = new ComponentName(aInfo.packageName, className); 13646 String msg = "Permission Denial: Component " + comp.flattenToShortString() 13647 + " requests FLAG_SINGLE_USER, but app does not hold " 13648 + INTERACT_ACROSS_USERS; 13649 Slog.w(TAG, msg); 13650 throw new SecurityException(msg); 13651 } 13652 // Permission passed 13653 result = true; 13654 } 13655 } else if ("system".equals(componentProcessName)) { 13656 result = true; 13657 } else { 13658 // App with pre-defined UID, check if it's a persistent app 13659 result = (aInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0; 13660 } 13661 if (DEBUG_MU) { 13662 Slog.v(TAG, "isSingleton(" + componentProcessName + ", " + aInfo 13663 + ", " + className + ", 0x" + Integer.toHexString(flags) + ") = " + result); 13664 } 13665 return result; 13666 } 13667 13668 /** 13669 * Checks to see if the caller is in the same app as the singleton 13670 * component, or the component is in a special app. It allows special apps 13671 * to export singleton components but prevents exporting singleton 13672 * components for regular apps. 13673 */ 13674 boolean isValidSingletonCall(int callingUid, int componentUid) { 13675 int componentAppId = UserHandle.getAppId(componentUid); 13676 return UserHandle.isSameApp(callingUid, componentUid) 13677 || componentAppId == Process.SYSTEM_UID 13678 || componentAppId == Process.PHONE_UID 13679 || ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, componentUid) 13680 == PackageManager.PERMISSION_GRANTED; 13681 } 13682 13683 public int bindService(IApplicationThread caller, IBinder token, 13684 Intent service, String resolvedType, 13685 IServiceConnection connection, int flags, int userId) { 13686 enforceNotIsolatedCaller("bindService"); 13687 // Refuse possible leaked file descriptors 13688 if (service != null && service.hasFileDescriptors() == true) { 13689 throw new IllegalArgumentException("File descriptors passed in Intent"); 13690 } 13691 13692 synchronized(this) { 13693 return mServices.bindServiceLocked(caller, token, service, resolvedType, 13694 connection, flags, userId); 13695 } 13696 } 13697 13698 public boolean unbindService(IServiceConnection connection) { 13699 synchronized (this) { 13700 return mServices.unbindServiceLocked(connection); 13701 } 13702 } 13703 13704 public void publishService(IBinder token, Intent intent, IBinder service) { 13705 // Refuse possible leaked file descriptors 13706 if (intent != null && intent.hasFileDescriptors() == true) { 13707 throw new IllegalArgumentException("File descriptors passed in Intent"); 13708 } 13709 13710 synchronized(this) { 13711 if (!(token instanceof ServiceRecord)) { 13712 throw new IllegalArgumentException("Invalid service token"); 13713 } 13714 mServices.publishServiceLocked((ServiceRecord)token, intent, service); 13715 } 13716 } 13717 13718 public void unbindFinished(IBinder token, Intent intent, boolean doRebind) { 13719 // Refuse possible leaked file descriptors 13720 if (intent != null && intent.hasFileDescriptors() == true) { 13721 throw new IllegalArgumentException("File descriptors passed in Intent"); 13722 } 13723 13724 synchronized(this) { 13725 mServices.unbindFinishedLocked((ServiceRecord)token, intent, doRebind); 13726 } 13727 } 13728 13729 public void serviceDoneExecuting(IBinder token, int type, int startId, int res) { 13730 synchronized(this) { 13731 if (!(token instanceof ServiceRecord)) { 13732 throw new IllegalArgumentException("Invalid service token"); 13733 } 13734 mServices.serviceDoneExecutingLocked((ServiceRecord)token, type, startId, res); 13735 } 13736 } 13737 13738 // ========================================================= 13739 // BACKUP AND RESTORE 13740 // ========================================================= 13741 13742 // Cause the target app to be launched if necessary and its backup agent 13743 // instantiated. The backup agent will invoke backupAgentCreated() on the 13744 // activity manager to announce its creation. 13745 public boolean bindBackupAgent(ApplicationInfo app, int backupMode) { 13746 if (DEBUG_BACKUP) Slog.v(TAG, "bindBackupAgent: app=" + app + " mode=" + backupMode); 13747 enforceCallingPermission("android.permission.CONFIRM_FULL_BACKUP", "bindBackupAgent"); 13748 13749 synchronized(this) { 13750 // !!! TODO: currently no check here that we're already bound 13751 BatteryStatsImpl.Uid.Pkg.Serv ss = null; 13752 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 13753 synchronized (stats) { 13754 ss = stats.getServiceStatsLocked(app.uid, app.packageName, app.name); 13755 } 13756 13757 // Backup agent is now in use, its package can't be stopped. 13758 try { 13759 AppGlobals.getPackageManager().setPackageStoppedState( 13760 app.packageName, false, UserHandle.getUserId(app.uid)); 13761 } catch (RemoteException e) { 13762 } catch (IllegalArgumentException e) { 13763 Slog.w(TAG, "Failed trying to unstop package " 13764 + app.packageName + ": " + e); 13765 } 13766 13767 BackupRecord r = new BackupRecord(ss, app, backupMode); 13768 ComponentName hostingName = (backupMode == IApplicationThread.BACKUP_MODE_INCREMENTAL) 13769 ? new ComponentName(app.packageName, app.backupAgentName) 13770 : new ComponentName("android", "FullBackupAgent"); 13771 // startProcessLocked() returns existing proc's record if it's already running 13772 ProcessRecord proc = startProcessLocked(app.processName, app, 13773 false, 0, "backup", hostingName, false, false, false); 13774 if (proc == null) { 13775 Slog.e(TAG, "Unable to start backup agent process " + r); 13776 return false; 13777 } 13778 13779 r.app = proc; 13780 mBackupTarget = r; 13781 mBackupAppName = app.packageName; 13782 13783 // Try not to kill the process during backup 13784 updateOomAdjLocked(proc); 13785 13786 // If the process is already attached, schedule the creation of the backup agent now. 13787 // If it is not yet live, this will be done when it attaches to the framework. 13788 if (proc.thread != null) { 13789 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc already running: " + proc); 13790 try { 13791 proc.thread.scheduleCreateBackupAgent(app, 13792 compatibilityInfoForPackageLocked(app), backupMode); 13793 } catch (RemoteException e) { 13794 // Will time out on the backup manager side 13795 } 13796 } else { 13797 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc not running, waiting for attach"); 13798 } 13799 // Invariants: at this point, the target app process exists and the application 13800 // is either already running or in the process of coming up. mBackupTarget and 13801 // mBackupAppName describe the app, so that when it binds back to the AM we 13802 // know that it's scheduled for a backup-agent operation. 13803 } 13804 13805 return true; 13806 } 13807 13808 @Override 13809 public void clearPendingBackup() { 13810 if (DEBUG_BACKUP) Slog.v(TAG, "clearPendingBackup"); 13811 enforceCallingPermission("android.permission.BACKUP", "clearPendingBackup"); 13812 13813 synchronized (this) { 13814 mBackupTarget = null; 13815 mBackupAppName = null; 13816 } 13817 } 13818 13819 // A backup agent has just come up 13820 public void backupAgentCreated(String agentPackageName, IBinder agent) { 13821 if (DEBUG_BACKUP) Slog.v(TAG, "backupAgentCreated: " + agentPackageName 13822 + " = " + agent); 13823 13824 synchronized(this) { 13825 if (!agentPackageName.equals(mBackupAppName)) { 13826 Slog.e(TAG, "Backup agent created for " + agentPackageName + " but not requested!"); 13827 return; 13828 } 13829 } 13830 13831 long oldIdent = Binder.clearCallingIdentity(); 13832 try { 13833 IBackupManager bm = IBackupManager.Stub.asInterface( 13834 ServiceManager.getService(Context.BACKUP_SERVICE)); 13835 bm.agentConnected(agentPackageName, agent); 13836 } catch (RemoteException e) { 13837 // can't happen; the backup manager service is local 13838 } catch (Exception e) { 13839 Slog.w(TAG, "Exception trying to deliver BackupAgent binding: "); 13840 e.printStackTrace(); 13841 } finally { 13842 Binder.restoreCallingIdentity(oldIdent); 13843 } 13844 } 13845 13846 // done with this agent 13847 public void unbindBackupAgent(ApplicationInfo appInfo) { 13848 if (DEBUG_BACKUP) Slog.v(TAG, "unbindBackupAgent: " + appInfo); 13849 if (appInfo == null) { 13850 Slog.w(TAG, "unbind backup agent for null app"); 13851 return; 13852 } 13853 13854 synchronized(this) { 13855 try { 13856 if (mBackupAppName == null) { 13857 Slog.w(TAG, "Unbinding backup agent with no active backup"); 13858 return; 13859 } 13860 13861 if (!mBackupAppName.equals(appInfo.packageName)) { 13862 Slog.e(TAG, "Unbind of " + appInfo + " but is not the current backup target"); 13863 return; 13864 } 13865 13866 // Not backing this app up any more; reset its OOM adjustment 13867 final ProcessRecord proc = mBackupTarget.app; 13868 updateOomAdjLocked(proc); 13869 13870 // If the app crashed during backup, 'thread' will be null here 13871 if (proc.thread != null) { 13872 try { 13873 proc.thread.scheduleDestroyBackupAgent(appInfo, 13874 compatibilityInfoForPackageLocked(appInfo)); 13875 } catch (Exception e) { 13876 Slog.e(TAG, "Exception when unbinding backup agent:"); 13877 e.printStackTrace(); 13878 } 13879 } 13880 } finally { 13881 mBackupTarget = null; 13882 mBackupAppName = null; 13883 } 13884 } 13885 } 13886 // ========================================================= 13887 // BROADCASTS 13888 // ========================================================= 13889 13890 private final List getStickiesLocked(String action, IntentFilter filter, 13891 List cur, int userId) { 13892 final ContentResolver resolver = mContext.getContentResolver(); 13893 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 13894 if (stickies == null) { 13895 return cur; 13896 } 13897 final ArrayList<Intent> list = stickies.get(action); 13898 if (list == null) { 13899 return cur; 13900 } 13901 int N = list.size(); 13902 for (int i=0; i<N; i++) { 13903 Intent intent = list.get(i); 13904 if (filter.match(resolver, intent, true, TAG) >= 0) { 13905 if (cur == null) { 13906 cur = new ArrayList<Intent>(); 13907 } 13908 cur.add(intent); 13909 } 13910 } 13911 return cur; 13912 } 13913 13914 boolean isPendingBroadcastProcessLocked(int pid) { 13915 return mFgBroadcastQueue.isPendingBroadcastProcessLocked(pid) 13916 || mBgBroadcastQueue.isPendingBroadcastProcessLocked(pid); 13917 } 13918 13919 void skipPendingBroadcastLocked(int pid) { 13920 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 13921 for (BroadcastQueue queue : mBroadcastQueues) { 13922 queue.skipPendingBroadcastLocked(pid); 13923 } 13924 } 13925 13926 // The app just attached; send any pending broadcasts that it should receive 13927 boolean sendPendingBroadcastsLocked(ProcessRecord app) { 13928 boolean didSomething = false; 13929 for (BroadcastQueue queue : mBroadcastQueues) { 13930 didSomething |= queue.sendPendingBroadcastsLocked(app); 13931 } 13932 return didSomething; 13933 } 13934 13935 public Intent registerReceiver(IApplicationThread caller, String callerPackage, 13936 IIntentReceiver receiver, IntentFilter filter, String permission, int userId) { 13937 enforceNotIsolatedCaller("registerReceiver"); 13938 int callingUid; 13939 int callingPid; 13940 synchronized(this) { 13941 ProcessRecord callerApp = null; 13942 if (caller != null) { 13943 callerApp = getRecordForAppLocked(caller); 13944 if (callerApp == null) { 13945 throw new SecurityException( 13946 "Unable to find app for caller " + caller 13947 + " (pid=" + Binder.getCallingPid() 13948 + ") when registering receiver " + receiver); 13949 } 13950 if (callerApp.info.uid != Process.SYSTEM_UID && 13951 !callerApp.pkgList.containsKey(callerPackage) && 13952 !"android".equals(callerPackage)) { 13953 throw new SecurityException("Given caller package " + callerPackage 13954 + " is not running in process " + callerApp); 13955 } 13956 callingUid = callerApp.info.uid; 13957 callingPid = callerApp.pid; 13958 } else { 13959 callerPackage = null; 13960 callingUid = Binder.getCallingUid(); 13961 callingPid = Binder.getCallingPid(); 13962 } 13963 13964 userId = this.handleIncomingUser(callingPid, callingUid, userId, 13965 true, ALLOW_FULL_ONLY, "registerReceiver", callerPackage); 13966 13967 List allSticky = null; 13968 13969 // Look for any matching sticky broadcasts... 13970 Iterator actions = filter.actionsIterator(); 13971 if (actions != null) { 13972 while (actions.hasNext()) { 13973 String action = (String)actions.next(); 13974 allSticky = getStickiesLocked(action, filter, allSticky, 13975 UserHandle.USER_ALL); 13976 allSticky = getStickiesLocked(action, filter, allSticky, 13977 UserHandle.getUserId(callingUid)); 13978 } 13979 } else { 13980 allSticky = getStickiesLocked(null, filter, allSticky, 13981 UserHandle.USER_ALL); 13982 allSticky = getStickiesLocked(null, filter, allSticky, 13983 UserHandle.getUserId(callingUid)); 13984 } 13985 13986 // The first sticky in the list is returned directly back to 13987 // the client. 13988 Intent sticky = allSticky != null ? (Intent)allSticky.get(0) : null; 13989 13990 if (DEBUG_BROADCAST) Slog.v(TAG, "Register receiver " + filter 13991 + ": " + sticky); 13992 13993 if (receiver == null) { 13994 return sticky; 13995 } 13996 13997 ReceiverList rl 13998 = (ReceiverList)mRegisteredReceivers.get(receiver.asBinder()); 13999 if (rl == null) { 14000 rl = new ReceiverList(this, callerApp, callingPid, callingUid, 14001 userId, receiver); 14002 if (rl.app != null) { 14003 rl.app.receivers.add(rl); 14004 } else { 14005 try { 14006 receiver.asBinder().linkToDeath(rl, 0); 14007 } catch (RemoteException e) { 14008 return sticky; 14009 } 14010 rl.linkedToDeath = true; 14011 } 14012 mRegisteredReceivers.put(receiver.asBinder(), rl); 14013 } else if (rl.uid != callingUid) { 14014 throw new IllegalArgumentException( 14015 "Receiver requested to register for uid " + callingUid 14016 + " was previously registered for uid " + rl.uid); 14017 } else if (rl.pid != callingPid) { 14018 throw new IllegalArgumentException( 14019 "Receiver requested to register for pid " + callingPid 14020 + " was previously registered for pid " + rl.pid); 14021 } else if (rl.userId != userId) { 14022 throw new IllegalArgumentException( 14023 "Receiver requested to register for user " + userId 14024 + " was previously registered for user " + rl.userId); 14025 } 14026 BroadcastFilter bf = new BroadcastFilter(filter, rl, callerPackage, 14027 permission, callingUid, userId); 14028 rl.add(bf); 14029 if (!bf.debugCheck()) { 14030 Slog.w(TAG, "==> For Dynamic broadast"); 14031 } 14032 mReceiverResolver.addFilter(bf); 14033 14034 // Enqueue broadcasts for all existing stickies that match 14035 // this filter. 14036 if (allSticky != null) { 14037 ArrayList receivers = new ArrayList(); 14038 receivers.add(bf); 14039 14040 int N = allSticky.size(); 14041 for (int i=0; i<N; i++) { 14042 Intent intent = (Intent)allSticky.get(i); 14043 BroadcastQueue queue = broadcastQueueForIntent(intent); 14044 BroadcastRecord r = new BroadcastRecord(queue, intent, null, 14045 null, -1, -1, null, null, AppOpsManager.OP_NONE, receivers, null, 0, 14046 null, null, false, true, true, -1); 14047 queue.enqueueParallelBroadcastLocked(r); 14048 queue.scheduleBroadcastsLocked(); 14049 } 14050 } 14051 14052 return sticky; 14053 } 14054 } 14055 14056 public void unregisterReceiver(IIntentReceiver receiver) { 14057 if (DEBUG_BROADCAST) Slog.v(TAG, "Unregister receiver: " + receiver); 14058 14059 final long origId = Binder.clearCallingIdentity(); 14060 try { 14061 boolean doTrim = false; 14062 14063 synchronized(this) { 14064 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder()); 14065 if (rl != null) { 14066 if (rl.curBroadcast != null) { 14067 BroadcastRecord r = rl.curBroadcast; 14068 final boolean doNext = finishReceiverLocked( 14069 receiver.asBinder(), r.resultCode, r.resultData, 14070 r.resultExtras, r.resultAbort); 14071 if (doNext) { 14072 doTrim = true; 14073 r.queue.processNextBroadcast(false); 14074 } 14075 } 14076 14077 if (rl.app != null) { 14078 rl.app.receivers.remove(rl); 14079 } 14080 removeReceiverLocked(rl); 14081 if (rl.linkedToDeath) { 14082 rl.linkedToDeath = false; 14083 rl.receiver.asBinder().unlinkToDeath(rl, 0); 14084 } 14085 } 14086 } 14087 14088 // If we actually concluded any broadcasts, we might now be able 14089 // to trim the recipients' apps from our working set 14090 if (doTrim) { 14091 trimApplications(); 14092 return; 14093 } 14094 14095 } finally { 14096 Binder.restoreCallingIdentity(origId); 14097 } 14098 } 14099 14100 void removeReceiverLocked(ReceiverList rl) { 14101 mRegisteredReceivers.remove(rl.receiver.asBinder()); 14102 int N = rl.size(); 14103 for (int i=0; i<N; i++) { 14104 mReceiverResolver.removeFilter(rl.get(i)); 14105 } 14106 } 14107 14108 private final void sendPackageBroadcastLocked(int cmd, String[] packages, int userId) { 14109 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 14110 ProcessRecord r = mLruProcesses.get(i); 14111 if (r.thread != null && (userId == UserHandle.USER_ALL || r.userId == userId)) { 14112 try { 14113 r.thread.dispatchPackageBroadcast(cmd, packages); 14114 } catch (RemoteException ex) { 14115 } 14116 } 14117 } 14118 } 14119 14120 private List<ResolveInfo> collectReceiverComponents(Intent intent, String resolvedType, 14121 int[] users) { 14122 List<ResolveInfo> receivers = null; 14123 try { 14124 HashSet<ComponentName> singleUserReceivers = null; 14125 boolean scannedFirstReceivers = false; 14126 for (int user : users) { 14127 List<ResolveInfo> newReceivers = AppGlobals.getPackageManager() 14128 .queryIntentReceivers(intent, resolvedType, STOCK_PM_FLAGS, user); 14129 if (user != 0 && newReceivers != null) { 14130 // If this is not the primary user, we need to check for 14131 // any receivers that should be filtered out. 14132 for (int i=0; i<newReceivers.size(); i++) { 14133 ResolveInfo ri = newReceivers.get(i); 14134 if ((ri.activityInfo.flags&ActivityInfo.FLAG_PRIMARY_USER_ONLY) != 0) { 14135 newReceivers.remove(i); 14136 i--; 14137 } 14138 } 14139 } 14140 if (newReceivers != null && newReceivers.size() == 0) { 14141 newReceivers = null; 14142 } 14143 if (receivers == null) { 14144 receivers = newReceivers; 14145 } else if (newReceivers != null) { 14146 // We need to concatenate the additional receivers 14147 // found with what we have do far. This would be easy, 14148 // but we also need to de-dup any receivers that are 14149 // singleUser. 14150 if (!scannedFirstReceivers) { 14151 // Collect any single user receivers we had already retrieved. 14152 scannedFirstReceivers = true; 14153 for (int i=0; i<receivers.size(); i++) { 14154 ResolveInfo ri = receivers.get(i); 14155 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 14156 ComponentName cn = new ComponentName( 14157 ri.activityInfo.packageName, ri.activityInfo.name); 14158 if (singleUserReceivers == null) { 14159 singleUserReceivers = new HashSet<ComponentName>(); 14160 } 14161 singleUserReceivers.add(cn); 14162 } 14163 } 14164 } 14165 // Add the new results to the existing results, tracking 14166 // and de-dupping single user receivers. 14167 for (int i=0; i<newReceivers.size(); i++) { 14168 ResolveInfo ri = newReceivers.get(i); 14169 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 14170 ComponentName cn = new ComponentName( 14171 ri.activityInfo.packageName, ri.activityInfo.name); 14172 if (singleUserReceivers == null) { 14173 singleUserReceivers = new HashSet<ComponentName>(); 14174 } 14175 if (!singleUserReceivers.contains(cn)) { 14176 singleUserReceivers.add(cn); 14177 receivers.add(ri); 14178 } 14179 } else { 14180 receivers.add(ri); 14181 } 14182 } 14183 } 14184 } 14185 } catch (RemoteException ex) { 14186 // pm is in same process, this will never happen. 14187 } 14188 return receivers; 14189 } 14190 14191 private final int broadcastIntentLocked(ProcessRecord callerApp, 14192 String callerPackage, Intent intent, String resolvedType, 14193 IIntentReceiver resultTo, int resultCode, String resultData, 14194 Bundle map, String requiredPermission, int appOp, 14195 boolean ordered, boolean sticky, int callingPid, int callingUid, 14196 int userId) { 14197 intent = new Intent(intent); 14198 14199 // By default broadcasts do not go to stopped apps. 14200 intent.addFlags(Intent.FLAG_EXCLUDE_STOPPED_PACKAGES); 14201 14202 if (DEBUG_BROADCAST_LIGHT) Slog.v( 14203 TAG, (sticky ? "Broadcast sticky: ": "Broadcast: ") + intent 14204 + " ordered=" + ordered + " userid=" + userId); 14205 if ((resultTo != null) && !ordered) { 14206 Slog.w(TAG, "Broadcast " + intent + " not ordered but result callback requested!"); 14207 } 14208 14209 userId = handleIncomingUser(callingPid, callingUid, userId, 14210 true, ALLOW_NON_FULL, "broadcast", callerPackage); 14211 14212 // Make sure that the user who is receiving this broadcast is started. 14213 // If not, we will just skip it. 14214 14215 14216 if (userId != UserHandle.USER_ALL && mStartedUsers.get(userId) == null) { 14217 if (callingUid != Process.SYSTEM_UID || (intent.getFlags() 14218 & Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) { 14219 Slog.w(TAG, "Skipping broadcast of " + intent 14220 + ": user " + userId + " is stopped"); 14221 return ActivityManager.BROADCAST_SUCCESS; 14222 } 14223 } 14224 14225 /* 14226 * Prevent non-system code (defined here to be non-persistent 14227 * processes) from sending protected broadcasts. 14228 */ 14229 int callingAppId = UserHandle.getAppId(callingUid); 14230 if (callingAppId == Process.SYSTEM_UID || callingAppId == Process.PHONE_UID 14231 || callingAppId == Process.SHELL_UID || callingAppId == Process.BLUETOOTH_UID 14232 || callingAppId == Process.NFC_UID || callingUid == 0) { 14233 // Always okay. 14234 } else if (callerApp == null || !callerApp.persistent) { 14235 try { 14236 if (AppGlobals.getPackageManager().isProtectedBroadcast( 14237 intent.getAction())) { 14238 String msg = "Permission Denial: not allowed to send broadcast " 14239 + intent.getAction() + " from pid=" 14240 + callingPid + ", uid=" + callingUid; 14241 Slog.w(TAG, msg); 14242 throw new SecurityException(msg); 14243 } else if (AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(intent.getAction())) { 14244 // Special case for compatibility: we don't want apps to send this, 14245 // but historically it has not been protected and apps may be using it 14246 // to poke their own app widget. So, instead of making it protected, 14247 // just limit it to the caller. 14248 if (callerApp == null) { 14249 String msg = "Permission Denial: not allowed to send broadcast " 14250 + intent.getAction() + " from unknown caller."; 14251 Slog.w(TAG, msg); 14252 throw new SecurityException(msg); 14253 } else if (intent.getComponent() != null) { 14254 // They are good enough to send to an explicit component... verify 14255 // it is being sent to the calling app. 14256 if (!intent.getComponent().getPackageName().equals( 14257 callerApp.info.packageName)) { 14258 String msg = "Permission Denial: not allowed to send broadcast " 14259 + intent.getAction() + " to " 14260 + intent.getComponent().getPackageName() + " from " 14261 + callerApp.info.packageName; 14262 Slog.w(TAG, msg); 14263 throw new SecurityException(msg); 14264 } 14265 } else { 14266 // Limit broadcast to their own package. 14267 intent.setPackage(callerApp.info.packageName); 14268 } 14269 } 14270 } catch (RemoteException e) { 14271 Slog.w(TAG, "Remote exception", e); 14272 return ActivityManager.BROADCAST_SUCCESS; 14273 } 14274 } 14275 14276 // Handle special intents: if this broadcast is from the package 14277 // manager about a package being removed, we need to remove all of 14278 // its activities from the history stack. 14279 final boolean uidRemoved = Intent.ACTION_UID_REMOVED.equals( 14280 intent.getAction()); 14281 if (Intent.ACTION_PACKAGE_REMOVED.equals(intent.getAction()) 14282 || Intent.ACTION_PACKAGE_CHANGED.equals(intent.getAction()) 14283 || Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction()) 14284 || uidRemoved) { 14285 if (checkComponentPermission( 14286 android.Manifest.permission.BROADCAST_PACKAGE_REMOVED, 14287 callingPid, callingUid, -1, true) 14288 == PackageManager.PERMISSION_GRANTED) { 14289 if (uidRemoved) { 14290 final Bundle intentExtras = intent.getExtras(); 14291 final int uid = intentExtras != null 14292 ? intentExtras.getInt(Intent.EXTRA_UID) : -1; 14293 if (uid >= 0) { 14294 BatteryStatsImpl bs = mBatteryStatsService.getActiveStatistics(); 14295 synchronized (bs) { 14296 bs.removeUidStatsLocked(uid); 14297 } 14298 mAppOpsService.uidRemoved(uid); 14299 } 14300 } else { 14301 // If resources are unavailable just force stop all 14302 // those packages and flush the attribute cache as well. 14303 if (Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction())) { 14304 String list[] = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 14305 if (list != null && (list.length > 0)) { 14306 for (String pkg : list) { 14307 forceStopPackageLocked(pkg, -1, false, true, true, false, false, userId, 14308 "storage unmount"); 14309 } 14310 sendPackageBroadcastLocked( 14311 IApplicationThread.EXTERNAL_STORAGE_UNAVAILABLE, list, userId); 14312 } 14313 } else { 14314 Uri data = intent.getData(); 14315 String ssp; 14316 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 14317 boolean removed = Intent.ACTION_PACKAGE_REMOVED.equals( 14318 intent.getAction()); 14319 boolean fullUninstall = removed && 14320 !intent.getBooleanExtra(Intent.EXTRA_REPLACING, false); 14321 if (!intent.getBooleanExtra(Intent.EXTRA_DONT_KILL_APP, false)) { 14322 forceStopPackageLocked(ssp, UserHandle.getAppId( 14323 intent.getIntExtra(Intent.EXTRA_UID, -1)), false, true, true, 14324 false, fullUninstall, userId, 14325 removed ? "pkg removed" : "pkg changed"); 14326 } 14327 if (removed) { 14328 sendPackageBroadcastLocked(IApplicationThread.PACKAGE_REMOVED, 14329 new String[] {ssp}, userId); 14330 if (!intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)) { 14331 mAppOpsService.packageRemoved( 14332 intent.getIntExtra(Intent.EXTRA_UID, -1), ssp); 14333 14334 // Remove all permissions granted from/to this package 14335 removeUriPermissionsForPackageLocked(ssp, userId, true); 14336 } 14337 } 14338 } 14339 } 14340 } 14341 } else { 14342 String msg = "Permission Denial: " + intent.getAction() 14343 + " broadcast from " + callerPackage + " (pid=" + callingPid 14344 + ", uid=" + callingUid + ")" 14345 + " requires " 14346 + android.Manifest.permission.BROADCAST_PACKAGE_REMOVED; 14347 Slog.w(TAG, msg); 14348 throw new SecurityException(msg); 14349 } 14350 14351 // Special case for adding a package: by default turn on compatibility 14352 // mode. 14353 } else if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction())) { 14354 Uri data = intent.getData(); 14355 String ssp; 14356 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 14357 mCompatModePackages.handlePackageAddedLocked(ssp, 14358 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)); 14359 } 14360 } 14361 14362 /* 14363 * If this is the time zone changed action, queue up a message that will reset the timezone 14364 * of all currently running processes. This message will get queued up before the broadcast 14365 * happens. 14366 */ 14367 if (Intent.ACTION_TIMEZONE_CHANGED.equals(intent.getAction())) { 14368 mHandler.sendEmptyMessage(UPDATE_TIME_ZONE); 14369 } 14370 14371 /* 14372 * If the user set the time, let all running processes know. 14373 */ 14374 if (Intent.ACTION_TIME_CHANGED.equals(intent.getAction())) { 14375 final int is24Hour = intent.getBooleanExtra( 14376 Intent.EXTRA_TIME_PREF_24_HOUR_FORMAT, false) ? 1 : 0; 14377 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_TIME, is24Hour, 0)); 14378 } 14379 14380 if (Intent.ACTION_CLEAR_DNS_CACHE.equals(intent.getAction())) { 14381 mHandler.sendEmptyMessage(CLEAR_DNS_CACHE_MSG); 14382 } 14383 14384 if (Proxy.PROXY_CHANGE_ACTION.equals(intent.getAction())) { 14385 ProxyInfo proxy = intent.getParcelableExtra(Proxy.EXTRA_PROXY_INFO); 14386 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_HTTP_PROXY_MSG, proxy)); 14387 } 14388 14389 // Add to the sticky list if requested. 14390 if (sticky) { 14391 if (checkPermission(android.Manifest.permission.BROADCAST_STICKY, 14392 callingPid, callingUid) 14393 != PackageManager.PERMISSION_GRANTED) { 14394 String msg = "Permission Denial: broadcastIntent() requesting a sticky broadcast from pid=" 14395 + callingPid + ", uid=" + callingUid 14396 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 14397 Slog.w(TAG, msg); 14398 throw new SecurityException(msg); 14399 } 14400 if (requiredPermission != null) { 14401 Slog.w(TAG, "Can't broadcast sticky intent " + intent 14402 + " and enforce permission " + requiredPermission); 14403 return ActivityManager.BROADCAST_STICKY_CANT_HAVE_PERMISSION; 14404 } 14405 if (intent.getComponent() != null) { 14406 throw new SecurityException( 14407 "Sticky broadcasts can't target a specific component"); 14408 } 14409 // We use userId directly here, since the "all" target is maintained 14410 // as a separate set of sticky broadcasts. 14411 if (userId != UserHandle.USER_ALL) { 14412 // But first, if this is not a broadcast to all users, then 14413 // make sure it doesn't conflict with an existing broadcast to 14414 // all users. 14415 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get( 14416 UserHandle.USER_ALL); 14417 if (stickies != null) { 14418 ArrayList<Intent> list = stickies.get(intent.getAction()); 14419 if (list != null) { 14420 int N = list.size(); 14421 int i; 14422 for (i=0; i<N; i++) { 14423 if (intent.filterEquals(list.get(i))) { 14424 throw new IllegalArgumentException( 14425 "Sticky broadcast " + intent + " for user " 14426 + userId + " conflicts with existing global broadcast"); 14427 } 14428 } 14429 } 14430 } 14431 } 14432 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 14433 if (stickies == null) { 14434 stickies = new ArrayMap<String, ArrayList<Intent>>(); 14435 mStickyBroadcasts.put(userId, stickies); 14436 } 14437 ArrayList<Intent> list = stickies.get(intent.getAction()); 14438 if (list == null) { 14439 list = new ArrayList<Intent>(); 14440 stickies.put(intent.getAction(), list); 14441 } 14442 int N = list.size(); 14443 int i; 14444 for (i=0; i<N; i++) { 14445 if (intent.filterEquals(list.get(i))) { 14446 // This sticky already exists, replace it. 14447 list.set(i, new Intent(intent)); 14448 break; 14449 } 14450 } 14451 if (i >= N) { 14452 list.add(new Intent(intent)); 14453 } 14454 } 14455 14456 int[] users; 14457 if (userId == UserHandle.USER_ALL) { 14458 // Caller wants broadcast to go to all started users. 14459 users = mStartedUserArray; 14460 } else { 14461 // Caller wants broadcast to go to one specific user. 14462 users = new int[] {userId}; 14463 } 14464 14465 // Figure out who all will receive this broadcast. 14466 List receivers = null; 14467 List<BroadcastFilter> registeredReceivers = null; 14468 // Need to resolve the intent to interested receivers... 14469 if ((intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) 14470 == 0) { 14471 receivers = collectReceiverComponents(intent, resolvedType, users); 14472 } 14473 if (intent.getComponent() == null) { 14474 registeredReceivers = mReceiverResolver.queryIntent(intent, 14475 resolvedType, false, userId); 14476 } 14477 14478 final boolean replacePending = 14479 (intent.getFlags()&Intent.FLAG_RECEIVER_REPLACE_PENDING) != 0; 14480 14481 if (DEBUG_BROADCAST) Slog.v(TAG, "Enqueing broadcast: " + intent.getAction() 14482 + " replacePending=" + replacePending); 14483 14484 int NR = registeredReceivers != null ? registeredReceivers.size() : 0; 14485 if (!ordered && NR > 0) { 14486 // If we are not serializing this broadcast, then send the 14487 // registered receivers separately so they don't wait for the 14488 // components to be launched. 14489 final BroadcastQueue queue = broadcastQueueForIntent(intent); 14490 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 14491 callerPackage, callingPid, callingUid, resolvedType, requiredPermission, 14492 appOp, registeredReceivers, resultTo, resultCode, resultData, map, 14493 ordered, sticky, false, userId); 14494 if (DEBUG_BROADCAST) Slog.v( 14495 TAG, "Enqueueing parallel broadcast " + r); 14496 final boolean replaced = replacePending && queue.replaceParallelBroadcastLocked(r); 14497 if (!replaced) { 14498 queue.enqueueParallelBroadcastLocked(r); 14499 queue.scheduleBroadcastsLocked(); 14500 } 14501 registeredReceivers = null; 14502 NR = 0; 14503 } 14504 14505 // Merge into one list. 14506 int ir = 0; 14507 if (receivers != null) { 14508 // A special case for PACKAGE_ADDED: do not allow the package 14509 // being added to see this broadcast. This prevents them from 14510 // using this as a back door to get run as soon as they are 14511 // installed. Maybe in the future we want to have a special install 14512 // broadcast or such for apps, but we'd like to deliberately make 14513 // this decision. 14514 String skipPackages[] = null; 14515 if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction()) 14516 || Intent.ACTION_PACKAGE_RESTARTED.equals(intent.getAction()) 14517 || Intent.ACTION_PACKAGE_DATA_CLEARED.equals(intent.getAction())) { 14518 Uri data = intent.getData(); 14519 if (data != null) { 14520 String pkgName = data.getSchemeSpecificPart(); 14521 if (pkgName != null) { 14522 skipPackages = new String[] { pkgName }; 14523 } 14524 } 14525 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction())) { 14526 skipPackages = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 14527 } 14528 if (skipPackages != null && (skipPackages.length > 0)) { 14529 for (String skipPackage : skipPackages) { 14530 if (skipPackage != null) { 14531 int NT = receivers.size(); 14532 for (int it=0; it<NT; it++) { 14533 ResolveInfo curt = (ResolveInfo)receivers.get(it); 14534 if (curt.activityInfo.packageName.equals(skipPackage)) { 14535 receivers.remove(it); 14536 it--; 14537 NT--; 14538 } 14539 } 14540 } 14541 } 14542 } 14543 14544 int NT = receivers != null ? receivers.size() : 0; 14545 int it = 0; 14546 ResolveInfo curt = null; 14547 BroadcastFilter curr = null; 14548 while (it < NT && ir < NR) { 14549 if (curt == null) { 14550 curt = (ResolveInfo)receivers.get(it); 14551 } 14552 if (curr == null) { 14553 curr = registeredReceivers.get(ir); 14554 } 14555 if (curr.getPriority() >= curt.priority) { 14556 // Insert this broadcast record into the final list. 14557 receivers.add(it, curr); 14558 ir++; 14559 curr = null; 14560 it++; 14561 NT++; 14562 } else { 14563 // Skip to the next ResolveInfo in the final list. 14564 it++; 14565 curt = null; 14566 } 14567 } 14568 } 14569 while (ir < NR) { 14570 if (receivers == null) { 14571 receivers = new ArrayList(); 14572 } 14573 receivers.add(registeredReceivers.get(ir)); 14574 ir++; 14575 } 14576 14577 if ((receivers != null && receivers.size() > 0) 14578 || resultTo != null) { 14579 BroadcastQueue queue = broadcastQueueForIntent(intent); 14580 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 14581 callerPackage, callingPid, callingUid, resolvedType, 14582 requiredPermission, appOp, receivers, resultTo, resultCode, 14583 resultData, map, ordered, sticky, false, userId); 14584 if (DEBUG_BROADCAST) Slog.v( 14585 TAG, "Enqueueing ordered broadcast " + r 14586 + ": prev had " + queue.mOrderedBroadcasts.size()); 14587 if (DEBUG_BROADCAST) { 14588 int seq = r.intent.getIntExtra("seq", -1); 14589 Slog.i(TAG, "Enqueueing broadcast " + r.intent.getAction() + " seq=" + seq); 14590 } 14591 boolean replaced = replacePending && queue.replaceOrderedBroadcastLocked(r); 14592 if (!replaced) { 14593 queue.enqueueOrderedBroadcastLocked(r); 14594 queue.scheduleBroadcastsLocked(); 14595 } 14596 } 14597 14598 return ActivityManager.BROADCAST_SUCCESS; 14599 } 14600 14601 final Intent verifyBroadcastLocked(Intent intent) { 14602 // Refuse possible leaked file descriptors 14603 if (intent != null && intent.hasFileDescriptors() == true) { 14604 throw new IllegalArgumentException("File descriptors passed in Intent"); 14605 } 14606 14607 int flags = intent.getFlags(); 14608 14609 if (!mProcessesReady) { 14610 // if the caller really truly claims to know what they're doing, go 14611 // ahead and allow the broadcast without launching any receivers 14612 if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT) != 0) { 14613 intent = new Intent(intent); 14614 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 14615 } else if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) { 14616 Slog.e(TAG, "Attempt to launch receivers of broadcast intent " + intent 14617 + " before boot completion"); 14618 throw new IllegalStateException("Cannot broadcast before boot completed"); 14619 } 14620 } 14621 14622 if ((flags&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 14623 throw new IllegalArgumentException( 14624 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 14625 } 14626 14627 return intent; 14628 } 14629 14630 public final int broadcastIntent(IApplicationThread caller, 14631 Intent intent, String resolvedType, IIntentReceiver resultTo, 14632 int resultCode, String resultData, Bundle map, 14633 String requiredPermission, int appOp, boolean serialized, boolean sticky, int userId) { 14634 enforceNotIsolatedCaller("broadcastIntent"); 14635 synchronized(this) { 14636 intent = verifyBroadcastLocked(intent); 14637 14638 final ProcessRecord callerApp = getRecordForAppLocked(caller); 14639 final int callingPid = Binder.getCallingPid(); 14640 final int callingUid = Binder.getCallingUid(); 14641 final long origId = Binder.clearCallingIdentity(); 14642 int res = broadcastIntentLocked(callerApp, 14643 callerApp != null ? callerApp.info.packageName : null, 14644 intent, resolvedType, resultTo, 14645 resultCode, resultData, map, requiredPermission, appOp, serialized, sticky, 14646 callingPid, callingUid, userId); 14647 Binder.restoreCallingIdentity(origId); 14648 return res; 14649 } 14650 } 14651 14652 int broadcastIntentInPackage(String packageName, int uid, 14653 Intent intent, String resolvedType, IIntentReceiver resultTo, 14654 int resultCode, String resultData, Bundle map, 14655 String requiredPermission, boolean serialized, boolean sticky, int userId) { 14656 synchronized(this) { 14657 intent = verifyBroadcastLocked(intent); 14658 14659 final long origId = Binder.clearCallingIdentity(); 14660 int res = broadcastIntentLocked(null, packageName, intent, resolvedType, 14661 resultTo, resultCode, resultData, map, requiredPermission, 14662 AppOpsManager.OP_NONE, serialized, sticky, -1, uid, userId); 14663 Binder.restoreCallingIdentity(origId); 14664 return res; 14665 } 14666 } 14667 14668 public final void unbroadcastIntent(IApplicationThread caller, Intent intent, int userId) { 14669 // Refuse possible leaked file descriptors 14670 if (intent != null && intent.hasFileDescriptors() == true) { 14671 throw new IllegalArgumentException("File descriptors passed in Intent"); 14672 } 14673 14674 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 14675 userId, true, ALLOW_NON_FULL, "removeStickyBroadcast", null); 14676 14677 synchronized(this) { 14678 if (checkCallingPermission(android.Manifest.permission.BROADCAST_STICKY) 14679 != PackageManager.PERMISSION_GRANTED) { 14680 String msg = "Permission Denial: unbroadcastIntent() from pid=" 14681 + Binder.getCallingPid() 14682 + ", uid=" + Binder.getCallingUid() 14683 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 14684 Slog.w(TAG, msg); 14685 throw new SecurityException(msg); 14686 } 14687 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 14688 if (stickies != null) { 14689 ArrayList<Intent> list = stickies.get(intent.getAction()); 14690 if (list != null) { 14691 int N = list.size(); 14692 int i; 14693 for (i=0; i<N; i++) { 14694 if (intent.filterEquals(list.get(i))) { 14695 list.remove(i); 14696 break; 14697 } 14698 } 14699 if (list.size() <= 0) { 14700 stickies.remove(intent.getAction()); 14701 } 14702 } 14703 if (stickies.size() <= 0) { 14704 mStickyBroadcasts.remove(userId); 14705 } 14706 } 14707 } 14708 } 14709 14710 private final boolean finishReceiverLocked(IBinder receiver, int resultCode, 14711 String resultData, Bundle resultExtras, boolean resultAbort) { 14712 final BroadcastRecord r = broadcastRecordForReceiverLocked(receiver); 14713 if (r == null) { 14714 Slog.w(TAG, "finishReceiver called but not found on queue"); 14715 return false; 14716 } 14717 14718 return r.queue.finishReceiverLocked(r, resultCode, resultData, resultExtras, resultAbort, false); 14719 } 14720 14721 void backgroundServicesFinishedLocked(int userId) { 14722 for (BroadcastQueue queue : mBroadcastQueues) { 14723 queue.backgroundServicesFinishedLocked(userId); 14724 } 14725 } 14726 14727 public void finishReceiver(IBinder who, int resultCode, String resultData, 14728 Bundle resultExtras, boolean resultAbort) { 14729 if (DEBUG_BROADCAST) Slog.v(TAG, "Finish receiver: " + who); 14730 14731 // Refuse possible leaked file descriptors 14732 if (resultExtras != null && resultExtras.hasFileDescriptors()) { 14733 throw new IllegalArgumentException("File descriptors passed in Bundle"); 14734 } 14735 14736 final long origId = Binder.clearCallingIdentity(); 14737 try { 14738 boolean doNext = false; 14739 BroadcastRecord r; 14740 14741 synchronized(this) { 14742 r = broadcastRecordForReceiverLocked(who); 14743 if (r != null) { 14744 doNext = r.queue.finishReceiverLocked(r, resultCode, 14745 resultData, resultExtras, resultAbort, true); 14746 } 14747 } 14748 14749 if (doNext) { 14750 r.queue.processNextBroadcast(false); 14751 } 14752 trimApplications(); 14753 } finally { 14754 Binder.restoreCallingIdentity(origId); 14755 } 14756 } 14757 14758 // ========================================================= 14759 // INSTRUMENTATION 14760 // ========================================================= 14761 14762 public boolean startInstrumentation(ComponentName className, 14763 String profileFile, int flags, Bundle arguments, 14764 IInstrumentationWatcher watcher, IUiAutomationConnection uiAutomationConnection, 14765 int userId, String abiOverride) { 14766 enforceNotIsolatedCaller("startInstrumentation"); 14767 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 14768 userId, false, ALLOW_FULL_ONLY, "startInstrumentation", null); 14769 // Refuse possible leaked file descriptors 14770 if (arguments != null && arguments.hasFileDescriptors()) { 14771 throw new IllegalArgumentException("File descriptors passed in Bundle"); 14772 } 14773 14774 synchronized(this) { 14775 InstrumentationInfo ii = null; 14776 ApplicationInfo ai = null; 14777 try { 14778 ii = mContext.getPackageManager().getInstrumentationInfo( 14779 className, STOCK_PM_FLAGS); 14780 ai = AppGlobals.getPackageManager().getApplicationInfo( 14781 ii.targetPackage, STOCK_PM_FLAGS, userId); 14782 } catch (PackageManager.NameNotFoundException e) { 14783 } catch (RemoteException e) { 14784 } 14785 if (ii == null) { 14786 reportStartInstrumentationFailure(watcher, className, 14787 "Unable to find instrumentation info for: " + className); 14788 return false; 14789 } 14790 if (ai == null) { 14791 reportStartInstrumentationFailure(watcher, className, 14792 "Unable to find instrumentation target package: " + ii.targetPackage); 14793 return false; 14794 } 14795 14796 int match = mContext.getPackageManager().checkSignatures( 14797 ii.targetPackage, ii.packageName); 14798 if (match < 0 && match != PackageManager.SIGNATURE_FIRST_NOT_SIGNED) { 14799 String msg = "Permission Denial: starting instrumentation " 14800 + className + " from pid=" 14801 + Binder.getCallingPid() 14802 + ", uid=" + Binder.getCallingPid() 14803 + " not allowed because package " + ii.packageName 14804 + " does not have a signature matching the target " 14805 + ii.targetPackage; 14806 reportStartInstrumentationFailure(watcher, className, msg); 14807 throw new SecurityException(msg); 14808 } 14809 14810 final long origId = Binder.clearCallingIdentity(); 14811 // Instrumentation can kill and relaunch even persistent processes 14812 forceStopPackageLocked(ii.targetPackage, -1, true, false, true, true, false, userId, 14813 "start instr"); 14814 ProcessRecord app = addAppLocked(ai, false, abiOverride); 14815 app.instrumentationClass = className; 14816 app.instrumentationInfo = ai; 14817 app.instrumentationProfileFile = profileFile; 14818 app.instrumentationArguments = arguments; 14819 app.instrumentationWatcher = watcher; 14820 app.instrumentationUiAutomationConnection = uiAutomationConnection; 14821 app.instrumentationResultClass = className; 14822 Binder.restoreCallingIdentity(origId); 14823 } 14824 14825 return true; 14826 } 14827 14828 /** 14829 * Report errors that occur while attempting to start Instrumentation. Always writes the 14830 * error to the logs, but if somebody is watching, send the report there too. This enables 14831 * the "am" command to report errors with more information. 14832 * 14833 * @param watcher The IInstrumentationWatcher. Null if there isn't one. 14834 * @param cn The component name of the instrumentation. 14835 * @param report The error report. 14836 */ 14837 private void reportStartInstrumentationFailure(IInstrumentationWatcher watcher, 14838 ComponentName cn, String report) { 14839 Slog.w(TAG, report); 14840 try { 14841 if (watcher != null) { 14842 Bundle results = new Bundle(); 14843 results.putString(Instrumentation.REPORT_KEY_IDENTIFIER, "ActivityManagerService"); 14844 results.putString("Error", report); 14845 watcher.instrumentationStatus(cn, -1, results); 14846 } 14847 } catch (RemoteException e) { 14848 Slog.w(TAG, e); 14849 } 14850 } 14851 14852 void finishInstrumentationLocked(ProcessRecord app, int resultCode, Bundle results) { 14853 if (app.instrumentationWatcher != null) { 14854 try { 14855 // NOTE: IInstrumentationWatcher *must* be oneway here 14856 app.instrumentationWatcher.instrumentationFinished( 14857 app.instrumentationClass, 14858 resultCode, 14859 results); 14860 } catch (RemoteException e) { 14861 } 14862 } 14863 if (app.instrumentationUiAutomationConnection != null) { 14864 try { 14865 app.instrumentationUiAutomationConnection.shutdown(); 14866 } catch (RemoteException re) { 14867 /* ignore */ 14868 } 14869 // Only a UiAutomation can set this flag and now that 14870 // it is finished we make sure it is reset to its default. 14871 mUserIsMonkey = false; 14872 } 14873 app.instrumentationWatcher = null; 14874 app.instrumentationUiAutomationConnection = null; 14875 app.instrumentationClass = null; 14876 app.instrumentationInfo = null; 14877 app.instrumentationProfileFile = null; 14878 app.instrumentationArguments = null; 14879 14880 forceStopPackageLocked(app.info.packageName, -1, false, false, true, true, false, app.userId, 14881 "finished inst"); 14882 } 14883 14884 public void finishInstrumentation(IApplicationThread target, 14885 int resultCode, Bundle results) { 14886 int userId = UserHandle.getCallingUserId(); 14887 // Refuse possible leaked file descriptors 14888 if (results != null && results.hasFileDescriptors()) { 14889 throw new IllegalArgumentException("File descriptors passed in Intent"); 14890 } 14891 14892 synchronized(this) { 14893 ProcessRecord app = getRecordForAppLocked(target); 14894 if (app == null) { 14895 Slog.w(TAG, "finishInstrumentation: no app for " + target); 14896 return; 14897 } 14898 final long origId = Binder.clearCallingIdentity(); 14899 finishInstrumentationLocked(app, resultCode, results); 14900 Binder.restoreCallingIdentity(origId); 14901 } 14902 } 14903 14904 // ========================================================= 14905 // CONFIGURATION 14906 // ========================================================= 14907 14908 public ConfigurationInfo getDeviceConfigurationInfo() { 14909 ConfigurationInfo config = new ConfigurationInfo(); 14910 synchronized (this) { 14911 config.reqTouchScreen = mConfiguration.touchscreen; 14912 config.reqKeyboardType = mConfiguration.keyboard; 14913 config.reqNavigation = mConfiguration.navigation; 14914 if (mConfiguration.navigation == Configuration.NAVIGATION_DPAD 14915 || mConfiguration.navigation == Configuration.NAVIGATION_TRACKBALL) { 14916 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_FIVE_WAY_NAV; 14917 } 14918 if (mConfiguration.keyboard != Configuration.KEYBOARD_UNDEFINED 14919 && mConfiguration.keyboard != Configuration.KEYBOARD_NOKEYS) { 14920 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_HARD_KEYBOARD; 14921 } 14922 config.reqGlEsVersion = GL_ES_VERSION; 14923 } 14924 return config; 14925 } 14926 14927 ActivityStack getFocusedStack() { 14928 return mStackSupervisor.getFocusedStack(); 14929 } 14930 14931 public Configuration getConfiguration() { 14932 Configuration ci; 14933 synchronized(this) { 14934 ci = new Configuration(mConfiguration); 14935 } 14936 return ci; 14937 } 14938 14939 public void updatePersistentConfiguration(Configuration values) { 14940 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 14941 "updateConfiguration()"); 14942 enforceCallingPermission(android.Manifest.permission.WRITE_SETTINGS, 14943 "updateConfiguration()"); 14944 if (values == null) { 14945 throw new NullPointerException("Configuration must not be null"); 14946 } 14947 14948 synchronized(this) { 14949 final long origId = Binder.clearCallingIdentity(); 14950 updateConfigurationLocked(values, null, true, false); 14951 Binder.restoreCallingIdentity(origId); 14952 } 14953 } 14954 14955 public void updateConfiguration(Configuration values) { 14956 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 14957 "updateConfiguration()"); 14958 14959 synchronized(this) { 14960 if (values == null && mWindowManager != null) { 14961 // sentinel: fetch the current configuration from the window manager 14962 values = mWindowManager.computeNewConfiguration(); 14963 } 14964 14965 if (mWindowManager != null) { 14966 mProcessList.applyDisplaySize(mWindowManager); 14967 } 14968 14969 final long origId = Binder.clearCallingIdentity(); 14970 if (values != null) { 14971 Settings.System.clearConfiguration(values); 14972 } 14973 updateConfigurationLocked(values, null, false, false); 14974 Binder.restoreCallingIdentity(origId); 14975 } 14976 } 14977 14978 /** 14979 * Do either or both things: (1) change the current configuration, and (2) 14980 * make sure the given activity is running with the (now) current 14981 * configuration. Returns true if the activity has been left running, or 14982 * false if <var>starting</var> is being destroyed to match the new 14983 * configuration. 14984 * @param persistent TODO 14985 */ 14986 boolean updateConfigurationLocked(Configuration values, 14987 ActivityRecord starting, boolean persistent, boolean initLocale) { 14988 int changes = 0; 14989 14990 if (values != null) { 14991 Configuration newConfig = new Configuration(mConfiguration); 14992 changes = newConfig.updateFrom(values); 14993 if (changes != 0) { 14994 if (DEBUG_SWITCH || DEBUG_CONFIGURATION) { 14995 Slog.i(TAG, "Updating configuration to: " + values); 14996 } 14997 14998 EventLog.writeEvent(EventLogTags.CONFIGURATION_CHANGED, changes); 14999 15000 if (values.locale != null && !initLocale) { 15001 saveLocaleLocked(values.locale, 15002 !values.locale.equals(mConfiguration.locale), 15003 values.userSetLocale); 15004 } 15005 15006 mConfigurationSeq++; 15007 if (mConfigurationSeq <= 0) { 15008 mConfigurationSeq = 1; 15009 } 15010 newConfig.seq = mConfigurationSeq; 15011 mConfiguration = newConfig; 15012 Slog.i(TAG, "Config changes=" + Integer.toHexString(changes) + " " + newConfig); 15013 mUsageStatsService.noteStartConfig(newConfig); 15014 15015 final Configuration configCopy = new Configuration(mConfiguration); 15016 15017 // TODO: If our config changes, should we auto dismiss any currently 15018 // showing dialogs? 15019 mShowDialogs = shouldShowDialogs(newConfig); 15020 15021 AttributeCache ac = AttributeCache.instance(); 15022 if (ac != null) { 15023 ac.updateConfiguration(configCopy); 15024 } 15025 15026 // Make sure all resources in our process are updated 15027 // right now, so that anyone who is going to retrieve 15028 // resource values after we return will be sure to get 15029 // the new ones. This is especially important during 15030 // boot, where the first config change needs to guarantee 15031 // all resources have that config before following boot 15032 // code is executed. 15033 mSystemThread.applyConfigurationToResources(configCopy); 15034 15035 if (persistent && Settings.System.hasInterestingConfigurationChanges(changes)) { 15036 Message msg = mHandler.obtainMessage(UPDATE_CONFIGURATION_MSG); 15037 msg.obj = new Configuration(configCopy); 15038 mHandler.sendMessage(msg); 15039 } 15040 15041 for (int i=mLruProcesses.size()-1; i>=0; i--) { 15042 ProcessRecord app = mLruProcesses.get(i); 15043 try { 15044 if (app.thread != null) { 15045 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Sending to proc " 15046 + app.processName + " new config " + mConfiguration); 15047 app.thread.scheduleConfigurationChanged(configCopy); 15048 } 15049 } catch (Exception e) { 15050 } 15051 } 15052 Intent intent = new Intent(Intent.ACTION_CONFIGURATION_CHANGED); 15053 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 15054 | Intent.FLAG_RECEIVER_REPLACE_PENDING 15055 | Intent.FLAG_RECEIVER_FOREGROUND); 15056 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, 15057 null, AppOpsManager.OP_NONE, false, false, MY_PID, 15058 Process.SYSTEM_UID, UserHandle.USER_ALL); 15059 if ((changes&ActivityInfo.CONFIG_LOCALE) != 0) { 15060 intent = new Intent(Intent.ACTION_LOCALE_CHANGED); 15061 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 15062 broadcastIntentLocked(null, null, intent, 15063 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 15064 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 15065 } 15066 } 15067 } 15068 15069 boolean kept = true; 15070 final ActivityStack mainStack = mStackSupervisor.getFocusedStack(); 15071 // mainStack is null during startup. 15072 if (mainStack != null) { 15073 if (changes != 0 && starting == null) { 15074 // If the configuration changed, and the caller is not already 15075 // in the process of starting an activity, then find the top 15076 // activity to check if its configuration needs to change. 15077 starting = mainStack.topRunningActivityLocked(null); 15078 } 15079 15080 if (starting != null) { 15081 kept = mainStack.ensureActivityConfigurationLocked(starting, changes); 15082 // And we need to make sure at this point that all other activities 15083 // are made visible with the correct configuration. 15084 mStackSupervisor.ensureActivitiesVisibleLocked(starting, changes); 15085 } 15086 } 15087 15088 if (values != null && mWindowManager != null) { 15089 mWindowManager.setNewConfiguration(mConfiguration); 15090 } 15091 15092 return kept; 15093 } 15094 15095 /** 15096 * Decide based on the configuration whether we should shouw the ANR, 15097 * crash, etc dialogs. The idea is that if there is no affordnace to 15098 * press the on-screen buttons, we shouldn't show the dialog. 15099 * 15100 * A thought: SystemUI might also want to get told about this, the Power 15101 * dialog / global actions also might want different behaviors. 15102 */ 15103 private static final boolean shouldShowDialogs(Configuration config) { 15104 return !(config.keyboard == Configuration.KEYBOARD_NOKEYS 15105 && config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH); 15106 } 15107 15108 /** 15109 * Save the locale. You must be inside a synchronized (this) block. 15110 */ 15111 private void saveLocaleLocked(Locale l, boolean isDiff, boolean isPersist) { 15112 if(isDiff) { 15113 SystemProperties.set("user.language", l.getLanguage()); 15114 SystemProperties.set("user.region", l.getCountry()); 15115 } 15116 15117 if(isPersist) { 15118 SystemProperties.set("persist.sys.language", l.getLanguage()); 15119 SystemProperties.set("persist.sys.country", l.getCountry()); 15120 SystemProperties.set("persist.sys.localevar", l.getVariant()); 15121 } 15122 } 15123 15124 @Override 15125 public boolean targetTaskAffinityMatchesActivity(IBinder token, String destAffinity) { 15126 ActivityRecord srec = ActivityRecord.forToken(token); 15127 return srec != null && srec.task.affinity != null && 15128 srec.task.affinity.equals(destAffinity); 15129 } 15130 15131 public boolean navigateUpTo(IBinder token, Intent destIntent, int resultCode, 15132 Intent resultData) { 15133 15134 synchronized (this) { 15135 final ActivityStack stack = ActivityRecord.getStackLocked(token); 15136 if (stack != null) { 15137 return stack.navigateUpToLocked(token, destIntent, resultCode, resultData); 15138 } 15139 return false; 15140 } 15141 } 15142 15143 public int getLaunchedFromUid(IBinder activityToken) { 15144 ActivityRecord srec = ActivityRecord.forToken(activityToken); 15145 if (srec == null) { 15146 return -1; 15147 } 15148 return srec.launchedFromUid; 15149 } 15150 15151 public String getLaunchedFromPackage(IBinder activityToken) { 15152 ActivityRecord srec = ActivityRecord.forToken(activityToken); 15153 if (srec == null) { 15154 return null; 15155 } 15156 return srec.launchedFromPackage; 15157 } 15158 15159 // ========================================================= 15160 // LIFETIME MANAGEMENT 15161 // ========================================================= 15162 15163 // Returns which broadcast queue the app is the current [or imminent] receiver 15164 // on, or 'null' if the app is not an active broadcast recipient. 15165 private BroadcastQueue isReceivingBroadcast(ProcessRecord app) { 15166 BroadcastRecord r = app.curReceiver; 15167 if (r != null) { 15168 return r.queue; 15169 } 15170 15171 // It's not the current receiver, but it might be starting up to become one 15172 synchronized (this) { 15173 for (BroadcastQueue queue : mBroadcastQueues) { 15174 r = queue.mPendingBroadcast; 15175 if (r != null && r.curApp == app) { 15176 // found it; report which queue it's in 15177 return queue; 15178 } 15179 } 15180 } 15181 15182 return null; 15183 } 15184 15185 private final int computeOomAdjLocked(ProcessRecord app, int cachedAdj, ProcessRecord TOP_APP, 15186 boolean doingAll, long now) { 15187 if (mAdjSeq == app.adjSeq) { 15188 // This adjustment has already been computed. 15189 return app.curRawAdj; 15190 } 15191 15192 if (app.thread == null) { 15193 app.adjSeq = mAdjSeq; 15194 app.curSchedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15195 app.curProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15196 return (app.curAdj=app.curRawAdj=ProcessList.CACHED_APP_MAX_ADJ); 15197 } 15198 15199 app.adjTypeCode = ActivityManager.RunningAppProcessInfo.REASON_UNKNOWN; 15200 app.adjSource = null; 15201 app.adjTarget = null; 15202 app.empty = false; 15203 app.cached = false; 15204 15205 final int activitiesSize = app.activities.size(); 15206 15207 if (app.maxAdj <= ProcessList.FOREGROUND_APP_ADJ) { 15208 // The max adjustment doesn't allow this app to be anything 15209 // below foreground, so it is not worth doing work for it. 15210 app.adjType = "fixed"; 15211 app.adjSeq = mAdjSeq; 15212 app.curRawAdj = app.maxAdj; 15213 app.foregroundActivities = false; 15214 app.curSchedGroup = Process.THREAD_GROUP_DEFAULT; 15215 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT; 15216 // System processes can do UI, and when they do we want to have 15217 // them trim their memory after the user leaves the UI. To 15218 // facilitate this, here we need to determine whether or not it 15219 // is currently showing UI. 15220 app.systemNoUi = true; 15221 if (app == TOP_APP) { 15222 app.systemNoUi = false; 15223 } else if (activitiesSize > 0) { 15224 for (int j = 0; j < activitiesSize; j++) { 15225 final ActivityRecord r = app.activities.get(j); 15226 if (r.visible) { 15227 app.systemNoUi = false; 15228 } 15229 } 15230 } 15231 if (!app.systemNoUi) { 15232 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT_UI; 15233 } 15234 return (app.curAdj=app.maxAdj); 15235 } 15236 15237 app.systemNoUi = false; 15238 15239 // Determine the importance of the process, starting with most 15240 // important to least, and assign an appropriate OOM adjustment. 15241 int adj; 15242 int schedGroup; 15243 int procState; 15244 boolean foregroundActivities = false; 15245 BroadcastQueue queue; 15246 if (app == TOP_APP) { 15247 // The last app on the list is the foreground app. 15248 adj = ProcessList.FOREGROUND_APP_ADJ; 15249 schedGroup = Process.THREAD_GROUP_DEFAULT; 15250 app.adjType = "top-activity"; 15251 foregroundActivities = true; 15252 procState = ActivityManager.PROCESS_STATE_TOP; 15253 } else if (app.instrumentationClass != null) { 15254 // Don't want to kill running instrumentation. 15255 adj = ProcessList.FOREGROUND_APP_ADJ; 15256 schedGroup = Process.THREAD_GROUP_DEFAULT; 15257 app.adjType = "instrumentation"; 15258 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15259 } else if ((queue = isReceivingBroadcast(app)) != null) { 15260 // An app that is currently receiving a broadcast also 15261 // counts as being in the foreground for OOM killer purposes. 15262 // It's placed in a sched group based on the nature of the 15263 // broadcast as reflected by which queue it's active in. 15264 adj = ProcessList.FOREGROUND_APP_ADJ; 15265 schedGroup = (queue == mFgBroadcastQueue) 15266 ? Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 15267 app.adjType = "broadcast"; 15268 procState = ActivityManager.PROCESS_STATE_RECEIVER; 15269 } else if (app.executingServices.size() > 0) { 15270 // An app that is currently executing a service callback also 15271 // counts as being in the foreground. 15272 adj = ProcessList.FOREGROUND_APP_ADJ; 15273 schedGroup = app.execServicesFg ? 15274 Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 15275 app.adjType = "exec-service"; 15276 procState = ActivityManager.PROCESS_STATE_SERVICE; 15277 //Slog.i(TAG, "EXEC " + (app.execServicesFg ? "FG" : "BG") + ": " + app); 15278 } else { 15279 // As far as we know the process is empty. We may change our mind later. 15280 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15281 // At this point we don't actually know the adjustment. Use the cached adj 15282 // value that the caller wants us to. 15283 adj = cachedAdj; 15284 procState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15285 app.cached = true; 15286 app.empty = true; 15287 app.adjType = "cch-empty"; 15288 } 15289 15290 // Examine all activities if not already foreground. 15291 if (!foregroundActivities && activitiesSize > 0) { 15292 for (int j = 0; j < activitiesSize; j++) { 15293 final ActivityRecord r = app.activities.get(j); 15294 if (r.app != app) { 15295 Slog.w(TAG, "Wtf, activity " + r + " in proc activity list not using proc " 15296 + app + "?!?"); 15297 continue; 15298 } 15299 if (r.visible) { 15300 // App has a visible activity; only upgrade adjustment. 15301 if (adj > ProcessList.VISIBLE_APP_ADJ) { 15302 adj = ProcessList.VISIBLE_APP_ADJ; 15303 app.adjType = "visible"; 15304 } 15305 if (procState > ActivityManager.PROCESS_STATE_TOP) { 15306 procState = ActivityManager.PROCESS_STATE_TOP; 15307 } 15308 schedGroup = Process.THREAD_GROUP_DEFAULT; 15309 app.cached = false; 15310 app.empty = false; 15311 foregroundActivities = true; 15312 break; 15313 } else if (r.state == ActivityState.PAUSING || r.state == ActivityState.PAUSED) { 15314 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15315 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15316 app.adjType = "pausing"; 15317 } 15318 if (procState > ActivityManager.PROCESS_STATE_TOP) { 15319 procState = ActivityManager.PROCESS_STATE_TOP; 15320 } 15321 schedGroup = Process.THREAD_GROUP_DEFAULT; 15322 app.cached = false; 15323 app.empty = false; 15324 foregroundActivities = true; 15325 } else if (r.state == ActivityState.STOPPING) { 15326 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15327 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15328 app.adjType = "stopping"; 15329 } 15330 // For the process state, we will at this point consider the 15331 // process to be cached. It will be cached either as an activity 15332 // or empty depending on whether the activity is finishing. We do 15333 // this so that we can treat the process as cached for purposes of 15334 // memory trimming (determing current memory level, trim command to 15335 // send to process) since there can be an arbitrary number of stopping 15336 // processes and they should soon all go into the cached state. 15337 if (!r.finishing) { 15338 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15339 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 15340 } 15341 } 15342 app.cached = false; 15343 app.empty = false; 15344 foregroundActivities = true; 15345 } else { 15346 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15347 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 15348 app.adjType = "cch-act"; 15349 } 15350 } 15351 } 15352 } 15353 15354 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15355 if (app.foregroundServices) { 15356 // The user is aware of this app, so make it visible. 15357 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15358 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15359 app.cached = false; 15360 app.adjType = "fg-service"; 15361 schedGroup = Process.THREAD_GROUP_DEFAULT; 15362 } else if (app.forcingToForeground != null) { 15363 // The user is aware of this app, so make it visible. 15364 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15365 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15366 app.cached = false; 15367 app.adjType = "force-fg"; 15368 app.adjSource = app.forcingToForeground; 15369 schedGroup = Process.THREAD_GROUP_DEFAULT; 15370 } 15371 } 15372 15373 if (app == mHeavyWeightProcess) { 15374 if (adj > ProcessList.HEAVY_WEIGHT_APP_ADJ) { 15375 // We don't want to kill the current heavy-weight process. 15376 adj = ProcessList.HEAVY_WEIGHT_APP_ADJ; 15377 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15378 app.cached = false; 15379 app.adjType = "heavy"; 15380 } 15381 if (procState > ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 15382 procState = ActivityManager.PROCESS_STATE_HEAVY_WEIGHT; 15383 } 15384 } 15385 15386 if (app == mHomeProcess) { 15387 if (adj > ProcessList.HOME_APP_ADJ) { 15388 // This process is hosting what we currently consider to be the 15389 // home app, so we don't want to let it go into the background. 15390 adj = ProcessList.HOME_APP_ADJ; 15391 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15392 app.cached = false; 15393 app.adjType = "home"; 15394 } 15395 if (procState > ActivityManager.PROCESS_STATE_HOME) { 15396 procState = ActivityManager.PROCESS_STATE_HOME; 15397 } 15398 } 15399 15400 if (app == mPreviousProcess && app.activities.size() > 0) { 15401 if (adj > ProcessList.PREVIOUS_APP_ADJ) { 15402 // This was the previous process that showed UI to the user. 15403 // We want to try to keep it around more aggressively, to give 15404 // a good experience around switching between two apps. 15405 adj = ProcessList.PREVIOUS_APP_ADJ; 15406 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15407 app.cached = false; 15408 app.adjType = "previous"; 15409 } 15410 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 15411 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 15412 } 15413 } 15414 15415 if (false) Slog.i(TAG, "OOM " + app + ": initial adj=" + adj 15416 + " reason=" + app.adjType); 15417 15418 // By default, we use the computed adjustment. It may be changed if 15419 // there are applications dependent on our services or providers, but 15420 // this gives us a baseline and makes sure we don't get into an 15421 // infinite recursion. 15422 app.adjSeq = mAdjSeq; 15423 app.curRawAdj = adj; 15424 app.hasStartedServices = false; 15425 15426 if (mBackupTarget != null && app == mBackupTarget.app) { 15427 // If possible we want to avoid killing apps while they're being backed up 15428 if (adj > ProcessList.BACKUP_APP_ADJ) { 15429 if (DEBUG_BACKUP) Slog.v(TAG, "oom BACKUP_APP_ADJ for " + app); 15430 adj = ProcessList.BACKUP_APP_ADJ; 15431 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 15432 procState = ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 15433 } 15434 app.adjType = "backup"; 15435 app.cached = false; 15436 } 15437 if (procState > ActivityManager.PROCESS_STATE_BACKUP) { 15438 procState = ActivityManager.PROCESS_STATE_BACKUP; 15439 } 15440 } 15441 15442 boolean mayBeTop = false; 15443 15444 for (int is = app.services.size()-1; 15445 is >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15446 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15447 || procState > ActivityManager.PROCESS_STATE_TOP); 15448 is--) { 15449 ServiceRecord s = app.services.valueAt(is); 15450 if (s.startRequested) { 15451 app.hasStartedServices = true; 15452 if (procState > ActivityManager.PROCESS_STATE_SERVICE) { 15453 procState = ActivityManager.PROCESS_STATE_SERVICE; 15454 } 15455 if (app.hasShownUi && app != mHomeProcess) { 15456 // If this process has shown some UI, let it immediately 15457 // go to the LRU list because it may be pretty heavy with 15458 // UI stuff. We'll tag it with a label just to help 15459 // debug and understand what is going on. 15460 if (adj > ProcessList.SERVICE_ADJ) { 15461 app.adjType = "cch-started-ui-services"; 15462 } 15463 } else { 15464 if (now < (s.lastActivity + ActiveServices.MAX_SERVICE_INACTIVITY)) { 15465 // This service has seen some activity within 15466 // recent memory, so we will keep its process ahead 15467 // of the background processes. 15468 if (adj > ProcessList.SERVICE_ADJ) { 15469 adj = ProcessList.SERVICE_ADJ; 15470 app.adjType = "started-services"; 15471 app.cached = false; 15472 } 15473 } 15474 // If we have let the service slide into the background 15475 // state, still have some text describing what it is doing 15476 // even though the service no longer has an impact. 15477 if (adj > ProcessList.SERVICE_ADJ) { 15478 app.adjType = "cch-started-services"; 15479 } 15480 } 15481 } 15482 for (int conni = s.connections.size()-1; 15483 conni >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15484 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15485 || procState > ActivityManager.PROCESS_STATE_TOP); 15486 conni--) { 15487 ArrayList<ConnectionRecord> clist = s.connections.valueAt(conni); 15488 for (int i = 0; 15489 i < clist.size() && (adj > ProcessList.FOREGROUND_APP_ADJ 15490 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15491 || procState > ActivityManager.PROCESS_STATE_TOP); 15492 i++) { 15493 // XXX should compute this based on the max of 15494 // all connected clients. 15495 ConnectionRecord cr = clist.get(i); 15496 if (cr.binding.client == app) { 15497 // Binding to ourself is not interesting. 15498 continue; 15499 } 15500 if ((cr.flags&Context.BIND_WAIVE_PRIORITY) == 0) { 15501 ProcessRecord client = cr.binding.client; 15502 int clientAdj = computeOomAdjLocked(client, cachedAdj, 15503 TOP_APP, doingAll, now); 15504 int clientProcState = client.curProcState; 15505 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15506 // If the other app is cached for any reason, for purposes here 15507 // we are going to consider it empty. The specific cached state 15508 // doesn't propagate except under certain conditions. 15509 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15510 } 15511 String adjType = null; 15512 if ((cr.flags&Context.BIND_ALLOW_OOM_MANAGEMENT) != 0) { 15513 // Not doing bind OOM management, so treat 15514 // this guy more like a started service. 15515 if (app.hasShownUi && app != mHomeProcess) { 15516 // If this process has shown some UI, let it immediately 15517 // go to the LRU list because it may be pretty heavy with 15518 // UI stuff. We'll tag it with a label just to help 15519 // debug and understand what is going on. 15520 if (adj > clientAdj) { 15521 adjType = "cch-bound-ui-services"; 15522 } 15523 app.cached = false; 15524 clientAdj = adj; 15525 clientProcState = procState; 15526 } else { 15527 if (now >= (s.lastActivity 15528 + ActiveServices.MAX_SERVICE_INACTIVITY)) { 15529 // This service has not seen activity within 15530 // recent memory, so allow it to drop to the 15531 // LRU list if there is no other reason to keep 15532 // it around. We'll also tag it with a label just 15533 // to help debug and undertand what is going on. 15534 if (adj > clientAdj) { 15535 adjType = "cch-bound-services"; 15536 } 15537 clientAdj = adj; 15538 } 15539 } 15540 } 15541 if (adj > clientAdj) { 15542 // If this process has recently shown UI, and 15543 // the process that is binding to it is less 15544 // important than being visible, then we don't 15545 // care about the binding as much as we care 15546 // about letting this process get into the LRU 15547 // list to be killed and restarted if needed for 15548 // memory. 15549 if (app.hasShownUi && app != mHomeProcess 15550 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15551 adjType = "cch-bound-ui-services"; 15552 } else { 15553 if ((cr.flags&(Context.BIND_ABOVE_CLIENT 15554 |Context.BIND_IMPORTANT)) != 0) { 15555 adj = clientAdj; 15556 } else if ((cr.flags&Context.BIND_NOT_VISIBLE) != 0 15557 && clientAdj < ProcessList.PERCEPTIBLE_APP_ADJ 15558 && adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15559 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15560 } else if (clientAdj > ProcessList.VISIBLE_APP_ADJ) { 15561 adj = clientAdj; 15562 } else { 15563 if (adj > ProcessList.VISIBLE_APP_ADJ) { 15564 adj = ProcessList.VISIBLE_APP_ADJ; 15565 } 15566 } 15567 if (!client.cached) { 15568 app.cached = false; 15569 } 15570 adjType = "service"; 15571 } 15572 } 15573 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 15574 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 15575 schedGroup = Process.THREAD_GROUP_DEFAULT; 15576 } 15577 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 15578 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 15579 // Special handling of clients who are in the top state. 15580 // We *may* want to consider this process to be in the 15581 // top state as well, but only if there is not another 15582 // reason for it to be running. Being on the top is a 15583 // special state, meaning you are specifically running 15584 // for the current top app. If the process is already 15585 // running in the background for some other reason, it 15586 // is more important to continue considering it to be 15587 // in the background state. 15588 mayBeTop = true; 15589 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15590 } else { 15591 // Special handling for above-top states (persistent 15592 // processes). These should not bring the current process 15593 // into the top state, since they are not on top. Instead 15594 // give them the best state after that. 15595 clientProcState = 15596 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15597 } 15598 } 15599 } else { 15600 if (clientProcState < 15601 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 15602 clientProcState = 15603 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 15604 } 15605 } 15606 if (procState > clientProcState) { 15607 procState = clientProcState; 15608 } 15609 if (procState < ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 15610 && (cr.flags&Context.BIND_SHOWING_UI) != 0) { 15611 app.pendingUiClean = true; 15612 } 15613 if (adjType != null) { 15614 app.adjType = adjType; 15615 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15616 .REASON_SERVICE_IN_USE; 15617 app.adjSource = cr.binding.client; 15618 app.adjSourceOom = clientAdj; 15619 app.adjTarget = s.name; 15620 } 15621 } 15622 if ((cr.flags&Context.BIND_TREAT_LIKE_ACTIVITY) != 0) { 15623 app.treatLikeActivity = true; 15624 } 15625 final ActivityRecord a = cr.activity; 15626 if ((cr.flags&Context.BIND_ADJUST_WITH_ACTIVITY) != 0) { 15627 if (a != null && adj > ProcessList.FOREGROUND_APP_ADJ && 15628 (a.visible || a.state == ActivityState.RESUMED 15629 || a.state == ActivityState.PAUSING)) { 15630 adj = ProcessList.FOREGROUND_APP_ADJ; 15631 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 15632 schedGroup = Process.THREAD_GROUP_DEFAULT; 15633 } 15634 app.cached = false; 15635 app.adjType = "service"; 15636 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15637 .REASON_SERVICE_IN_USE; 15638 app.adjSource = a; 15639 app.adjSourceOom = adj; 15640 app.adjTarget = s.name; 15641 } 15642 } 15643 } 15644 } 15645 } 15646 15647 for (int provi = app.pubProviders.size()-1; 15648 provi >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15649 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15650 || procState > ActivityManager.PROCESS_STATE_TOP); 15651 provi--) { 15652 ContentProviderRecord cpr = app.pubProviders.valueAt(provi); 15653 for (int i = cpr.connections.size()-1; 15654 i >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15655 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15656 || procState > ActivityManager.PROCESS_STATE_TOP); 15657 i--) { 15658 ContentProviderConnection conn = cpr.connections.get(i); 15659 ProcessRecord client = conn.client; 15660 if (client == app) { 15661 // Being our own client is not interesting. 15662 continue; 15663 } 15664 int clientAdj = computeOomAdjLocked(client, cachedAdj, TOP_APP, doingAll, now); 15665 int clientProcState = client.curProcState; 15666 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15667 // If the other app is cached for any reason, for purposes here 15668 // we are going to consider it empty. 15669 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15670 } 15671 if (adj > clientAdj) { 15672 if (app.hasShownUi && app != mHomeProcess 15673 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15674 app.adjType = "cch-ui-provider"; 15675 } else { 15676 adj = clientAdj > ProcessList.FOREGROUND_APP_ADJ 15677 ? clientAdj : ProcessList.FOREGROUND_APP_ADJ; 15678 app.adjType = "provider"; 15679 } 15680 app.cached &= client.cached; 15681 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15682 .REASON_PROVIDER_IN_USE; 15683 app.adjSource = client; 15684 app.adjSourceOom = clientAdj; 15685 app.adjTarget = cpr.name; 15686 } 15687 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 15688 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 15689 // Special handling of clients who are in the top state. 15690 // We *may* want to consider this process to be in the 15691 // top state as well, but only if there is not another 15692 // reason for it to be running. Being on the top is a 15693 // special state, meaning you are specifically running 15694 // for the current top app. If the process is already 15695 // running in the background for some other reason, it 15696 // is more important to continue considering it to be 15697 // in the background state. 15698 mayBeTop = true; 15699 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15700 } else { 15701 // Special handling for above-top states (persistent 15702 // processes). These should not bring the current process 15703 // into the top state, since they are not on top. Instead 15704 // give them the best state after that. 15705 clientProcState = 15706 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15707 } 15708 } 15709 if (procState > clientProcState) { 15710 procState = clientProcState; 15711 } 15712 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 15713 schedGroup = Process.THREAD_GROUP_DEFAULT; 15714 } 15715 } 15716 // If the provider has external (non-framework) process 15717 // dependencies, ensure that its adjustment is at least 15718 // FOREGROUND_APP_ADJ. 15719 if (cpr.hasExternalProcessHandles()) { 15720 if (adj > ProcessList.FOREGROUND_APP_ADJ) { 15721 adj = ProcessList.FOREGROUND_APP_ADJ; 15722 schedGroup = Process.THREAD_GROUP_DEFAULT; 15723 app.cached = false; 15724 app.adjType = "provider"; 15725 app.adjTarget = cpr.name; 15726 } 15727 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) { 15728 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15729 } 15730 } 15731 } 15732 15733 if (mayBeTop && procState > ActivityManager.PROCESS_STATE_TOP) { 15734 // A client of one of our services or providers is in the top state. We 15735 // *may* want to be in the top state, but not if we are already running in 15736 // the background for some other reason. For the decision here, we are going 15737 // to pick out a few specific states that we want to remain in when a client 15738 // is top (states that tend to be longer-term) and otherwise allow it to go 15739 // to the top state. 15740 switch (procState) { 15741 case ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND: 15742 case ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND: 15743 case ActivityManager.PROCESS_STATE_SERVICE: 15744 // These all are longer-term states, so pull them up to the top 15745 // of the background states, but not all the way to the top state. 15746 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15747 break; 15748 default: 15749 // Otherwise, top is a better choice, so take it. 15750 procState = ActivityManager.PROCESS_STATE_TOP; 15751 break; 15752 } 15753 } 15754 15755 if (procState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 15756 if (app.hasClientActivities) { 15757 // This is a cached process, but with client activities. Mark it so. 15758 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT; 15759 app.adjType = "cch-client-act"; 15760 } else if (app.treatLikeActivity) { 15761 // This is a cached process, but somebody wants us to treat it like it has 15762 // an activity, okay! 15763 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 15764 app.adjType = "cch-as-act"; 15765 } 15766 } 15767 15768 if (adj == ProcessList.SERVICE_ADJ) { 15769 if (doingAll) { 15770 app.serviceb = mNewNumAServiceProcs > (mNumServiceProcs/3); 15771 mNewNumServiceProcs++; 15772 //Slog.i(TAG, "ADJ " + app + " serviceb=" + app.serviceb); 15773 if (!app.serviceb) { 15774 // This service isn't far enough down on the LRU list to 15775 // normally be a B service, but if we are low on RAM and it 15776 // is large we want to force it down since we would prefer to 15777 // keep launcher over it. 15778 if (mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 15779 && app.lastPss >= mProcessList.getCachedRestoreThresholdKb()) { 15780 app.serviceHighRam = true; 15781 app.serviceb = true; 15782 //Slog.i(TAG, "ADJ " + app + " high ram!"); 15783 } else { 15784 mNewNumAServiceProcs++; 15785 //Slog.i(TAG, "ADJ " + app + " not high ram!"); 15786 } 15787 } else { 15788 app.serviceHighRam = false; 15789 } 15790 } 15791 if (app.serviceb) { 15792 adj = ProcessList.SERVICE_B_ADJ; 15793 } 15794 } 15795 15796 app.curRawAdj = adj; 15797 15798 //Slog.i(TAG, "OOM ADJ " + app + ": pid=" + app.pid + 15799 // " adj=" + adj + " curAdj=" + app.curAdj + " maxAdj=" + app.maxAdj); 15800 if (adj > app.maxAdj) { 15801 adj = app.maxAdj; 15802 if (app.maxAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 15803 schedGroup = Process.THREAD_GROUP_DEFAULT; 15804 } 15805 } 15806 15807 // Do final modification to adj. Everything we do between here and applying 15808 // the final setAdj must be done in this function, because we will also use 15809 // it when computing the final cached adj later. Note that we don't need to 15810 // worry about this for max adj above, since max adj will always be used to 15811 // keep it out of the cached vaues. 15812 app.curAdj = app.modifyRawOomAdj(adj); 15813 app.curSchedGroup = schedGroup; 15814 app.curProcState = procState; 15815 app.foregroundActivities = foregroundActivities; 15816 15817 return app.curRawAdj; 15818 } 15819 15820 /** 15821 * Schedule PSS collection of a process. 15822 */ 15823 void requestPssLocked(ProcessRecord proc, int procState) { 15824 if (mPendingPssProcesses.contains(proc)) { 15825 return; 15826 } 15827 if (mPendingPssProcesses.size() == 0) { 15828 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 15829 } 15830 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of: " + proc); 15831 proc.pssProcState = procState; 15832 mPendingPssProcesses.add(proc); 15833 } 15834 15835 /** 15836 * Schedule PSS collection of all processes. 15837 */ 15838 void requestPssAllProcsLocked(long now, boolean always, boolean memLowered) { 15839 if (!always) { 15840 if (now < (mLastFullPssTime + 15841 (memLowered ? FULL_PSS_LOWERED_INTERVAL : FULL_PSS_MIN_INTERVAL))) { 15842 return; 15843 } 15844 } 15845 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of all procs! memLowered=" + memLowered); 15846 mLastFullPssTime = now; 15847 mFullPssPending = true; 15848 mPendingPssProcesses.ensureCapacity(mLruProcesses.size()); 15849 mPendingPssProcesses.clear(); 15850 for (int i=mLruProcesses.size()-1; i>=0; i--) { 15851 ProcessRecord app = mLruProcesses.get(i); 15852 if (memLowered || now > (app.lastStateTime+ProcessList.PSS_ALL_INTERVAL)) { 15853 app.pssProcState = app.setProcState; 15854 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 15855 isSleeping(), now); 15856 mPendingPssProcesses.add(app); 15857 } 15858 } 15859 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 15860 } 15861 15862 /** 15863 * Ask a given process to GC right now. 15864 */ 15865 final void performAppGcLocked(ProcessRecord app) { 15866 try { 15867 app.lastRequestedGc = SystemClock.uptimeMillis(); 15868 if (app.thread != null) { 15869 if (app.reportLowMemory) { 15870 app.reportLowMemory = false; 15871 app.thread.scheduleLowMemory(); 15872 } else { 15873 app.thread.processInBackground(); 15874 } 15875 } 15876 } catch (Exception e) { 15877 // whatever. 15878 } 15879 } 15880 15881 /** 15882 * Returns true if things are idle enough to perform GCs. 15883 */ 15884 private final boolean canGcNowLocked() { 15885 boolean processingBroadcasts = false; 15886 for (BroadcastQueue q : mBroadcastQueues) { 15887 if (q.mParallelBroadcasts.size() != 0 || q.mOrderedBroadcasts.size() != 0) { 15888 processingBroadcasts = true; 15889 } 15890 } 15891 return !processingBroadcasts 15892 && (isSleeping() || mStackSupervisor.allResumedActivitiesIdle()); 15893 } 15894 15895 /** 15896 * Perform GCs on all processes that are waiting for it, but only 15897 * if things are idle. 15898 */ 15899 final void performAppGcsLocked() { 15900 final int N = mProcessesToGc.size(); 15901 if (N <= 0) { 15902 return; 15903 } 15904 if (canGcNowLocked()) { 15905 while (mProcessesToGc.size() > 0) { 15906 ProcessRecord proc = mProcessesToGc.remove(0); 15907 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ || proc.reportLowMemory) { 15908 if ((proc.lastRequestedGc+GC_MIN_INTERVAL) 15909 <= SystemClock.uptimeMillis()) { 15910 // To avoid spamming the system, we will GC processes one 15911 // at a time, waiting a few seconds between each. 15912 performAppGcLocked(proc); 15913 scheduleAppGcsLocked(); 15914 return; 15915 } else { 15916 // It hasn't been long enough since we last GCed this 15917 // process... put it in the list to wait for its time. 15918 addProcessToGcListLocked(proc); 15919 break; 15920 } 15921 } 15922 } 15923 15924 scheduleAppGcsLocked(); 15925 } 15926 } 15927 15928 /** 15929 * If all looks good, perform GCs on all processes waiting for them. 15930 */ 15931 final void performAppGcsIfAppropriateLocked() { 15932 if (canGcNowLocked()) { 15933 performAppGcsLocked(); 15934 return; 15935 } 15936 // Still not idle, wait some more. 15937 scheduleAppGcsLocked(); 15938 } 15939 15940 /** 15941 * Schedule the execution of all pending app GCs. 15942 */ 15943 final void scheduleAppGcsLocked() { 15944 mHandler.removeMessages(GC_BACKGROUND_PROCESSES_MSG); 15945 15946 if (mProcessesToGc.size() > 0) { 15947 // Schedule a GC for the time to the next process. 15948 ProcessRecord proc = mProcessesToGc.get(0); 15949 Message msg = mHandler.obtainMessage(GC_BACKGROUND_PROCESSES_MSG); 15950 15951 long when = proc.lastRequestedGc + GC_MIN_INTERVAL; 15952 long now = SystemClock.uptimeMillis(); 15953 if (when < (now+GC_TIMEOUT)) { 15954 when = now + GC_TIMEOUT; 15955 } 15956 mHandler.sendMessageAtTime(msg, when); 15957 } 15958 } 15959 15960 /** 15961 * Add a process to the array of processes waiting to be GCed. Keeps the 15962 * list in sorted order by the last GC time. The process can't already be 15963 * on the list. 15964 */ 15965 final void addProcessToGcListLocked(ProcessRecord proc) { 15966 boolean added = false; 15967 for (int i=mProcessesToGc.size()-1; i>=0; i--) { 15968 if (mProcessesToGc.get(i).lastRequestedGc < 15969 proc.lastRequestedGc) { 15970 added = true; 15971 mProcessesToGc.add(i+1, proc); 15972 break; 15973 } 15974 } 15975 if (!added) { 15976 mProcessesToGc.add(0, proc); 15977 } 15978 } 15979 15980 /** 15981 * Set up to ask a process to GC itself. This will either do it 15982 * immediately, or put it on the list of processes to gc the next 15983 * time things are idle. 15984 */ 15985 final void scheduleAppGcLocked(ProcessRecord app) { 15986 long now = SystemClock.uptimeMillis(); 15987 if ((app.lastRequestedGc+GC_MIN_INTERVAL) > now) { 15988 return; 15989 } 15990 if (!mProcessesToGc.contains(app)) { 15991 addProcessToGcListLocked(app); 15992 scheduleAppGcsLocked(); 15993 } 15994 } 15995 15996 final void checkExcessivePowerUsageLocked(boolean doKills) { 15997 updateCpuStatsNow(); 15998 15999 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 16000 boolean doWakeKills = doKills; 16001 boolean doCpuKills = doKills; 16002 if (mLastPowerCheckRealtime == 0) { 16003 doWakeKills = false; 16004 } 16005 if (mLastPowerCheckUptime == 0) { 16006 doCpuKills = false; 16007 } 16008 if (stats.isScreenOn()) { 16009 doWakeKills = false; 16010 } 16011 final long curRealtime = SystemClock.elapsedRealtime(); 16012 final long realtimeSince = curRealtime - mLastPowerCheckRealtime; 16013 final long curUptime = SystemClock.uptimeMillis(); 16014 final long uptimeSince = curUptime - mLastPowerCheckUptime; 16015 mLastPowerCheckRealtime = curRealtime; 16016 mLastPowerCheckUptime = curUptime; 16017 if (realtimeSince < WAKE_LOCK_MIN_CHECK_DURATION) { 16018 doWakeKills = false; 16019 } 16020 if (uptimeSince < CPU_MIN_CHECK_DURATION) { 16021 doCpuKills = false; 16022 } 16023 int i = mLruProcesses.size(); 16024 while (i > 0) { 16025 i--; 16026 ProcessRecord app = mLruProcesses.get(i); 16027 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 16028 long wtime; 16029 synchronized (stats) { 16030 wtime = stats.getProcessWakeTime(app.info.uid, 16031 app.pid, curRealtime); 16032 } 16033 long wtimeUsed = wtime - app.lastWakeTime; 16034 long cputimeUsed = app.curCpuTime - app.lastCpuTime; 16035 if (DEBUG_POWER) { 16036 StringBuilder sb = new StringBuilder(128); 16037 sb.append("Wake for "); 16038 app.toShortString(sb); 16039 sb.append(": over "); 16040 TimeUtils.formatDuration(realtimeSince, sb); 16041 sb.append(" used "); 16042 TimeUtils.formatDuration(wtimeUsed, sb); 16043 sb.append(" ("); 16044 sb.append((wtimeUsed*100)/realtimeSince); 16045 sb.append("%)"); 16046 Slog.i(TAG, sb.toString()); 16047 sb.setLength(0); 16048 sb.append("CPU for "); 16049 app.toShortString(sb); 16050 sb.append(": over "); 16051 TimeUtils.formatDuration(uptimeSince, sb); 16052 sb.append(" used "); 16053 TimeUtils.formatDuration(cputimeUsed, sb); 16054 sb.append(" ("); 16055 sb.append((cputimeUsed*100)/uptimeSince); 16056 sb.append("%)"); 16057 Slog.i(TAG, sb.toString()); 16058 } 16059 // If a process has held a wake lock for more 16060 // than 50% of the time during this period, 16061 // that sounds bad. Kill! 16062 if (doWakeKills && realtimeSince > 0 16063 && ((wtimeUsed*100)/realtimeSince) >= 50) { 16064 synchronized (stats) { 16065 stats.reportExcessiveWakeLocked(app.info.uid, app.processName, 16066 realtimeSince, wtimeUsed); 16067 } 16068 killUnneededProcessLocked(app, "excessive wake held " + wtimeUsed 16069 + " during " + realtimeSince); 16070 app.baseProcessTracker.reportExcessiveWake(app.pkgList); 16071 } else if (doCpuKills && uptimeSince > 0 16072 && ((cputimeUsed*100)/uptimeSince) >= 25) { 16073 synchronized (stats) { 16074 stats.reportExcessiveCpuLocked(app.info.uid, app.processName, 16075 uptimeSince, cputimeUsed); 16076 } 16077 killUnneededProcessLocked(app, "excessive cpu " + cputimeUsed 16078 + " during " + uptimeSince); 16079 app.baseProcessTracker.reportExcessiveCpu(app.pkgList); 16080 } else { 16081 app.lastWakeTime = wtime; 16082 app.lastCpuTime = app.curCpuTime; 16083 } 16084 } 16085 } 16086 } 16087 16088 private final boolean applyOomAdjLocked(ProcessRecord app, 16089 ProcessRecord TOP_APP, boolean doingAll, long now) { 16090 boolean success = true; 16091 16092 if (app.curRawAdj != app.setRawAdj) { 16093 app.setRawAdj = app.curRawAdj; 16094 } 16095 16096 int changes = 0; 16097 16098 if (app.curAdj != app.setAdj) { 16099 ProcessList.setOomAdj(app.pid, app.info.uid, app.curAdj); 16100 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v( 16101 TAG, "Set " + app.pid + " " + app.processName + 16102 " adj " + app.curAdj + ": " + app.adjType); 16103 app.setAdj = app.curAdj; 16104 } 16105 16106 if (app.setSchedGroup != app.curSchedGroup) { 16107 app.setSchedGroup = app.curSchedGroup; 16108 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16109 "Setting process group of " + app.processName 16110 + " to " + app.curSchedGroup); 16111 if (app.waitingToKill != null && 16112 app.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 16113 killUnneededProcessLocked(app, app.waitingToKill); 16114 success = false; 16115 } else { 16116 if (true) { 16117 long oldId = Binder.clearCallingIdentity(); 16118 try { 16119 Process.setProcessGroup(app.pid, app.curSchedGroup); 16120 } catch (Exception e) { 16121 Slog.w(TAG, "Failed setting process group of " + app.pid 16122 + " to " + app.curSchedGroup); 16123 e.printStackTrace(); 16124 } finally { 16125 Binder.restoreCallingIdentity(oldId); 16126 } 16127 } else { 16128 if (app.thread != null) { 16129 try { 16130 app.thread.setSchedulingGroup(app.curSchedGroup); 16131 } catch (RemoteException e) { 16132 } 16133 } 16134 } 16135 Process.setSwappiness(app.pid, 16136 app.curSchedGroup <= Process.THREAD_GROUP_BG_NONINTERACTIVE); 16137 } 16138 } 16139 if (app.repForegroundActivities != app.foregroundActivities) { 16140 app.repForegroundActivities = app.foregroundActivities; 16141 changes |= ProcessChangeItem.CHANGE_ACTIVITIES; 16142 } 16143 if (app.repProcState != app.curProcState) { 16144 app.repProcState = app.curProcState; 16145 changes |= ProcessChangeItem.CHANGE_PROCESS_STATE; 16146 if (app.thread != null) { 16147 try { 16148 if (false) { 16149 //RuntimeException h = new RuntimeException("here"); 16150 Slog.i(TAG, "Sending new process state " + app.repProcState 16151 + " to " + app /*, h*/); 16152 } 16153 app.thread.setProcessState(app.repProcState); 16154 } catch (RemoteException e) { 16155 } 16156 } 16157 } 16158 if (app.setProcState < 0 || ProcessList.procStatesDifferForMem(app.curProcState, 16159 app.setProcState)) { 16160 app.lastStateTime = now; 16161 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 16162 isSleeping(), now); 16163 if (DEBUG_PSS) Slog.d(TAG, "Process state change from " 16164 + ProcessList.makeProcStateString(app.setProcState) + " to " 16165 + ProcessList.makeProcStateString(app.curProcState) + " next pss in " 16166 + (app.nextPssTime-now) + ": " + app); 16167 } else { 16168 if (now > app.nextPssTime || (now > (app.lastPssTime+ProcessList.PSS_MAX_INTERVAL) 16169 && now > (app.lastStateTime+ProcessList.PSS_MIN_TIME_FROM_STATE_CHANGE))) { 16170 requestPssLocked(app, app.setProcState); 16171 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, false, 16172 isSleeping(), now); 16173 } else if (false && DEBUG_PSS) { 16174 Slog.d(TAG, "Not requesting PSS of " + app + ": next=" + (app.nextPssTime-now)); 16175 } 16176 } 16177 if (app.setProcState != app.curProcState) { 16178 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16179 "Proc state change of " + app.processName 16180 + " to " + app.curProcState); 16181 boolean setImportant = app.setProcState < ActivityManager.PROCESS_STATE_SERVICE; 16182 boolean curImportant = app.curProcState < ActivityManager.PROCESS_STATE_SERVICE; 16183 if (setImportant && !curImportant) { 16184 // This app is no longer something we consider important enough to allow to 16185 // use arbitrary amounts of battery power. Note 16186 // its current wake lock time to later know to kill it if 16187 // it is not behaving well. 16188 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 16189 synchronized (stats) { 16190 app.lastWakeTime = stats.getProcessWakeTime(app.info.uid, 16191 app.pid, SystemClock.elapsedRealtime()); 16192 } 16193 app.lastCpuTime = app.curCpuTime; 16194 16195 } 16196 app.setProcState = app.curProcState; 16197 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 16198 app.notCachedSinceIdle = false; 16199 } 16200 if (!doingAll) { 16201 setProcessTrackerStateLocked(app, mProcessStats.getMemFactorLocked(), now); 16202 } else { 16203 app.procStateChanged = true; 16204 } 16205 } 16206 16207 if (changes != 0) { 16208 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Changes in " + app + ": " + changes); 16209 int i = mPendingProcessChanges.size()-1; 16210 ProcessChangeItem item = null; 16211 while (i >= 0) { 16212 item = mPendingProcessChanges.get(i); 16213 if (item.pid == app.pid) { 16214 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Re-using existing item: " + item); 16215 break; 16216 } 16217 i--; 16218 } 16219 if (i < 0) { 16220 // No existing item in pending changes; need a new one. 16221 final int NA = mAvailProcessChanges.size(); 16222 if (NA > 0) { 16223 item = mAvailProcessChanges.remove(NA-1); 16224 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Retreiving available item: " + item); 16225 } else { 16226 item = new ProcessChangeItem(); 16227 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Allocating new item: " + item); 16228 } 16229 item.changes = 0; 16230 item.pid = app.pid; 16231 item.uid = app.info.uid; 16232 if (mPendingProcessChanges.size() == 0) { 16233 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, 16234 "*** Enqueueing dispatch processes changed!"); 16235 mHandler.obtainMessage(DISPATCH_PROCESSES_CHANGED).sendToTarget(); 16236 } 16237 mPendingProcessChanges.add(item); 16238 } 16239 item.changes |= changes; 16240 item.processState = app.repProcState; 16241 item.foregroundActivities = app.repForegroundActivities; 16242 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Item " 16243 + Integer.toHexString(System.identityHashCode(item)) 16244 + " " + app.toShortString() + ": changes=" + item.changes 16245 + " procState=" + item.processState 16246 + " foreground=" + item.foregroundActivities 16247 + " type=" + app.adjType + " source=" + app.adjSource 16248 + " target=" + app.adjTarget); 16249 } 16250 16251 return success; 16252 } 16253 16254 private final void setProcessTrackerStateLocked(ProcessRecord proc, int memFactor, long now) { 16255 if (proc.thread != null) { 16256 if (proc.baseProcessTracker != null) { 16257 proc.baseProcessTracker.setState(proc.repProcState, memFactor, now, proc.pkgList); 16258 } 16259 if (proc.repProcState >= 0) { 16260 mBatteryStatsService.noteProcessState(proc.processName, proc.info.uid, 16261 proc.repProcState); 16262 } 16263 } 16264 } 16265 16266 private final boolean updateOomAdjLocked(ProcessRecord app, int cachedAdj, 16267 ProcessRecord TOP_APP, boolean doingAll, long now) { 16268 if (app.thread == null) { 16269 return false; 16270 } 16271 16272 computeOomAdjLocked(app, cachedAdj, TOP_APP, doingAll, now); 16273 16274 return applyOomAdjLocked(app, TOP_APP, doingAll, now); 16275 } 16276 16277 final void updateProcessForegroundLocked(ProcessRecord proc, boolean isForeground, 16278 boolean oomAdj) { 16279 if (isForeground != proc.foregroundServices) { 16280 proc.foregroundServices = isForeground; 16281 ArrayList<ProcessRecord> curProcs = mForegroundPackages.get(proc.info.packageName, 16282 proc.info.uid); 16283 if (isForeground) { 16284 if (curProcs == null) { 16285 curProcs = new ArrayList<ProcessRecord>(); 16286 mForegroundPackages.put(proc.info.packageName, proc.info.uid, curProcs); 16287 } 16288 if (!curProcs.contains(proc)) { 16289 curProcs.add(proc); 16290 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_FOREGROUND_START, 16291 proc.info.packageName, proc.info.uid); 16292 } 16293 } else { 16294 if (curProcs != null) { 16295 if (curProcs.remove(proc)) { 16296 mBatteryStatsService.noteEvent( 16297 BatteryStats.HistoryItem.EVENT_FOREGROUND_FINISH, 16298 proc.info.packageName, proc.info.uid); 16299 if (curProcs.size() <= 0) { 16300 mForegroundPackages.remove(proc.info.packageName, proc.info.uid); 16301 } 16302 } 16303 } 16304 } 16305 if (oomAdj) { 16306 updateOomAdjLocked(); 16307 } 16308 } 16309 } 16310 16311 private final ActivityRecord resumedAppLocked() { 16312 ActivityRecord act = mStackSupervisor.resumedAppLocked(); 16313 String pkg; 16314 int uid; 16315 if (act != null) { 16316 pkg = act.packageName; 16317 uid = act.info.applicationInfo.uid; 16318 } else { 16319 pkg = null; 16320 uid = -1; 16321 } 16322 // Has the UID or resumed package name changed? 16323 if (uid != mCurResumedUid || (pkg != mCurResumedPackage 16324 && (pkg == null || !pkg.equals(mCurResumedPackage)))) { 16325 if (mCurResumedPackage != null) { 16326 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_FINISH, 16327 mCurResumedPackage, mCurResumedUid); 16328 } 16329 mCurResumedPackage = pkg; 16330 mCurResumedUid = uid; 16331 if (mCurResumedPackage != null) { 16332 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_START, 16333 mCurResumedPackage, mCurResumedUid); 16334 } 16335 } 16336 return act; 16337 } 16338 16339 final boolean updateOomAdjLocked(ProcessRecord app) { 16340 final ActivityRecord TOP_ACT = resumedAppLocked(); 16341 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 16342 final boolean wasCached = app.cached; 16343 16344 mAdjSeq++; 16345 16346 // This is the desired cached adjusment we want to tell it to use. 16347 // If our app is currently cached, we know it, and that is it. Otherwise, 16348 // we don't know it yet, and it needs to now be cached we will then 16349 // need to do a complete oom adj. 16350 final int cachedAdj = app.curRawAdj >= ProcessList.CACHED_APP_MIN_ADJ 16351 ? app.curRawAdj : ProcessList.UNKNOWN_ADJ; 16352 boolean success = updateOomAdjLocked(app, cachedAdj, TOP_APP, false, 16353 SystemClock.uptimeMillis()); 16354 if (wasCached != app.cached || app.curRawAdj == ProcessList.UNKNOWN_ADJ) { 16355 // Changed to/from cached state, so apps after it in the LRU 16356 // list may also be changed. 16357 updateOomAdjLocked(); 16358 } 16359 return success; 16360 } 16361 16362 final void updateOomAdjLocked() { 16363 final ActivityRecord TOP_ACT = resumedAppLocked(); 16364 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 16365 final long now = SystemClock.uptimeMillis(); 16366 final long oldTime = now - ProcessList.MAX_EMPTY_TIME; 16367 final int N = mLruProcesses.size(); 16368 16369 if (false) { 16370 RuntimeException e = new RuntimeException(); 16371 e.fillInStackTrace(); 16372 Slog.i(TAG, "updateOomAdj: top=" + TOP_ACT, e); 16373 } 16374 16375 mAdjSeq++; 16376 mNewNumServiceProcs = 0; 16377 mNewNumAServiceProcs = 0; 16378 16379 final int emptyProcessLimit; 16380 final int cachedProcessLimit; 16381 if (mProcessLimit <= 0) { 16382 emptyProcessLimit = cachedProcessLimit = 0; 16383 } else if (mProcessLimit == 1) { 16384 emptyProcessLimit = 1; 16385 cachedProcessLimit = 0; 16386 } else { 16387 emptyProcessLimit = ProcessList.computeEmptyProcessLimit(mProcessLimit); 16388 cachedProcessLimit = mProcessLimit - emptyProcessLimit; 16389 } 16390 16391 // Let's determine how many processes we have running vs. 16392 // how many slots we have for background processes; we may want 16393 // to put multiple processes in a slot of there are enough of 16394 // them. 16395 int numSlots = (ProcessList.CACHED_APP_MAX_ADJ 16396 - ProcessList.CACHED_APP_MIN_ADJ + 1) / 2; 16397 int numEmptyProcs = N - mNumNonCachedProcs - mNumCachedHiddenProcs; 16398 if (numEmptyProcs > cachedProcessLimit) { 16399 // If there are more empty processes than our limit on cached 16400 // processes, then use the cached process limit for the factor. 16401 // This ensures that the really old empty processes get pushed 16402 // down to the bottom, so if we are running low on memory we will 16403 // have a better chance at keeping around more cached processes 16404 // instead of a gazillion empty processes. 16405 numEmptyProcs = cachedProcessLimit; 16406 } 16407 int emptyFactor = numEmptyProcs/numSlots; 16408 if (emptyFactor < 1) emptyFactor = 1; 16409 int cachedFactor = (mNumCachedHiddenProcs > 0 ? mNumCachedHiddenProcs : 1)/numSlots; 16410 if (cachedFactor < 1) cachedFactor = 1; 16411 int stepCached = 0; 16412 int stepEmpty = 0; 16413 int numCached = 0; 16414 int numEmpty = 0; 16415 int numTrimming = 0; 16416 16417 mNumNonCachedProcs = 0; 16418 mNumCachedHiddenProcs = 0; 16419 16420 // First update the OOM adjustment for each of the 16421 // application processes based on their current state. 16422 int curCachedAdj = ProcessList.CACHED_APP_MIN_ADJ; 16423 int nextCachedAdj = curCachedAdj+1; 16424 int curEmptyAdj = ProcessList.CACHED_APP_MIN_ADJ; 16425 int nextEmptyAdj = curEmptyAdj+2; 16426 for (int i=N-1; i>=0; i--) { 16427 ProcessRecord app = mLruProcesses.get(i); 16428 if (!app.killedByAm && app.thread != null) { 16429 app.procStateChanged = false; 16430 computeOomAdjLocked(app, ProcessList.UNKNOWN_ADJ, TOP_APP, true, now); 16431 16432 // If we haven't yet assigned the final cached adj 16433 // to the process, do that now. 16434 if (app.curAdj >= ProcessList.UNKNOWN_ADJ) { 16435 switch (app.curProcState) { 16436 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 16437 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 16438 // This process is a cached process holding activities... 16439 // assign it the next cached value for that type, and then 16440 // step that cached level. 16441 app.curRawAdj = curCachedAdj; 16442 app.curAdj = app.modifyRawOomAdj(curCachedAdj); 16443 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning activity LRU #" + i 16444 + " adj: " + app.curAdj + " (curCachedAdj=" + curCachedAdj 16445 + ")"); 16446 if (curCachedAdj != nextCachedAdj) { 16447 stepCached++; 16448 if (stepCached >= cachedFactor) { 16449 stepCached = 0; 16450 curCachedAdj = nextCachedAdj; 16451 nextCachedAdj += 2; 16452 if (nextCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) { 16453 nextCachedAdj = ProcessList.CACHED_APP_MAX_ADJ; 16454 } 16455 } 16456 } 16457 break; 16458 default: 16459 // For everything else, assign next empty cached process 16460 // level and bump that up. Note that this means that 16461 // long-running services that have dropped down to the 16462 // cached level will be treated as empty (since their process 16463 // state is still as a service), which is what we want. 16464 app.curRawAdj = curEmptyAdj; 16465 app.curAdj = app.modifyRawOomAdj(curEmptyAdj); 16466 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning empty LRU #" + i 16467 + " adj: " + app.curAdj + " (curEmptyAdj=" + curEmptyAdj 16468 + ")"); 16469 if (curEmptyAdj != nextEmptyAdj) { 16470 stepEmpty++; 16471 if (stepEmpty >= emptyFactor) { 16472 stepEmpty = 0; 16473 curEmptyAdj = nextEmptyAdj; 16474 nextEmptyAdj += 2; 16475 if (nextEmptyAdj > ProcessList.CACHED_APP_MAX_ADJ) { 16476 nextEmptyAdj = ProcessList.CACHED_APP_MAX_ADJ; 16477 } 16478 } 16479 } 16480 break; 16481 } 16482 } 16483 16484 applyOomAdjLocked(app, TOP_APP, true, now); 16485 16486 // Count the number of process types. 16487 switch (app.curProcState) { 16488 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 16489 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 16490 mNumCachedHiddenProcs++; 16491 numCached++; 16492 if (numCached > cachedProcessLimit) { 16493 killUnneededProcessLocked(app, "cached #" + numCached); 16494 } 16495 break; 16496 case ActivityManager.PROCESS_STATE_CACHED_EMPTY: 16497 if (numEmpty > ProcessList.TRIM_EMPTY_APPS 16498 && app.lastActivityTime < oldTime) { 16499 killUnneededProcessLocked(app, "empty for " 16500 + ((oldTime + ProcessList.MAX_EMPTY_TIME - app.lastActivityTime) 16501 / 1000) + "s"); 16502 } else { 16503 numEmpty++; 16504 if (numEmpty > emptyProcessLimit) { 16505 killUnneededProcessLocked(app, "empty #" + numEmpty); 16506 } 16507 } 16508 break; 16509 default: 16510 mNumNonCachedProcs++; 16511 break; 16512 } 16513 16514 if (app.isolated && app.services.size() <= 0) { 16515 // If this is an isolated process, and there are no 16516 // services running in it, then the process is no longer 16517 // needed. We agressively kill these because we can by 16518 // definition not re-use the same process again, and it is 16519 // good to avoid having whatever code was running in them 16520 // left sitting around after no longer needed. 16521 killUnneededProcessLocked(app, "isolated not needed"); 16522 } 16523 16524 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 16525 && !app.killedByAm) { 16526 numTrimming++; 16527 } 16528 } 16529 } 16530 16531 mNumServiceProcs = mNewNumServiceProcs; 16532 16533 // Now determine the memory trimming level of background processes. 16534 // Unfortunately we need to start at the back of the list to do this 16535 // properly. We only do this if the number of background apps we 16536 // are managing to keep around is less than half the maximum we desire; 16537 // if we are keeping a good number around, we'll let them use whatever 16538 // memory they want. 16539 final int numCachedAndEmpty = numCached + numEmpty; 16540 int memFactor; 16541 if (numCached <= ProcessList.TRIM_CACHED_APPS 16542 && numEmpty <= ProcessList.TRIM_EMPTY_APPS) { 16543 if (numCachedAndEmpty <= ProcessList.TRIM_CRITICAL_THRESHOLD) { 16544 memFactor = ProcessStats.ADJ_MEM_FACTOR_CRITICAL; 16545 } else if (numCachedAndEmpty <= ProcessList.TRIM_LOW_THRESHOLD) { 16546 memFactor = ProcessStats.ADJ_MEM_FACTOR_LOW; 16547 } else { 16548 memFactor = ProcessStats.ADJ_MEM_FACTOR_MODERATE; 16549 } 16550 } else { 16551 memFactor = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 16552 } 16553 // We always allow the memory level to go up (better). We only allow it to go 16554 // down if we are in a state where that is allowed, *and* the total number of processes 16555 // has gone down since last time. 16556 if (DEBUG_OOM_ADJ) Slog.d(TAG, "oom: memFactor=" + memFactor + " last=" + mLastMemoryLevel 16557 + " allowLow=" + mAllowLowerMemLevel + " numProcs=" + mLruProcesses.size() 16558 + " last=" + mLastNumProcesses); 16559 if (memFactor > mLastMemoryLevel) { 16560 if (!mAllowLowerMemLevel || mLruProcesses.size() >= mLastNumProcesses) { 16561 memFactor = mLastMemoryLevel; 16562 if (DEBUG_OOM_ADJ) Slog.d(TAG, "Keeping last mem factor!"); 16563 } 16564 } 16565 mLastMemoryLevel = memFactor; 16566 mLastNumProcesses = mLruProcesses.size(); 16567 boolean allChanged = mProcessStats.setMemFactorLocked(memFactor, !isSleeping(), now); 16568 final int trackerMemFactor = mProcessStats.getMemFactorLocked(); 16569 if (memFactor != ProcessStats.ADJ_MEM_FACTOR_NORMAL) { 16570 if (mLowRamStartTime == 0) { 16571 mLowRamStartTime = now; 16572 } 16573 int step = 0; 16574 int fgTrimLevel; 16575 switch (memFactor) { 16576 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 16577 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_CRITICAL; 16578 break; 16579 case ProcessStats.ADJ_MEM_FACTOR_LOW: 16580 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_LOW; 16581 break; 16582 default: 16583 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_MODERATE; 16584 break; 16585 } 16586 int factor = numTrimming/3; 16587 int minFactor = 2; 16588 if (mHomeProcess != null) minFactor++; 16589 if (mPreviousProcess != null) minFactor++; 16590 if (factor < minFactor) factor = minFactor; 16591 int curLevel = ComponentCallbacks2.TRIM_MEMORY_COMPLETE; 16592 for (int i=N-1; i>=0; i--) { 16593 ProcessRecord app = mLruProcesses.get(i); 16594 if (allChanged || app.procStateChanged) { 16595 setProcessTrackerStateLocked(app, trackerMemFactor, now); 16596 app.procStateChanged = false; 16597 } 16598 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 16599 && !app.killedByAm) { 16600 if (app.trimMemoryLevel < curLevel && app.thread != null) { 16601 try { 16602 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16603 "Trimming memory of " + app.processName 16604 + " to " + curLevel); 16605 app.thread.scheduleTrimMemory(curLevel); 16606 } catch (RemoteException e) { 16607 } 16608 if (false) { 16609 // For now we won't do this; our memory trimming seems 16610 // to be good enough at this point that destroying 16611 // activities causes more harm than good. 16612 if (curLevel >= ComponentCallbacks2.TRIM_MEMORY_COMPLETE 16613 && app != mHomeProcess && app != mPreviousProcess) { 16614 // Need to do this on its own message because the stack may not 16615 // be in a consistent state at this point. 16616 // For these apps we will also finish their activities 16617 // to help them free memory. 16618 mStackSupervisor.scheduleDestroyAllActivities(app, "trim"); 16619 } 16620 } 16621 } 16622 app.trimMemoryLevel = curLevel; 16623 step++; 16624 if (step >= factor) { 16625 step = 0; 16626 switch (curLevel) { 16627 case ComponentCallbacks2.TRIM_MEMORY_COMPLETE: 16628 curLevel = ComponentCallbacks2.TRIM_MEMORY_MODERATE; 16629 break; 16630 case ComponentCallbacks2.TRIM_MEMORY_MODERATE: 16631 curLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 16632 break; 16633 } 16634 } 16635 } else if (app.curProcState == ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 16636 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_BACKGROUND 16637 && app.thread != null) { 16638 try { 16639 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16640 "Trimming memory of heavy-weight " + app.processName 16641 + " to " + ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 16642 app.thread.scheduleTrimMemory( 16643 ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 16644 } catch (RemoteException e) { 16645 } 16646 } 16647 app.trimMemoryLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 16648 } else { 16649 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 16650 || app.systemNoUi) && app.pendingUiClean) { 16651 // If this application is now in the background and it 16652 // had done UI, then give it the special trim level to 16653 // have it free UI resources. 16654 final int level = ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN; 16655 if (app.trimMemoryLevel < level && app.thread != null) { 16656 try { 16657 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16658 "Trimming memory of bg-ui " + app.processName 16659 + " to " + level); 16660 app.thread.scheduleTrimMemory(level); 16661 } catch (RemoteException e) { 16662 } 16663 } 16664 app.pendingUiClean = false; 16665 } 16666 if (app.trimMemoryLevel < fgTrimLevel && app.thread != null) { 16667 try { 16668 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16669 "Trimming memory of fg " + app.processName 16670 + " to " + fgTrimLevel); 16671 app.thread.scheduleTrimMemory(fgTrimLevel); 16672 } catch (RemoteException e) { 16673 } 16674 } 16675 app.trimMemoryLevel = fgTrimLevel; 16676 } 16677 } 16678 } else { 16679 if (mLowRamStartTime != 0) { 16680 mLowRamTimeSinceLastIdle += now - mLowRamStartTime; 16681 mLowRamStartTime = 0; 16682 } 16683 for (int i=N-1; i>=0; i--) { 16684 ProcessRecord app = mLruProcesses.get(i); 16685 if (allChanged || app.procStateChanged) { 16686 setProcessTrackerStateLocked(app, trackerMemFactor, now); 16687 app.procStateChanged = false; 16688 } 16689 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 16690 || app.systemNoUi) && app.pendingUiClean) { 16691 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN 16692 && app.thread != null) { 16693 try { 16694 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16695 "Trimming memory of ui hidden " + app.processName 16696 + " to " + ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 16697 app.thread.scheduleTrimMemory( 16698 ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 16699 } catch (RemoteException e) { 16700 } 16701 } 16702 app.pendingUiClean = false; 16703 } 16704 app.trimMemoryLevel = 0; 16705 } 16706 } 16707 16708 if (mAlwaysFinishActivities) { 16709 // Need to do this on its own message because the stack may not 16710 // be in a consistent state at this point. 16711 mStackSupervisor.scheduleDestroyAllActivities(null, "always-finish"); 16712 } 16713 16714 if (allChanged) { 16715 requestPssAllProcsLocked(now, false, mProcessStats.isMemFactorLowered()); 16716 } 16717 16718 if (mProcessStats.shouldWriteNowLocked(now)) { 16719 mHandler.post(new Runnable() { 16720 @Override public void run() { 16721 synchronized (ActivityManagerService.this) { 16722 mProcessStats.writeStateAsyncLocked(); 16723 } 16724 } 16725 }); 16726 } 16727 16728 if (DEBUG_OOM_ADJ) { 16729 Slog.d(TAG, "Did OOM ADJ in " + (SystemClock.uptimeMillis()-now) + "ms"); 16730 } 16731 } 16732 16733 final void trimApplications() { 16734 synchronized (this) { 16735 int i; 16736 16737 // First remove any unused application processes whose package 16738 // has been removed. 16739 for (i=mRemovedProcesses.size()-1; i>=0; i--) { 16740 final ProcessRecord app = mRemovedProcesses.get(i); 16741 if (app.activities.size() == 0 16742 && app.curReceiver == null && app.services.size() == 0) { 16743 Slog.i( 16744 TAG, "Exiting empty application process " 16745 + app.processName + " (" 16746 + (app.thread != null ? app.thread.asBinder() : null) 16747 + ")\n"); 16748 if (app.pid > 0 && app.pid != MY_PID) { 16749 EventLog.writeEvent(EventLogTags.AM_KILL, app.userId, app.pid, 16750 app.processName, app.setAdj, "empty"); 16751 app.killedByAm = true; 16752 Process.killProcessQuiet(app.pid); 16753 Process.killProcessGroup(app.info.uid, app.pid); 16754 } else { 16755 try { 16756 app.thread.scheduleExit(); 16757 } catch (Exception e) { 16758 // Ignore exceptions. 16759 } 16760 } 16761 cleanUpApplicationRecordLocked(app, false, true, -1); 16762 mRemovedProcesses.remove(i); 16763 16764 if (app.persistent) { 16765 addAppLocked(app.info, false, null /* ABI override */); 16766 } 16767 } 16768 } 16769 16770 // Now update the oom adj for all processes. 16771 updateOomAdjLocked(); 16772 } 16773 } 16774 16775 /** This method sends the specified signal to each of the persistent apps */ 16776 public void signalPersistentProcesses(int sig) throws RemoteException { 16777 if (sig != Process.SIGNAL_USR1) { 16778 throw new SecurityException("Only SIGNAL_USR1 is allowed"); 16779 } 16780 16781 synchronized (this) { 16782 if (checkCallingPermission(android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES) 16783 != PackageManager.PERMISSION_GRANTED) { 16784 throw new SecurityException("Requires permission " 16785 + android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES); 16786 } 16787 16788 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 16789 ProcessRecord r = mLruProcesses.get(i); 16790 if (r.thread != null && r.persistent) { 16791 Process.sendSignal(r.pid, sig); 16792 } 16793 } 16794 } 16795 } 16796 16797 private void stopProfilerLocked(ProcessRecord proc, String path, int profileType) { 16798 if (proc == null || proc == mProfileProc) { 16799 proc = mProfileProc; 16800 path = mProfileFile; 16801 profileType = mProfileType; 16802 clearProfilerLocked(); 16803 } 16804 if (proc == null) { 16805 return; 16806 } 16807 try { 16808 proc.thread.profilerControl(false, path, null, profileType); 16809 } catch (RemoteException e) { 16810 throw new IllegalStateException("Process disappeared"); 16811 } 16812 } 16813 16814 private void clearProfilerLocked() { 16815 if (mProfileFd != null) { 16816 try { 16817 mProfileFd.close(); 16818 } catch (IOException e) { 16819 } 16820 } 16821 mProfileApp = null; 16822 mProfileProc = null; 16823 mProfileFile = null; 16824 mProfileType = 0; 16825 mAutoStopProfiler = false; 16826 } 16827 16828 public boolean profileControl(String process, int userId, boolean start, 16829 String path, ParcelFileDescriptor fd, int profileType) throws RemoteException { 16830 16831 try { 16832 synchronized (this) { 16833 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 16834 // its own permission. 16835 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 16836 != PackageManager.PERMISSION_GRANTED) { 16837 throw new SecurityException("Requires permission " 16838 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 16839 } 16840 16841 if (start && fd == null) { 16842 throw new IllegalArgumentException("null fd"); 16843 } 16844 16845 ProcessRecord proc = null; 16846 if (process != null) { 16847 proc = findProcessLocked(process, userId, "profileControl"); 16848 } 16849 16850 if (start && (proc == null || proc.thread == null)) { 16851 throw new IllegalArgumentException("Unknown process: " + process); 16852 } 16853 16854 if (start) { 16855 stopProfilerLocked(null, null, 0); 16856 setProfileApp(proc.info, proc.processName, path, fd, false); 16857 mProfileProc = proc; 16858 mProfileType = profileType; 16859 try { 16860 fd = fd.dup(); 16861 } catch (IOException e) { 16862 fd = null; 16863 } 16864 proc.thread.profilerControl(start, path, fd, profileType); 16865 fd = null; 16866 mProfileFd = null; 16867 } else { 16868 stopProfilerLocked(proc, path, profileType); 16869 if (fd != null) { 16870 try { 16871 fd.close(); 16872 } catch (IOException e) { 16873 } 16874 } 16875 } 16876 16877 return true; 16878 } 16879 } catch (RemoteException e) { 16880 throw new IllegalStateException("Process disappeared"); 16881 } finally { 16882 if (fd != null) { 16883 try { 16884 fd.close(); 16885 } catch (IOException e) { 16886 } 16887 } 16888 } 16889 } 16890 16891 private ProcessRecord findProcessLocked(String process, int userId, String callName) { 16892 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 16893 userId, true, ALLOW_FULL_ONLY, callName, null); 16894 ProcessRecord proc = null; 16895 try { 16896 int pid = Integer.parseInt(process); 16897 synchronized (mPidsSelfLocked) { 16898 proc = mPidsSelfLocked.get(pid); 16899 } 16900 } catch (NumberFormatException e) { 16901 } 16902 16903 if (proc == null) { 16904 ArrayMap<String, SparseArray<ProcessRecord>> all 16905 = mProcessNames.getMap(); 16906 SparseArray<ProcessRecord> procs = all.get(process); 16907 if (procs != null && procs.size() > 0) { 16908 proc = procs.valueAt(0); 16909 if (userId != UserHandle.USER_ALL && proc.userId != userId) { 16910 for (int i=1; i<procs.size(); i++) { 16911 ProcessRecord thisProc = procs.valueAt(i); 16912 if (thisProc.userId == userId) { 16913 proc = thisProc; 16914 break; 16915 } 16916 } 16917 } 16918 } 16919 } 16920 16921 return proc; 16922 } 16923 16924 public boolean dumpHeap(String process, int userId, boolean managed, 16925 String path, ParcelFileDescriptor fd) throws RemoteException { 16926 16927 try { 16928 synchronized (this) { 16929 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 16930 // its own permission (same as profileControl). 16931 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 16932 != PackageManager.PERMISSION_GRANTED) { 16933 throw new SecurityException("Requires permission " 16934 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 16935 } 16936 16937 if (fd == null) { 16938 throw new IllegalArgumentException("null fd"); 16939 } 16940 16941 ProcessRecord proc = findProcessLocked(process, userId, "dumpHeap"); 16942 if (proc == null || proc.thread == null) { 16943 throw new IllegalArgumentException("Unknown process: " + process); 16944 } 16945 16946 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 16947 if (!isDebuggable) { 16948 if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 16949 throw new SecurityException("Process not debuggable: " + proc); 16950 } 16951 } 16952 16953 proc.thread.dumpHeap(managed, path, fd); 16954 fd = null; 16955 return true; 16956 } 16957 } catch (RemoteException e) { 16958 throw new IllegalStateException("Process disappeared"); 16959 } finally { 16960 if (fd != null) { 16961 try { 16962 fd.close(); 16963 } catch (IOException e) { 16964 } 16965 } 16966 } 16967 } 16968 16969 /** In this method we try to acquire our lock to make sure that we have not deadlocked */ 16970 public void monitor() { 16971 synchronized (this) { } 16972 } 16973 16974 void onCoreSettingsChange(Bundle settings) { 16975 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 16976 ProcessRecord processRecord = mLruProcesses.get(i); 16977 try { 16978 if (processRecord.thread != null) { 16979 processRecord.thread.setCoreSettings(settings); 16980 } 16981 } catch (RemoteException re) { 16982 /* ignore */ 16983 } 16984 } 16985 } 16986 16987 // Multi-user methods 16988 16989 /** 16990 * Start user, if its not already running, but don't bring it to foreground. 16991 */ 16992 @Override 16993 public boolean startUserInBackground(final int userId) { 16994 return startUser(userId, /* foreground */ false); 16995 } 16996 16997 /** 16998 * Refreshes the list of users related to the current user when either a 16999 * user switch happens or when a new related user is started in the 17000 * background. 17001 */ 17002 private void updateCurrentProfileIdsLocked() { 17003 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17004 mCurrentUserId, false /* enabledOnly */); 17005 int[] currentProfileIds = new int[profiles.size()]; // profiles will not be null 17006 for (int i = 0; i < currentProfileIds.length; i++) { 17007 currentProfileIds[i] = profiles.get(i).id; 17008 } 17009 mCurrentProfileIds = currentProfileIds; 17010 17011 synchronized (mUserProfileGroupIdsSelfLocked) { 17012 mUserProfileGroupIdsSelfLocked.clear(); 17013 final List<UserInfo> users = getUserManagerLocked().getUsers(false); 17014 for (int i = 0; i < users.size(); i++) { 17015 UserInfo user = users.get(i); 17016 if (user.profileGroupId != UserInfo.NO_PROFILE_GROUP_ID) { 17017 mUserProfileGroupIdsSelfLocked.put(user.id, user.profileGroupId); 17018 } 17019 } 17020 } 17021 } 17022 17023 private Set getProfileIdsLocked(int userId) { 17024 Set userIds = new HashSet<Integer>(); 17025 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17026 userId, false /* enabledOnly */); 17027 for (UserInfo user : profiles) { 17028 userIds.add(Integer.valueOf(user.id)); 17029 } 17030 return userIds; 17031 } 17032 17033 @Override 17034 public boolean switchUser(final int userId) { 17035 return startUser(userId, /* foregound */ true); 17036 } 17037 17038 private boolean startUser(final int userId, boolean foreground) { 17039 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17040 != PackageManager.PERMISSION_GRANTED) { 17041 String msg = "Permission Denial: switchUser() from pid=" 17042 + Binder.getCallingPid() 17043 + ", uid=" + Binder.getCallingUid() 17044 + " requires " + INTERACT_ACROSS_USERS_FULL; 17045 Slog.w(TAG, msg); 17046 throw new SecurityException(msg); 17047 } 17048 17049 if (DEBUG_MU) Slog.i(TAG_MU, "starting userid:" + userId + " fore:" + foreground); 17050 17051 final long ident = Binder.clearCallingIdentity(); 17052 try { 17053 synchronized (this) { 17054 final int oldUserId = mCurrentUserId; 17055 if (oldUserId == userId) { 17056 return true; 17057 } 17058 17059 mStackSupervisor.setLockTaskModeLocked(null, false); 17060 17061 final UserInfo userInfo = getUserManagerLocked().getUserInfo(userId); 17062 if (userInfo == null) { 17063 Slog.w(TAG, "No user info for user #" + userId); 17064 return false; 17065 } 17066 17067 if (foreground) { 17068 mWindowManager.startFreezingScreen(R.anim.screen_user_exit, 17069 R.anim.screen_user_enter); 17070 } 17071 17072 boolean needStart = false; 17073 17074 // If the user we are switching to is not currently started, then 17075 // we need to start it now. 17076 if (mStartedUsers.get(userId) == null) { 17077 mStartedUsers.put(userId, new UserStartedState(new UserHandle(userId), false)); 17078 updateStartedUserArrayLocked(); 17079 needStart = true; 17080 } 17081 17082 final Integer userIdInt = Integer.valueOf(userId); 17083 mUserLru.remove(userIdInt); 17084 mUserLru.add(userIdInt); 17085 17086 if (foreground) { 17087 mCurrentUserId = userId; 17088 updateCurrentProfileIdsLocked(); 17089 mWindowManager.setCurrentUser(userId, mCurrentProfileIds); 17090 // Once the internal notion of the active user has switched, we lock the device 17091 // with the option to show the user switcher on the keyguard. 17092 mWindowManager.lockNow(null); 17093 } else { 17094 final Integer currentUserIdInt = Integer.valueOf(mCurrentUserId); 17095 updateCurrentProfileIdsLocked(); 17096 mWindowManager.setCurrentProfileIds(mCurrentProfileIds); 17097 mUserLru.remove(currentUserIdInt); 17098 mUserLru.add(currentUserIdInt); 17099 } 17100 17101 final UserStartedState uss = mStartedUsers.get(userId); 17102 17103 // Make sure user is in the started state. If it is currently 17104 // stopping, we need to knock that off. 17105 if (uss.mState == UserStartedState.STATE_STOPPING) { 17106 // If we are stopping, we haven't sent ACTION_SHUTDOWN, 17107 // so we can just fairly silently bring the user back from 17108 // the almost-dead. 17109 uss.mState = UserStartedState.STATE_RUNNING; 17110 updateStartedUserArrayLocked(); 17111 needStart = true; 17112 } else if (uss.mState == UserStartedState.STATE_SHUTDOWN) { 17113 // This means ACTION_SHUTDOWN has been sent, so we will 17114 // need to treat this as a new boot of the user. 17115 uss.mState = UserStartedState.STATE_BOOTING; 17116 updateStartedUserArrayLocked(); 17117 needStart = true; 17118 } 17119 17120 if (uss.mState == UserStartedState.STATE_BOOTING) { 17121 // Booting up a new user, need to tell system services about it. 17122 // Note that this is on the same handler as scheduling of broadcasts, 17123 // which is important because it needs to go first. 17124 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_START_MSG, userId)); 17125 } 17126 17127 if (foreground) { 17128 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_CURRENT_MSG, userId, 17129 oldUserId)); 17130 mHandler.removeMessages(REPORT_USER_SWITCH_MSG); 17131 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 17132 mHandler.sendMessage(mHandler.obtainMessage(REPORT_USER_SWITCH_MSG, 17133 oldUserId, userId, uss)); 17134 mHandler.sendMessageDelayed(mHandler.obtainMessage(USER_SWITCH_TIMEOUT_MSG, 17135 oldUserId, userId, uss), USER_SWITCH_TIMEOUT); 17136 } 17137 17138 if (needStart) { 17139 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 17140 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 17141 | Intent.FLAG_RECEIVER_FOREGROUND); 17142 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17143 broadcastIntentLocked(null, null, intent, 17144 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 17145 false, false, MY_PID, Process.SYSTEM_UID, userId); 17146 } 17147 17148 if ((userInfo.flags&UserInfo.FLAG_INITIALIZED) == 0) { 17149 if (userId != UserHandle.USER_OWNER) { 17150 Intent intent = new Intent(Intent.ACTION_USER_INITIALIZE); 17151 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 17152 broadcastIntentLocked(null, null, intent, null, 17153 new IIntentReceiver.Stub() { 17154 public void performReceive(Intent intent, int resultCode, 17155 String data, Bundle extras, boolean ordered, 17156 boolean sticky, int sendingUser) { 17157 userInitialized(uss, userId); 17158 } 17159 }, 0, null, null, null, AppOpsManager.OP_NONE, 17160 true, false, MY_PID, Process.SYSTEM_UID, 17161 userId); 17162 uss.initializing = true; 17163 } else { 17164 getUserManagerLocked().makeInitialized(userInfo.id); 17165 } 17166 } 17167 17168 if (foreground) { 17169 boolean homeInFront = mStackSupervisor.switchUserLocked(userId, uss); 17170 if (homeInFront) { 17171 startHomeActivityLocked(userId); 17172 } else { 17173 mStackSupervisor.resumeTopActivitiesLocked(); 17174 } 17175 EventLogTags.writeAmSwitchUser(userId); 17176 getUserManagerLocked().userForeground(userId); 17177 sendUserSwitchBroadcastsLocked(oldUserId, userId); 17178 } else { 17179 mStackSupervisor.startBackgroundUserLocked(userId, uss); 17180 } 17181 17182 if (needStart) { 17183 Intent intent = new Intent(Intent.ACTION_USER_STARTING); 17184 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 17185 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17186 broadcastIntentLocked(null, null, intent, 17187 null, new IIntentReceiver.Stub() { 17188 @Override 17189 public void performReceive(Intent intent, int resultCode, String data, 17190 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 17191 throws RemoteException { 17192 } 17193 }, 0, null, null, 17194 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 17195 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 17196 } 17197 } 17198 } finally { 17199 Binder.restoreCallingIdentity(ident); 17200 } 17201 17202 return true; 17203 } 17204 17205 void sendUserSwitchBroadcastsLocked(int oldUserId, int newUserId) { 17206 long ident = Binder.clearCallingIdentity(); 17207 try { 17208 Intent intent; 17209 if (oldUserId >= 0) { 17210 // Send USER_BACKGROUND broadcast to all profiles of the outgoing user 17211 List<UserInfo> profiles = mUserManager.getProfiles(oldUserId, false); 17212 int count = profiles.size(); 17213 for (int i = 0; i < count; i++) { 17214 int profileUserId = profiles.get(i).id; 17215 intent = new Intent(Intent.ACTION_USER_BACKGROUND); 17216 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 17217 | Intent.FLAG_RECEIVER_FOREGROUND); 17218 intent.putExtra(Intent.EXTRA_USER_HANDLE, profileUserId); 17219 broadcastIntentLocked(null, null, intent, 17220 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 17221 false, false, MY_PID, Process.SYSTEM_UID, profileUserId); 17222 } 17223 } 17224 if (newUserId >= 0) { 17225 // Send USER_FOREGROUND broadcast to all profiles of the incoming user 17226 List<UserInfo> profiles = mUserManager.getProfiles(newUserId, false); 17227 int count = profiles.size(); 17228 for (int i = 0; i < count; i++) { 17229 int profileUserId = profiles.get(i).id; 17230 intent = new Intent(Intent.ACTION_USER_FOREGROUND); 17231 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 17232 | Intent.FLAG_RECEIVER_FOREGROUND); 17233 intent.putExtra(Intent.EXTRA_USER_HANDLE, profileUserId); 17234 broadcastIntentLocked(null, null, intent, 17235 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 17236 false, false, MY_PID, Process.SYSTEM_UID, profileUserId); 17237 } 17238 intent = new Intent(Intent.ACTION_USER_SWITCHED); 17239 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 17240 | Intent.FLAG_RECEIVER_FOREGROUND); 17241 intent.putExtra(Intent.EXTRA_USER_HANDLE, newUserId); 17242 broadcastIntentLocked(null, null, intent, 17243 null, null, 0, null, null, 17244 android.Manifest.permission.MANAGE_USERS, AppOpsManager.OP_NONE, 17245 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 17246 } 17247 } finally { 17248 Binder.restoreCallingIdentity(ident); 17249 } 17250 } 17251 17252 void dispatchUserSwitch(final UserStartedState uss, final int oldUserId, 17253 final int newUserId) { 17254 final int N = mUserSwitchObservers.beginBroadcast(); 17255 if (N > 0) { 17256 final IRemoteCallback callback = new IRemoteCallback.Stub() { 17257 int mCount = 0; 17258 @Override 17259 public void sendResult(Bundle data) throws RemoteException { 17260 synchronized (ActivityManagerService.this) { 17261 if (mCurUserSwitchCallback == this) { 17262 mCount++; 17263 if (mCount == N) { 17264 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 17265 } 17266 } 17267 } 17268 } 17269 }; 17270 synchronized (this) { 17271 uss.switching = true; 17272 mCurUserSwitchCallback = callback; 17273 } 17274 for (int i=0; i<N; i++) { 17275 try { 17276 mUserSwitchObservers.getBroadcastItem(i).onUserSwitching( 17277 newUserId, callback); 17278 } catch (RemoteException e) { 17279 } 17280 } 17281 } else { 17282 synchronized (this) { 17283 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 17284 } 17285 } 17286 mUserSwitchObservers.finishBroadcast(); 17287 } 17288 17289 void timeoutUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 17290 synchronized (this) { 17291 Slog.w(TAG, "User switch timeout: from " + oldUserId + " to " + newUserId); 17292 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 17293 } 17294 } 17295 17296 void sendContinueUserSwitchLocked(UserStartedState uss, int oldUserId, int newUserId) { 17297 mCurUserSwitchCallback = null; 17298 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 17299 mHandler.sendMessage(mHandler.obtainMessage(CONTINUE_USER_SWITCH_MSG, 17300 oldUserId, newUserId, uss)); 17301 } 17302 17303 void userInitialized(UserStartedState uss, int newUserId) { 17304 completeSwitchAndInitalize(uss, newUserId, true, false); 17305 } 17306 17307 void continueUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 17308 completeSwitchAndInitalize(uss, newUserId, false, true); 17309 } 17310 17311 void completeSwitchAndInitalize(UserStartedState uss, int newUserId, 17312 boolean clearInitializing, boolean clearSwitching) { 17313 boolean unfrozen = false; 17314 synchronized (this) { 17315 if (clearInitializing) { 17316 uss.initializing = false; 17317 getUserManagerLocked().makeInitialized(uss.mHandle.getIdentifier()); 17318 } 17319 if (clearSwitching) { 17320 uss.switching = false; 17321 } 17322 if (!uss.switching && !uss.initializing) { 17323 mWindowManager.stopFreezingScreen(); 17324 unfrozen = true; 17325 } 17326 } 17327 if (unfrozen) { 17328 final int N = mUserSwitchObservers.beginBroadcast(); 17329 for (int i=0; i<N; i++) { 17330 try { 17331 mUserSwitchObservers.getBroadcastItem(i).onUserSwitchComplete(newUserId); 17332 } catch (RemoteException e) { 17333 } 17334 } 17335 mUserSwitchObservers.finishBroadcast(); 17336 } 17337 } 17338 17339 void scheduleStartProfilesLocked() { 17340 if (!mHandler.hasMessages(START_PROFILES_MSG)) { 17341 mHandler.sendMessageDelayed(mHandler.obtainMessage(START_PROFILES_MSG), 17342 DateUtils.SECOND_IN_MILLIS); 17343 } 17344 } 17345 17346 void startProfilesLocked() { 17347 if (DEBUG_MU) Slog.i(TAG_MU, "startProfilesLocked"); 17348 List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17349 mCurrentUserId, false /* enabledOnly */); 17350 List<UserInfo> toStart = new ArrayList<UserInfo>(profiles.size()); 17351 for (UserInfo user : profiles) { 17352 if ((user.flags & UserInfo.FLAG_INITIALIZED) == UserInfo.FLAG_INITIALIZED 17353 && user.id != mCurrentUserId) { 17354 toStart.add(user); 17355 } 17356 } 17357 final int n = toStart.size(); 17358 int i = 0; 17359 for (; i < n && i < (MAX_RUNNING_USERS - 1); ++i) { 17360 startUserInBackground(toStart.get(i).id); 17361 } 17362 if (i < n) { 17363 Slog.w(TAG_MU, "More profiles than MAX_RUNNING_USERS"); 17364 } 17365 } 17366 17367 void finishUserBoot(UserStartedState uss) { 17368 synchronized (this) { 17369 if (uss.mState == UserStartedState.STATE_BOOTING 17370 && mStartedUsers.get(uss.mHandle.getIdentifier()) == uss) { 17371 uss.mState = UserStartedState.STATE_RUNNING; 17372 final int userId = uss.mHandle.getIdentifier(); 17373 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 17374 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17375 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 17376 broadcastIntentLocked(null, null, intent, 17377 null, null, 0, null, null, 17378 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, AppOpsManager.OP_NONE, 17379 true, false, MY_PID, Process.SYSTEM_UID, userId); 17380 } 17381 } 17382 } 17383 17384 void finishUserSwitch(UserStartedState uss) { 17385 synchronized (this) { 17386 finishUserBoot(uss); 17387 17388 startProfilesLocked(); 17389 17390 int num = mUserLru.size(); 17391 int i = 0; 17392 while (num > MAX_RUNNING_USERS && i < mUserLru.size()) { 17393 Integer oldUserId = mUserLru.get(i); 17394 UserStartedState oldUss = mStartedUsers.get(oldUserId); 17395 if (oldUss == null) { 17396 // Shouldn't happen, but be sane if it does. 17397 mUserLru.remove(i); 17398 num--; 17399 continue; 17400 } 17401 if (oldUss.mState == UserStartedState.STATE_STOPPING 17402 || oldUss.mState == UserStartedState.STATE_SHUTDOWN) { 17403 // This user is already stopping, doesn't count. 17404 num--; 17405 i++; 17406 continue; 17407 } 17408 if (oldUserId == UserHandle.USER_OWNER || oldUserId == mCurrentUserId) { 17409 // Owner and current can't be stopped, but count as running. 17410 i++; 17411 continue; 17412 } 17413 // This is a user to be stopped. 17414 stopUserLocked(oldUserId, null); 17415 num--; 17416 i++; 17417 } 17418 } 17419 } 17420 17421 @Override 17422 public int stopUser(final int userId, final IStopUserCallback callback) { 17423 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17424 != PackageManager.PERMISSION_GRANTED) { 17425 String msg = "Permission Denial: switchUser() from pid=" 17426 + Binder.getCallingPid() 17427 + ", uid=" + Binder.getCallingUid() 17428 + " requires " + INTERACT_ACROSS_USERS_FULL; 17429 Slog.w(TAG, msg); 17430 throw new SecurityException(msg); 17431 } 17432 if (userId <= 0) { 17433 throw new IllegalArgumentException("Can't stop primary user " + userId); 17434 } 17435 synchronized (this) { 17436 return stopUserLocked(userId, callback); 17437 } 17438 } 17439 17440 private int stopUserLocked(final int userId, final IStopUserCallback callback) { 17441 if (DEBUG_MU) Slog.i(TAG_MU, "stopUserLocked userId=" + userId); 17442 if (mCurrentUserId == userId) { 17443 return ActivityManager.USER_OP_IS_CURRENT; 17444 } 17445 17446 final UserStartedState uss = mStartedUsers.get(userId); 17447 if (uss == null) { 17448 // User is not started, nothing to do... but we do need to 17449 // callback if requested. 17450 if (callback != null) { 17451 mHandler.post(new Runnable() { 17452 @Override 17453 public void run() { 17454 try { 17455 callback.userStopped(userId); 17456 } catch (RemoteException e) { 17457 } 17458 } 17459 }); 17460 } 17461 return ActivityManager.USER_OP_SUCCESS; 17462 } 17463 17464 if (callback != null) { 17465 uss.mStopCallbacks.add(callback); 17466 } 17467 17468 if (uss.mState != UserStartedState.STATE_STOPPING 17469 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17470 uss.mState = UserStartedState.STATE_STOPPING; 17471 updateStartedUserArrayLocked(); 17472 17473 long ident = Binder.clearCallingIdentity(); 17474 try { 17475 // We are going to broadcast ACTION_USER_STOPPING and then 17476 // once that is done send a final ACTION_SHUTDOWN and then 17477 // stop the user. 17478 final Intent stoppingIntent = new Intent(Intent.ACTION_USER_STOPPING); 17479 stoppingIntent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 17480 stoppingIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17481 stoppingIntent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 17482 final Intent shutdownIntent = new Intent(Intent.ACTION_SHUTDOWN); 17483 // This is the result receiver for the final shutdown broadcast. 17484 final IIntentReceiver shutdownReceiver = new IIntentReceiver.Stub() { 17485 @Override 17486 public void performReceive(Intent intent, int resultCode, String data, 17487 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 17488 finishUserStop(uss); 17489 } 17490 }; 17491 // This is the result receiver for the initial stopping broadcast. 17492 final IIntentReceiver stoppingReceiver = new IIntentReceiver.Stub() { 17493 @Override 17494 public void performReceive(Intent intent, int resultCode, String data, 17495 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 17496 // On to the next. 17497 synchronized (ActivityManagerService.this) { 17498 if (uss.mState != UserStartedState.STATE_STOPPING) { 17499 // Whoops, we are being started back up. Abort, abort! 17500 return; 17501 } 17502 uss.mState = UserStartedState.STATE_SHUTDOWN; 17503 } 17504 mBatteryStatsService.noteEvent( 17505 BatteryStats.HistoryItem.EVENT_USER_RUNNING_FINISH, 17506 Integer.toString(userId), userId); 17507 mSystemServiceManager.stopUser(userId); 17508 broadcastIntentLocked(null, null, shutdownIntent, 17509 null, shutdownReceiver, 0, null, null, null, AppOpsManager.OP_NONE, 17510 true, false, MY_PID, Process.SYSTEM_UID, userId); 17511 } 17512 }; 17513 // Kick things off. 17514 broadcastIntentLocked(null, null, stoppingIntent, 17515 null, stoppingReceiver, 0, null, null, 17516 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 17517 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 17518 } finally { 17519 Binder.restoreCallingIdentity(ident); 17520 } 17521 } 17522 17523 return ActivityManager.USER_OP_SUCCESS; 17524 } 17525 17526 void finishUserStop(UserStartedState uss) { 17527 final int userId = uss.mHandle.getIdentifier(); 17528 boolean stopped; 17529 ArrayList<IStopUserCallback> callbacks; 17530 synchronized (this) { 17531 callbacks = new ArrayList<IStopUserCallback>(uss.mStopCallbacks); 17532 if (mStartedUsers.get(userId) != uss) { 17533 stopped = false; 17534 } else if (uss.mState != UserStartedState.STATE_SHUTDOWN) { 17535 stopped = false; 17536 } else { 17537 stopped = true; 17538 // User can no longer run. 17539 mStartedUsers.remove(userId); 17540 mUserLru.remove(Integer.valueOf(userId)); 17541 updateStartedUserArrayLocked(); 17542 17543 // Clean up all state and processes associated with the user. 17544 // Kill all the processes for the user. 17545 forceStopUserLocked(userId, "finish user"); 17546 } 17547 } 17548 17549 for (int i=0; i<callbacks.size(); i++) { 17550 try { 17551 if (stopped) callbacks.get(i).userStopped(userId); 17552 else callbacks.get(i).userStopAborted(userId); 17553 } catch (RemoteException e) { 17554 } 17555 } 17556 17557 if (stopped) { 17558 mSystemServiceManager.cleanupUser(userId); 17559 synchronized (this) { 17560 mStackSupervisor.removeUserLocked(userId); 17561 } 17562 } 17563 } 17564 17565 @Override 17566 public UserInfo getCurrentUser() { 17567 if ((checkCallingPermission(INTERACT_ACROSS_USERS) 17568 != PackageManager.PERMISSION_GRANTED) && ( 17569 checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17570 != PackageManager.PERMISSION_GRANTED)) { 17571 String msg = "Permission Denial: getCurrentUser() from pid=" 17572 + Binder.getCallingPid() 17573 + ", uid=" + Binder.getCallingUid() 17574 + " requires " + INTERACT_ACROSS_USERS; 17575 Slog.w(TAG, msg); 17576 throw new SecurityException(msg); 17577 } 17578 synchronized (this) { 17579 return getUserManagerLocked().getUserInfo(mCurrentUserId); 17580 } 17581 } 17582 17583 int getCurrentUserIdLocked() { 17584 return mCurrentUserId; 17585 } 17586 17587 @Override 17588 public boolean isUserRunning(int userId, boolean orStopped) { 17589 if (checkCallingPermission(INTERACT_ACROSS_USERS) 17590 != PackageManager.PERMISSION_GRANTED) { 17591 String msg = "Permission Denial: isUserRunning() from pid=" 17592 + Binder.getCallingPid() 17593 + ", uid=" + Binder.getCallingUid() 17594 + " requires " + INTERACT_ACROSS_USERS; 17595 Slog.w(TAG, msg); 17596 throw new SecurityException(msg); 17597 } 17598 synchronized (this) { 17599 return isUserRunningLocked(userId, orStopped); 17600 } 17601 } 17602 17603 boolean isUserRunningLocked(int userId, boolean orStopped) { 17604 UserStartedState state = mStartedUsers.get(userId); 17605 if (state == null) { 17606 return false; 17607 } 17608 if (orStopped) { 17609 return true; 17610 } 17611 return state.mState != UserStartedState.STATE_STOPPING 17612 && state.mState != UserStartedState.STATE_SHUTDOWN; 17613 } 17614 17615 @Override 17616 public int[] getRunningUserIds() { 17617 if (checkCallingPermission(INTERACT_ACROSS_USERS) 17618 != PackageManager.PERMISSION_GRANTED) { 17619 String msg = "Permission Denial: isUserRunning() from pid=" 17620 + Binder.getCallingPid() 17621 + ", uid=" + Binder.getCallingUid() 17622 + " requires " + INTERACT_ACROSS_USERS; 17623 Slog.w(TAG, msg); 17624 throw new SecurityException(msg); 17625 } 17626 synchronized (this) { 17627 return mStartedUserArray; 17628 } 17629 } 17630 17631 private void updateStartedUserArrayLocked() { 17632 int num = 0; 17633 for (int i=0; i<mStartedUsers.size(); i++) { 17634 UserStartedState uss = mStartedUsers.valueAt(i); 17635 // This list does not include stopping users. 17636 if (uss.mState != UserStartedState.STATE_STOPPING 17637 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17638 num++; 17639 } 17640 } 17641 mStartedUserArray = new int[num]; 17642 num = 0; 17643 for (int i=0; i<mStartedUsers.size(); i++) { 17644 UserStartedState uss = mStartedUsers.valueAt(i); 17645 if (uss.mState != UserStartedState.STATE_STOPPING 17646 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17647 mStartedUserArray[num] = mStartedUsers.keyAt(i); 17648 num++; 17649 } 17650 } 17651 } 17652 17653 @Override 17654 public void registerUserSwitchObserver(IUserSwitchObserver observer) { 17655 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17656 != PackageManager.PERMISSION_GRANTED) { 17657 String msg = "Permission Denial: registerUserSwitchObserver() from pid=" 17658 + Binder.getCallingPid() 17659 + ", uid=" + Binder.getCallingUid() 17660 + " requires " + INTERACT_ACROSS_USERS_FULL; 17661 Slog.w(TAG, msg); 17662 throw new SecurityException(msg); 17663 } 17664 17665 mUserSwitchObservers.register(observer); 17666 } 17667 17668 @Override 17669 public void unregisterUserSwitchObserver(IUserSwitchObserver observer) { 17670 mUserSwitchObservers.unregister(observer); 17671 } 17672 17673 private boolean userExists(int userId) { 17674 if (userId == 0) { 17675 return true; 17676 } 17677 UserManagerService ums = getUserManagerLocked(); 17678 return ums != null ? (ums.getUserInfo(userId) != null) : false; 17679 } 17680 17681 int[] getUsersLocked() { 17682 UserManagerService ums = getUserManagerLocked(); 17683 return ums != null ? ums.getUserIds() : new int[] { 0 }; 17684 } 17685 17686 UserManagerService getUserManagerLocked() { 17687 if (mUserManager == null) { 17688 IBinder b = ServiceManager.getService(Context.USER_SERVICE); 17689 mUserManager = (UserManagerService)IUserManager.Stub.asInterface(b); 17690 } 17691 return mUserManager; 17692 } 17693 17694 private int applyUserId(int uid, int userId) { 17695 return UserHandle.getUid(userId, uid); 17696 } 17697 17698 ApplicationInfo getAppInfoForUser(ApplicationInfo info, int userId) { 17699 if (info == null) return null; 17700 ApplicationInfo newInfo = new ApplicationInfo(info); 17701 newInfo.uid = applyUserId(info.uid, userId); 17702 newInfo.dataDir = USER_DATA_DIR + userId + "/" 17703 + info.packageName; 17704 return newInfo; 17705 } 17706 17707 ActivityInfo getActivityInfoForUser(ActivityInfo aInfo, int userId) { 17708 if (aInfo == null 17709 || (userId < 1 && aInfo.applicationInfo.uid < UserHandle.PER_USER_RANGE)) { 17710 return aInfo; 17711 } 17712 17713 ActivityInfo info = new ActivityInfo(aInfo); 17714 info.applicationInfo = getAppInfoForUser(info.applicationInfo, userId); 17715 return info; 17716 } 17717 17718 private final class LocalService extends ActivityManagerInternal { 17719 @Override 17720 public void goingToSleep() { 17721 ActivityManagerService.this.goingToSleep(); 17722 } 17723 17724 @Override 17725 public void wakingUp() { 17726 ActivityManagerService.this.wakingUp(); 17727 } 17728 } 17729 17730 /** 17731 * An implementation of IAppTask, that allows an app to manage its own tasks via 17732 * {@link android.app.ActivityManager.AppTask}. We keep track of the callingUid to ensure that 17733 * only the process that calls getAppTasks() can call the AppTask methods. 17734 */ 17735 class AppTaskImpl extends IAppTask.Stub { 17736 private int mTaskId; 17737 private int mCallingUid; 17738 17739 public AppTaskImpl(int taskId, int callingUid) { 17740 mTaskId = taskId; 17741 mCallingUid = callingUid; 17742 } 17743 17744 @Override 17745 public void finishAndRemoveTask() { 17746 // Ensure that we are called from the same process that created this AppTask 17747 if (mCallingUid != Binder.getCallingUid()) { 17748 Slog.w(TAG, "finishAndRemoveTask: caller " + mCallingUid 17749 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 17750 return; 17751 } 17752 17753 synchronized (ActivityManagerService.this) { 17754 long origId = Binder.clearCallingIdentity(); 17755 try { 17756 TaskRecord tr = recentTaskForIdLocked(mTaskId); 17757 if (tr != null) { 17758 // Only kill the process if we are not a new document 17759 int flags = tr.getBaseIntent().getFlags(); 17760 boolean isDocument = (flags & Intent.FLAG_ACTIVITY_NEW_DOCUMENT) == 17761 Intent.FLAG_ACTIVITY_NEW_DOCUMENT; 17762 removeTaskByIdLocked(mTaskId, 17763 !isDocument ? ActivityManager.REMOVE_TASK_KILL_PROCESS : 0); 17764 } 17765 } finally { 17766 Binder.restoreCallingIdentity(origId); 17767 } 17768 } 17769 } 17770 17771 @Override 17772 public ActivityManager.RecentTaskInfo getTaskInfo() { 17773 // Ensure that we are called from the same process that created this AppTask 17774 if (mCallingUid != Binder.getCallingUid()) { 17775 Slog.w(TAG, "finishAndRemoveTask: caller " + mCallingUid 17776 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 17777 return null; 17778 } 17779 17780 synchronized (ActivityManagerService.this) { 17781 long origId = Binder.clearCallingIdentity(); 17782 try { 17783 TaskRecord tr = recentTaskForIdLocked(mTaskId); 17784 if (tr != null) { 17785 return createRecentTaskInfoFromTaskRecord(tr); 17786 } 17787 } finally { 17788 Binder.restoreCallingIdentity(origId); 17789 } 17790 return null; 17791 } 17792 } 17793 } 17794} 17795