ActivityManagerService.java revision f4f8bb793fe101af770dc974b29c26722bce285f
1/* 2 * Copyright (C) 2006-2008 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17package com.android.server.am; 18 19import static android.Manifest.permission.INTERACT_ACROSS_USERS; 20import static android.Manifest.permission.INTERACT_ACROSS_USERS_FULL; 21import static android.Manifest.permission.START_TASKS_FROM_RECENTS; 22import static android.content.pm.PackageManager.PERMISSION_GRANTED; 23import static com.android.internal.util.XmlUtils.readBooleanAttribute; 24import static com.android.internal.util.XmlUtils.readIntAttribute; 25import static com.android.internal.util.XmlUtils.readLongAttribute; 26import static com.android.internal.util.XmlUtils.writeBooleanAttribute; 27import static com.android.internal.util.XmlUtils.writeIntAttribute; 28import static com.android.internal.util.XmlUtils.writeLongAttribute; 29import static com.android.server.Watchdog.NATIVE_STACKS_OF_INTEREST; 30import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT; 31import static org.xmlpull.v1.XmlPullParser.START_TAG; 32import static com.android.server.am.ActivityStackSupervisor.HOME_STACK_ID; 33 34import android.Manifest; 35import android.app.AppOpsManager; 36import android.app.IActivityContainer; 37import android.app.IActivityContainerCallback; 38import android.app.IAppTask; 39import android.app.admin.DevicePolicyManager; 40import android.app.usage.UsageStats; 41import android.app.usage.UsageStatsManagerInternal; 42import android.appwidget.AppWidgetManager; 43import android.graphics.Rect; 44import android.os.BatteryStats; 45import android.os.PersistableBundle; 46import android.service.voice.IVoiceInteractionSession; 47import android.util.ArrayMap; 48import android.util.ArraySet; 49import android.util.SparseIntArray; 50 51import com.android.internal.R; 52import com.android.internal.annotations.GuardedBy; 53import com.android.internal.app.IAppOpsService; 54import com.android.internal.app.IVoiceInteractor; 55import com.android.internal.app.ProcessMap; 56import com.android.internal.app.ProcessStats; 57import com.android.internal.content.PackageMonitor; 58import com.android.internal.os.BackgroundThread; 59import com.android.internal.os.BatteryStatsImpl; 60import com.android.internal.os.ProcessCpuTracker; 61import com.android.internal.os.TransferPipe; 62import com.android.internal.os.Zygote; 63import com.android.internal.util.FastPrintWriter; 64import com.android.internal.util.FastXmlSerializer; 65import com.android.internal.util.MemInfoReader; 66import com.android.internal.util.Preconditions; 67import com.android.server.AppOpsService; 68import com.android.server.AttributeCache; 69import com.android.server.IntentResolver; 70import com.android.server.LocalServices; 71import com.android.server.ServiceThread; 72import com.android.server.SystemService; 73import com.android.server.SystemServiceManager; 74import com.android.server.Watchdog; 75import com.android.server.am.ActivityStack.ActivityState; 76import com.android.server.firewall.IntentFirewall; 77import com.android.server.pm.UserManagerService; 78import com.android.server.wm.AppTransition; 79import com.android.server.wm.WindowManagerService; 80import com.google.android.collect.Lists; 81import com.google.android.collect.Maps; 82 83import libcore.io.IoUtils; 84 85import org.xmlpull.v1.XmlPullParser; 86import org.xmlpull.v1.XmlPullParserException; 87import org.xmlpull.v1.XmlSerializer; 88 89import android.app.Activity; 90import android.app.ActivityManager; 91import android.app.ActivityManager.RunningTaskInfo; 92import android.app.ActivityManager.StackInfo; 93import android.app.ActivityManagerInternal; 94import android.app.ActivityManagerNative; 95import android.app.ActivityOptions; 96import android.app.ActivityThread; 97import android.app.AlertDialog; 98import android.app.AppGlobals; 99import android.app.ApplicationErrorReport; 100import android.app.Dialog; 101import android.app.IActivityController; 102import android.app.IApplicationThread; 103import android.app.IInstrumentationWatcher; 104import android.app.INotificationManager; 105import android.app.IProcessObserver; 106import android.app.IServiceConnection; 107import android.app.IStopUserCallback; 108import android.app.IUiAutomationConnection; 109import android.app.IUserSwitchObserver; 110import android.app.Instrumentation; 111import android.app.Notification; 112import android.app.NotificationManager; 113import android.app.PendingIntent; 114import android.app.backup.IBackupManager; 115import android.content.ActivityNotFoundException; 116import android.content.BroadcastReceiver; 117import android.content.ClipData; 118import android.content.ComponentCallbacks2; 119import android.content.ComponentName; 120import android.content.ContentProvider; 121import android.content.ContentResolver; 122import android.content.Context; 123import android.content.DialogInterface; 124import android.content.IContentProvider; 125import android.content.IIntentReceiver; 126import android.content.IIntentSender; 127import android.content.Intent; 128import android.content.IntentFilter; 129import android.content.IntentSender; 130import android.content.pm.ActivityInfo; 131import android.content.pm.ApplicationInfo; 132import android.content.pm.ConfigurationInfo; 133import android.content.pm.IPackageDataObserver; 134import android.content.pm.IPackageManager; 135import android.content.pm.InstrumentationInfo; 136import android.content.pm.PackageInfo; 137import android.content.pm.PackageManager; 138import android.content.pm.ParceledListSlice; 139import android.content.pm.UserInfo; 140import android.content.pm.PackageManager.NameNotFoundException; 141import android.content.pm.PathPermission; 142import android.content.pm.ProviderInfo; 143import android.content.pm.ResolveInfo; 144import android.content.pm.ServiceInfo; 145import android.content.res.CompatibilityInfo; 146import android.content.res.Configuration; 147import android.net.Proxy; 148import android.net.ProxyInfo; 149import android.net.Uri; 150import android.os.Binder; 151import android.os.Build; 152import android.os.Bundle; 153import android.os.Debug; 154import android.os.DropBoxManager; 155import android.os.Environment; 156import android.os.FactoryTest; 157import android.os.FileObserver; 158import android.os.FileUtils; 159import android.os.Handler; 160import android.os.IBinder; 161import android.os.IPermissionController; 162import android.os.IRemoteCallback; 163import android.os.IUserManager; 164import android.os.Looper; 165import android.os.Message; 166import android.os.Parcel; 167import android.os.ParcelFileDescriptor; 168import android.os.Process; 169import android.os.RemoteCallbackList; 170import android.os.RemoteException; 171import android.os.SELinux; 172import android.os.ServiceManager; 173import android.os.StrictMode; 174import android.os.SystemClock; 175import android.os.SystemProperties; 176import android.os.UpdateLock; 177import android.os.UserHandle; 178import android.provider.Settings; 179import android.text.format.DateUtils; 180import android.text.format.Time; 181import android.util.AtomicFile; 182import android.util.EventLog; 183import android.util.Log; 184import android.util.Pair; 185import android.util.PrintWriterPrinter; 186import android.util.Slog; 187import android.util.SparseArray; 188import android.util.TimeUtils; 189import android.util.Xml; 190import android.view.Gravity; 191import android.view.LayoutInflater; 192import android.view.View; 193import android.view.WindowManager; 194 195import java.io.BufferedInputStream; 196import java.io.BufferedOutputStream; 197import java.io.DataInputStream; 198import java.io.DataOutputStream; 199import java.io.File; 200import java.io.FileDescriptor; 201import java.io.FileInputStream; 202import java.io.FileNotFoundException; 203import java.io.FileOutputStream; 204import java.io.IOException; 205import java.io.InputStreamReader; 206import java.io.PrintWriter; 207import java.io.StringWriter; 208import java.lang.ref.WeakReference; 209import java.util.ArrayList; 210import java.util.Arrays; 211import java.util.Collections; 212import java.util.Comparator; 213import java.util.HashMap; 214import java.util.HashSet; 215import java.util.Iterator; 216import java.util.List; 217import java.util.Locale; 218import java.util.Map; 219import java.util.Set; 220import java.util.concurrent.atomic.AtomicBoolean; 221import java.util.concurrent.atomic.AtomicLong; 222 223public final class ActivityManagerService extends ActivityManagerNative 224 implements Watchdog.Monitor, BatteryStatsImpl.BatteryCallback { 225 226 private static final String USER_DATA_DIR = "/data/user/"; 227 // File that stores last updated system version and called preboot receivers 228 static final String CALLED_PRE_BOOTS_FILENAME = "called_pre_boots.dat"; 229 230 static final String TAG = "ActivityManager"; 231 static final String TAG_MU = "ActivityManagerServiceMU"; 232 static final boolean DEBUG = false; 233 static final boolean localLOGV = DEBUG; 234 static final boolean DEBUG_BACKUP = localLOGV || false; 235 static final boolean DEBUG_BROADCAST = localLOGV || false; 236 static final boolean DEBUG_BROADCAST_LIGHT = DEBUG_BROADCAST || false; 237 static final boolean DEBUG_BACKGROUND_BROADCAST = DEBUG_BROADCAST || false; 238 static final boolean DEBUG_CLEANUP = localLOGV || false; 239 static final boolean DEBUG_CONFIGURATION = localLOGV || false; 240 static final boolean DEBUG_FOCUS = false; 241 static final boolean DEBUG_IMMERSIVE = localLOGV || false; 242 static final boolean DEBUG_MU = localLOGV || false; 243 static final boolean DEBUG_OOM_ADJ = localLOGV || false; 244 static final boolean DEBUG_LRU = localLOGV || false; 245 static final boolean DEBUG_PAUSE = localLOGV || false; 246 static final boolean DEBUG_POWER = localLOGV || false; 247 static final boolean DEBUG_POWER_QUICK = DEBUG_POWER || false; 248 static final boolean DEBUG_PROCESS_OBSERVERS = localLOGV || false; 249 static final boolean DEBUG_PROCESSES = localLOGV || false; 250 static final boolean DEBUG_PROVIDER = localLOGV || false; 251 static final boolean DEBUG_RESULTS = localLOGV || false; 252 static final boolean DEBUG_SERVICE = localLOGV || false; 253 static final boolean DEBUG_SERVICE_EXECUTING = localLOGV || false; 254 static final boolean DEBUG_STACK = localLOGV || false; 255 static final boolean DEBUG_SWITCH = localLOGV || false; 256 static final boolean DEBUG_TASKS = localLOGV || false; 257 static final boolean DEBUG_THUMBNAILS = localLOGV || false; 258 static final boolean DEBUG_TRANSITION = localLOGV || false; 259 static final boolean DEBUG_URI_PERMISSION = localLOGV || false; 260 static final boolean DEBUG_USER_LEAVING = localLOGV || false; 261 static final boolean DEBUG_VISBILITY = localLOGV || false; 262 static final boolean DEBUG_PSS = localLOGV || false; 263 static final boolean DEBUG_LOCKSCREEN = localLOGV || false; 264 static final boolean VALIDATE_TOKENS = false; 265 static final boolean SHOW_ACTIVITY_START_TIME = true; 266 267 // Control over CPU and battery monitoring. 268 static final long BATTERY_STATS_TIME = 30*60*1000; // write battery stats every 30 minutes. 269 static final boolean MONITOR_CPU_USAGE = true; 270 static final long MONITOR_CPU_MIN_TIME = 5*1000; // don't sample cpu less than every 5 seconds. 271 static final long MONITOR_CPU_MAX_TIME = 0x0fffffff; // wait possibly forever for next cpu sample. 272 static final boolean MONITOR_THREAD_CPU_USAGE = false; 273 274 // The flags that are set for all calls we make to the package manager. 275 static final int STOCK_PM_FLAGS = PackageManager.GET_SHARED_LIBRARY_FILES; 276 277 private static final String SYSTEM_DEBUGGABLE = "ro.debuggable"; 278 279 static final boolean IS_USER_BUILD = "user".equals(Build.TYPE); 280 281 // Maximum number of recent tasks that we can remember. 282 static final int MAX_RECENT_TASKS = ActivityManager.isLowRamDeviceStatic() ? 100 : 200; 283 284 // Maximum number recent bitmaps to keep in memory. 285 static final int MAX_RECENT_BITMAPS = 5; 286 287 // Amount of time after a call to stopAppSwitches() during which we will 288 // prevent further untrusted switches from happening. 289 static final long APP_SWITCH_DELAY_TIME = 5*1000; 290 291 // How long we wait for a launched process to attach to the activity manager 292 // before we decide it's never going to come up for real. 293 static final int PROC_START_TIMEOUT = 10*1000; 294 295 // How long we wait for a launched process to attach to the activity manager 296 // before we decide it's never going to come up for real, when the process was 297 // started with a wrapper for instrumentation (such as Valgrind) because it 298 // could take much longer than usual. 299 static final int PROC_START_TIMEOUT_WITH_WRAPPER = 1200*1000; 300 301 // How long to wait after going idle before forcing apps to GC. 302 static final int GC_TIMEOUT = 5*1000; 303 304 // The minimum amount of time between successive GC requests for a process. 305 static final int GC_MIN_INTERVAL = 60*1000; 306 307 // The minimum amount of time between successive PSS requests for a process. 308 static final int FULL_PSS_MIN_INTERVAL = 10*60*1000; 309 310 // The minimum amount of time between successive PSS requests for a process 311 // when the request is due to the memory state being lowered. 312 static final int FULL_PSS_LOWERED_INTERVAL = 2*60*1000; 313 314 // The rate at which we check for apps using excessive power -- 15 mins. 315 static final int POWER_CHECK_DELAY = (DEBUG_POWER_QUICK ? 2 : 15) * 60*1000; 316 317 // The minimum sample duration we will allow before deciding we have 318 // enough data on wake locks to start killing things. 319 static final int WAKE_LOCK_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 320 321 // The minimum sample duration we will allow before deciding we have 322 // enough data on CPU usage to start killing things. 323 static final int CPU_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 324 325 // How long we allow a receiver to run before giving up on it. 326 static final int BROADCAST_FG_TIMEOUT = 10*1000; 327 static final int BROADCAST_BG_TIMEOUT = 60*1000; 328 329 // How long we wait until we timeout on key dispatching. 330 static final int KEY_DISPATCHING_TIMEOUT = 5*1000; 331 332 // How long we wait until we timeout on key dispatching during instrumentation. 333 static final int INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT = 60*1000; 334 335 // Amount of time we wait for observers to handle a user switch before 336 // giving up on them and unfreezing the screen. 337 static final int USER_SWITCH_TIMEOUT = 2*1000; 338 339 // Maximum number of users we allow to be running at a time. 340 static final int MAX_RUNNING_USERS = 3; 341 342 // How long to wait in getAssistContextExtras for the activity and foreground services 343 // to respond with the result. 344 static final int PENDING_ASSIST_EXTRAS_TIMEOUT = 500; 345 346 // Maximum number of persisted Uri grants a package is allowed 347 static final int MAX_PERSISTED_URI_GRANTS = 128; 348 349 static final int MY_PID = Process.myPid(); 350 351 static final String[] EMPTY_STRING_ARRAY = new String[0]; 352 353 // How many bytes to write into the dropbox log before truncating 354 static final int DROPBOX_MAX_SIZE = 256 * 1024; 355 356 // Access modes for handleIncomingUser. 357 static final int ALLOW_NON_FULL = 0; 358 static final int ALLOW_NON_FULL_IN_PROFILE = 1; 359 static final int ALLOW_FULL_ONLY = 2; 360 361 static final int LAST_PREBOOT_DELIVERED_FILE_VERSION = 10000; 362 363 /** All system services */ 364 SystemServiceManager mSystemServiceManager; 365 366 /** Run all ActivityStacks through this */ 367 ActivityStackSupervisor mStackSupervisor; 368 369 public IntentFirewall mIntentFirewall; 370 371 // Whether we should show our dialogs (ANR, crash, etc) or just perform their 372 // default actuion automatically. Important for devices without direct input 373 // devices. 374 private boolean mShowDialogs = true; 375 376 BroadcastQueue mFgBroadcastQueue; 377 BroadcastQueue mBgBroadcastQueue; 378 // Convenient for easy iteration over the queues. Foreground is first 379 // so that dispatch of foreground broadcasts gets precedence. 380 final BroadcastQueue[] mBroadcastQueues = new BroadcastQueue[2]; 381 382 BroadcastQueue broadcastQueueForIntent(Intent intent) { 383 final boolean isFg = (intent.getFlags() & Intent.FLAG_RECEIVER_FOREGROUND) != 0; 384 if (DEBUG_BACKGROUND_BROADCAST) { 385 Slog.i(TAG, "Broadcast intent " + intent + " on " 386 + (isFg ? "foreground" : "background") 387 + " queue"); 388 } 389 return (isFg) ? mFgBroadcastQueue : mBgBroadcastQueue; 390 } 391 392 BroadcastRecord broadcastRecordForReceiverLocked(IBinder receiver) { 393 for (BroadcastQueue queue : mBroadcastQueues) { 394 BroadcastRecord r = queue.getMatchingOrderedReceiver(receiver); 395 if (r != null) { 396 return r; 397 } 398 } 399 return null; 400 } 401 402 /** 403 * Activity we have told the window manager to have key focus. 404 */ 405 ActivityRecord mFocusedActivity = null; 406 407 /** 408 * List of intents that were used to start the most recent tasks. 409 */ 410 ArrayList<TaskRecord> mRecentTasks; 411 ArraySet<TaskRecord> mTmpRecents = new ArraySet<TaskRecord>(); 412 413 public class PendingAssistExtras extends Binder implements Runnable { 414 public final ActivityRecord activity; 415 public boolean haveResult = false; 416 public Bundle result = null; 417 public PendingAssistExtras(ActivityRecord _activity) { 418 activity = _activity; 419 } 420 @Override 421 public void run() { 422 Slog.w(TAG, "getAssistContextExtras failed: timeout retrieving from " + activity); 423 synchronized (this) { 424 haveResult = true; 425 notifyAll(); 426 } 427 } 428 } 429 430 final ArrayList<PendingAssistExtras> mPendingAssistExtras 431 = new ArrayList<PendingAssistExtras>(); 432 433 /** 434 * Process management. 435 */ 436 final ProcessList mProcessList = new ProcessList(); 437 438 /** 439 * All of the applications we currently have running organized by name. 440 * The keys are strings of the application package name (as 441 * returned by the package manager), and the keys are ApplicationRecord 442 * objects. 443 */ 444 final ProcessMap<ProcessRecord> mProcessNames = new ProcessMap<ProcessRecord>(); 445 446 /** 447 * Tracking long-term execution of processes to look for abuse and other 448 * bad app behavior. 449 */ 450 final ProcessStatsService mProcessStats; 451 452 /** 453 * The currently running isolated processes. 454 */ 455 final SparseArray<ProcessRecord> mIsolatedProcesses = new SparseArray<ProcessRecord>(); 456 457 /** 458 * Counter for assigning isolated process uids, to avoid frequently reusing the 459 * same ones. 460 */ 461 int mNextIsolatedProcessUid = 0; 462 463 /** 464 * The currently running heavy-weight process, if any. 465 */ 466 ProcessRecord mHeavyWeightProcess = null; 467 468 /** 469 * The last time that various processes have crashed. 470 */ 471 final ProcessMap<Long> mProcessCrashTimes = new ProcessMap<Long>(); 472 473 /** 474 * Information about a process that is currently marked as bad. 475 */ 476 static final class BadProcessInfo { 477 BadProcessInfo(long time, String shortMsg, String longMsg, String stack) { 478 this.time = time; 479 this.shortMsg = shortMsg; 480 this.longMsg = longMsg; 481 this.stack = stack; 482 } 483 484 final long time; 485 final String shortMsg; 486 final String longMsg; 487 final String stack; 488 } 489 490 /** 491 * Set of applications that we consider to be bad, and will reject 492 * incoming broadcasts from (which the user has no control over). 493 * Processes are added to this set when they have crashed twice within 494 * a minimum amount of time; they are removed from it when they are 495 * later restarted (hopefully due to some user action). The value is the 496 * time it was added to the list. 497 */ 498 final ProcessMap<BadProcessInfo> mBadProcesses = new ProcessMap<BadProcessInfo>(); 499 500 /** 501 * All of the processes we currently have running organized by pid. 502 * The keys are the pid running the application. 503 * 504 * <p>NOTE: This object is protected by its own lock, NOT the global 505 * activity manager lock! 506 */ 507 final SparseArray<ProcessRecord> mPidsSelfLocked = new SparseArray<ProcessRecord>(); 508 509 /** 510 * All of the processes that have been forced to be foreground. The key 511 * is the pid of the caller who requested it (we hold a death 512 * link on it). 513 */ 514 abstract class ForegroundToken implements IBinder.DeathRecipient { 515 int pid; 516 IBinder token; 517 } 518 final SparseArray<ForegroundToken> mForegroundProcesses = new SparseArray<ForegroundToken>(); 519 520 /** 521 * List of records for processes that someone had tried to start before the 522 * system was ready. We don't start them at that point, but ensure they 523 * are started by the time booting is complete. 524 */ 525 final ArrayList<ProcessRecord> mProcessesOnHold = new ArrayList<ProcessRecord>(); 526 527 /** 528 * List of persistent applications that are in the process 529 * of being started. 530 */ 531 final ArrayList<ProcessRecord> mPersistentStartingProcesses = new ArrayList<ProcessRecord>(); 532 533 /** 534 * Processes that are being forcibly torn down. 535 */ 536 final ArrayList<ProcessRecord> mRemovedProcesses = new ArrayList<ProcessRecord>(); 537 538 /** 539 * List of running applications, sorted by recent usage. 540 * The first entry in the list is the least recently used. 541 */ 542 final ArrayList<ProcessRecord> mLruProcesses = new ArrayList<ProcessRecord>(); 543 544 /** 545 * Where in mLruProcesses that the processes hosting activities start. 546 */ 547 int mLruProcessActivityStart = 0; 548 549 /** 550 * Where in mLruProcesses that the processes hosting services start. 551 * This is after (lower index) than mLruProcessesActivityStart. 552 */ 553 int mLruProcessServiceStart = 0; 554 555 /** 556 * List of processes that should gc as soon as things are idle. 557 */ 558 final ArrayList<ProcessRecord> mProcessesToGc = new ArrayList<ProcessRecord>(); 559 560 /** 561 * Processes we want to collect PSS data from. 562 */ 563 final ArrayList<ProcessRecord> mPendingPssProcesses = new ArrayList<ProcessRecord>(); 564 565 /** 566 * Last time we requested PSS data of all processes. 567 */ 568 long mLastFullPssTime = SystemClock.uptimeMillis(); 569 570 /** 571 * If set, the next time we collect PSS data we should do a full collection 572 * with data from native processes and the kernel. 573 */ 574 boolean mFullPssPending = false; 575 576 /** 577 * This is the process holding what we currently consider to be 578 * the "home" activity. 579 */ 580 ProcessRecord mHomeProcess; 581 582 /** 583 * This is the process holding the activity the user last visited that 584 * is in a different process from the one they are currently in. 585 */ 586 ProcessRecord mPreviousProcess; 587 588 /** 589 * The time at which the previous process was last visible. 590 */ 591 long mPreviousProcessVisibleTime; 592 593 /** 594 * Which uses have been started, so are allowed to run code. 595 */ 596 final SparseArray<UserStartedState> mStartedUsers = new SparseArray<UserStartedState>(); 597 598 /** 599 * LRU list of history of current users. Most recently current is at the end. 600 */ 601 final ArrayList<Integer> mUserLru = new ArrayList<Integer>(); 602 603 /** 604 * Constant array of the users that are currently started. 605 */ 606 int[] mStartedUserArray = new int[] { 0 }; 607 608 /** 609 * Registered observers of the user switching mechanics. 610 */ 611 final RemoteCallbackList<IUserSwitchObserver> mUserSwitchObservers 612 = new RemoteCallbackList<IUserSwitchObserver>(); 613 614 /** 615 * Currently active user switch. 616 */ 617 Object mCurUserSwitchCallback; 618 619 /** 620 * Packages that the user has asked to have run in screen size 621 * compatibility mode instead of filling the screen. 622 */ 623 final CompatModePackages mCompatModePackages; 624 625 /** 626 * Set of IntentSenderRecord objects that are currently active. 627 */ 628 final HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>> mIntentSenderRecords 629 = new HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>>(); 630 631 /** 632 * Fingerprints (hashCode()) of stack traces that we've 633 * already logged DropBox entries for. Guarded by itself. If 634 * something (rogue user app) forces this over 635 * MAX_DUP_SUPPRESSED_STACKS entries, the contents are cleared. 636 */ 637 private final HashSet<Integer> mAlreadyLoggedViolatedStacks = new HashSet<Integer>(); 638 private static final int MAX_DUP_SUPPRESSED_STACKS = 5000; 639 640 /** 641 * Strict Mode background batched logging state. 642 * 643 * The string buffer is guarded by itself, and its lock is also 644 * used to determine if another batched write is already 645 * in-flight. 646 */ 647 private final StringBuilder mStrictModeBuffer = new StringBuilder(); 648 649 /** 650 * Keeps track of all IIntentReceivers that have been registered for 651 * broadcasts. Hash keys are the receiver IBinder, hash value is 652 * a ReceiverList. 653 */ 654 final HashMap<IBinder, ReceiverList> mRegisteredReceivers = 655 new HashMap<IBinder, ReceiverList>(); 656 657 /** 658 * Resolver for broadcast intents to registered receivers. 659 * Holds BroadcastFilter (subclass of IntentFilter). 660 */ 661 final IntentResolver<BroadcastFilter, BroadcastFilter> mReceiverResolver 662 = new IntentResolver<BroadcastFilter, BroadcastFilter>() { 663 @Override 664 protected boolean allowFilterResult( 665 BroadcastFilter filter, List<BroadcastFilter> dest) { 666 IBinder target = filter.receiverList.receiver.asBinder(); 667 for (int i=dest.size()-1; i>=0; i--) { 668 if (dest.get(i).receiverList.receiver.asBinder() == target) { 669 return false; 670 } 671 } 672 return true; 673 } 674 675 @Override 676 protected BroadcastFilter newResult(BroadcastFilter filter, int match, int userId) { 677 if (userId == UserHandle.USER_ALL || filter.owningUserId == UserHandle.USER_ALL 678 || userId == filter.owningUserId) { 679 return super.newResult(filter, match, userId); 680 } 681 return null; 682 } 683 684 @Override 685 protected BroadcastFilter[] newArray(int size) { 686 return new BroadcastFilter[size]; 687 } 688 689 @Override 690 protected boolean isPackageForFilter(String packageName, BroadcastFilter filter) { 691 return packageName.equals(filter.packageName); 692 } 693 }; 694 695 /** 696 * State of all active sticky broadcasts per user. Keys are the action of the 697 * sticky Intent, values are an ArrayList of all broadcasted intents with 698 * that action (which should usually be one). The SparseArray is keyed 699 * by the user ID the sticky is for, and can include UserHandle.USER_ALL 700 * for stickies that are sent to all users. 701 */ 702 final SparseArray<ArrayMap<String, ArrayList<Intent>>> mStickyBroadcasts = 703 new SparseArray<ArrayMap<String, ArrayList<Intent>>>(); 704 705 final ActiveServices mServices; 706 707 /** 708 * Backup/restore process management 709 */ 710 String mBackupAppName = null; 711 BackupRecord mBackupTarget = null; 712 713 final ProviderMap mProviderMap; 714 715 /** 716 * List of content providers who have clients waiting for them. The 717 * application is currently being launched and the provider will be 718 * removed from this list once it is published. 719 */ 720 final ArrayList<ContentProviderRecord> mLaunchingProviders 721 = new ArrayList<ContentProviderRecord>(); 722 723 /** 724 * File storing persisted {@link #mGrantedUriPermissions}. 725 */ 726 private final AtomicFile mGrantFile; 727 728 /** XML constants used in {@link #mGrantFile} */ 729 private static final String TAG_URI_GRANTS = "uri-grants"; 730 private static final String TAG_URI_GRANT = "uri-grant"; 731 private static final String ATTR_USER_HANDLE = "userHandle"; 732 private static final String ATTR_SOURCE_USER_ID = "sourceUserId"; 733 private static final String ATTR_TARGET_USER_ID = "targetUserId"; 734 private static final String ATTR_SOURCE_PKG = "sourcePkg"; 735 private static final String ATTR_TARGET_PKG = "targetPkg"; 736 private static final String ATTR_URI = "uri"; 737 private static final String ATTR_MODE_FLAGS = "modeFlags"; 738 private static final String ATTR_CREATED_TIME = "createdTime"; 739 private static final String ATTR_PREFIX = "prefix"; 740 741 /** 742 * Global set of specific {@link Uri} permissions that have been granted. 743 * This optimized lookup structure maps from {@link UriPermission#targetUid} 744 * to {@link UriPermission#uri} to {@link UriPermission}. 745 */ 746 @GuardedBy("this") 747 private final SparseArray<ArrayMap<GrantUri, UriPermission>> 748 mGrantedUriPermissions = new SparseArray<ArrayMap<GrantUri, UriPermission>>(); 749 750 public static class GrantUri { 751 public final int sourceUserId; 752 public final Uri uri; 753 public boolean prefix; 754 755 public GrantUri(int sourceUserId, Uri uri, boolean prefix) { 756 this.sourceUserId = sourceUserId; 757 this.uri = uri; 758 this.prefix = prefix; 759 } 760 761 @Override 762 public int hashCode() { 763 return toString().hashCode(); 764 } 765 766 @Override 767 public boolean equals(Object o) { 768 if (o instanceof GrantUri) { 769 GrantUri other = (GrantUri) o; 770 return uri.equals(other.uri) && (sourceUserId == other.sourceUserId) 771 && prefix == other.prefix; 772 } 773 return false; 774 } 775 776 @Override 777 public String toString() { 778 String result = Integer.toString(sourceUserId) + " @ " + uri.toString(); 779 if (prefix) result += " [prefix]"; 780 return result; 781 } 782 783 public String toSafeString() { 784 String result = Integer.toString(sourceUserId) + " @ " + uri.toSafeString(); 785 if (prefix) result += " [prefix]"; 786 return result; 787 } 788 789 public static GrantUri resolve(int defaultSourceUserHandle, Uri uri) { 790 return new GrantUri(ContentProvider.getUserIdFromUri(uri, defaultSourceUserHandle), 791 ContentProvider.getUriWithoutUserId(uri), false); 792 } 793 } 794 795 CoreSettingsObserver mCoreSettingsObserver; 796 797 /** 798 * Thread-local storage used to carry caller permissions over through 799 * indirect content-provider access. 800 */ 801 private class Identity { 802 public int pid; 803 public int uid; 804 805 Identity(int _pid, int _uid) { 806 pid = _pid; 807 uid = _uid; 808 } 809 } 810 811 private static final ThreadLocal<Identity> sCallerIdentity = new ThreadLocal<Identity>(); 812 813 /** 814 * All information we have collected about the runtime performance of 815 * any user id that can impact battery performance. 816 */ 817 final BatteryStatsService mBatteryStatsService; 818 819 /** 820 * Information about component usage 821 */ 822 UsageStatsManagerInternal mUsageStatsService; 823 824 /** 825 * Information about and control over application operations 826 */ 827 final AppOpsService mAppOpsService; 828 829 /** 830 * Save recent tasks information across reboots. 831 */ 832 final TaskPersister mTaskPersister; 833 834 /** 835 * Current configuration information. HistoryRecord objects are given 836 * a reference to this object to indicate which configuration they are 837 * currently running in, so this object must be kept immutable. 838 */ 839 Configuration mConfiguration = new Configuration(); 840 841 /** 842 * Current sequencing integer of the configuration, for skipping old 843 * configurations. 844 */ 845 int mConfigurationSeq = 0; 846 847 /** 848 * Hardware-reported OpenGLES version. 849 */ 850 final int GL_ES_VERSION; 851 852 /** 853 * List of initialization arguments to pass to all processes when binding applications to them. 854 * For example, references to the commonly used services. 855 */ 856 HashMap<String, IBinder> mAppBindArgs; 857 858 /** 859 * Temporary to avoid allocations. Protected by main lock. 860 */ 861 final StringBuilder mStringBuilder = new StringBuilder(256); 862 863 /** 864 * Used to control how we initialize the service. 865 */ 866 ComponentName mTopComponent; 867 String mTopAction = Intent.ACTION_MAIN; 868 String mTopData; 869 boolean mProcessesReady = false; 870 boolean mSystemReady = false; 871 boolean mBooting = false; 872 boolean mWaitingUpdate = false; 873 boolean mDidUpdate = false; 874 boolean mOnBattery = false; 875 boolean mLaunchWarningShown = false; 876 877 Context mContext; 878 879 int mFactoryTest; 880 881 boolean mCheckedForSetup; 882 883 /** 884 * The time at which we will allow normal application switches again, 885 * after a call to {@link #stopAppSwitches()}. 886 */ 887 long mAppSwitchesAllowedTime; 888 889 /** 890 * This is set to true after the first switch after mAppSwitchesAllowedTime 891 * is set; any switches after that will clear the time. 892 */ 893 boolean mDidAppSwitch; 894 895 /** 896 * Last time (in realtime) at which we checked for power usage. 897 */ 898 long mLastPowerCheckRealtime; 899 900 /** 901 * Last time (in uptime) at which we checked for power usage. 902 */ 903 long mLastPowerCheckUptime; 904 905 /** 906 * Set while we are wanting to sleep, to prevent any 907 * activities from being started/resumed. 908 */ 909 private boolean mSleeping = false; 910 911 /** 912 * Set while we are running a voice interaction. This overrides 913 * sleeping while it is active. 914 */ 915 private boolean mRunningVoice = false; 916 917 /** 918 * State of external calls telling us if the device is asleep. 919 */ 920 private boolean mWentToSleep = false; 921 922 /** 923 * State of external call telling us if the lock screen is shown. 924 */ 925 private boolean mLockScreenShown = false; 926 927 /** 928 * Set if we are shutting down the system, similar to sleeping. 929 */ 930 boolean mShuttingDown = false; 931 932 /** 933 * Current sequence id for oom_adj computation traversal. 934 */ 935 int mAdjSeq = 0; 936 937 /** 938 * Current sequence id for process LRU updating. 939 */ 940 int mLruSeq = 0; 941 942 /** 943 * Keep track of the non-cached/empty process we last found, to help 944 * determine how to distribute cached/empty processes next time. 945 */ 946 int mNumNonCachedProcs = 0; 947 948 /** 949 * Keep track of the number of cached hidden procs, to balance oom adj 950 * distribution between those and empty procs. 951 */ 952 int mNumCachedHiddenProcs = 0; 953 954 /** 955 * Keep track of the number of service processes we last found, to 956 * determine on the next iteration which should be B services. 957 */ 958 int mNumServiceProcs = 0; 959 int mNewNumAServiceProcs = 0; 960 int mNewNumServiceProcs = 0; 961 962 /** 963 * Allow the current computed overall memory level of the system to go down? 964 * This is set to false when we are killing processes for reasons other than 965 * memory management, so that the now smaller process list will not be taken as 966 * an indication that memory is tighter. 967 */ 968 boolean mAllowLowerMemLevel = false; 969 970 /** 971 * The last computed memory level, for holding when we are in a state that 972 * processes are going away for other reasons. 973 */ 974 int mLastMemoryLevel = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 975 976 /** 977 * The last total number of process we have, to determine if changes actually look 978 * like a shrinking number of process due to lower RAM. 979 */ 980 int mLastNumProcesses; 981 982 /** 983 * The uptime of the last time we performed idle maintenance. 984 */ 985 long mLastIdleTime = SystemClock.uptimeMillis(); 986 987 /** 988 * Total time spent with RAM that has been added in the past since the last idle time. 989 */ 990 long mLowRamTimeSinceLastIdle = 0; 991 992 /** 993 * If RAM is currently low, when that horrible situation started. 994 */ 995 long mLowRamStartTime = 0; 996 997 /** 998 * For reporting to battery stats the current top application. 999 */ 1000 private String mCurResumedPackage = null; 1001 private int mCurResumedUid = -1; 1002 1003 /** 1004 * For reporting to battery stats the apps currently running foreground 1005 * service. The ProcessMap is package/uid tuples; each of these contain 1006 * an array of the currently foreground processes. 1007 */ 1008 final ProcessMap<ArrayList<ProcessRecord>> mForegroundPackages 1009 = new ProcessMap<ArrayList<ProcessRecord>>(); 1010 1011 /** 1012 * This is set if we had to do a delayed dexopt of an app before launching 1013 * it, to increase the ANR timeouts in that case. 1014 */ 1015 boolean mDidDexOpt; 1016 1017 /** 1018 * Set if the systemServer made a call to enterSafeMode. 1019 */ 1020 boolean mSafeMode; 1021 1022 String mDebugApp = null; 1023 boolean mWaitForDebugger = false; 1024 boolean mDebugTransient = false; 1025 String mOrigDebugApp = null; 1026 boolean mOrigWaitForDebugger = false; 1027 boolean mAlwaysFinishActivities = false; 1028 IActivityController mController = null; 1029 String mProfileApp = null; 1030 ProcessRecord mProfileProc = null; 1031 String mProfileFile; 1032 ParcelFileDescriptor mProfileFd; 1033 int mProfileType = 0; 1034 boolean mAutoStopProfiler = false; 1035 String mOpenGlTraceApp = null; 1036 1037 static class ProcessChangeItem { 1038 static final int CHANGE_ACTIVITIES = 1<<0; 1039 static final int CHANGE_PROCESS_STATE = 1<<1; 1040 int changes; 1041 int uid; 1042 int pid; 1043 int processState; 1044 boolean foregroundActivities; 1045 } 1046 1047 final RemoteCallbackList<IProcessObserver> mProcessObservers 1048 = new RemoteCallbackList<IProcessObserver>(); 1049 ProcessChangeItem[] mActiveProcessChanges = new ProcessChangeItem[5]; 1050 1051 final ArrayList<ProcessChangeItem> mPendingProcessChanges 1052 = new ArrayList<ProcessChangeItem>(); 1053 final ArrayList<ProcessChangeItem> mAvailProcessChanges 1054 = new ArrayList<ProcessChangeItem>(); 1055 1056 /** 1057 * Runtime CPU use collection thread. This object's lock is used to 1058 * protect all related state. 1059 */ 1060 final Thread mProcessCpuThread; 1061 1062 /** 1063 * Used to collect process stats when showing not responding dialog. 1064 * Protected by mProcessCpuThread. 1065 */ 1066 final ProcessCpuTracker mProcessCpuTracker = new ProcessCpuTracker( 1067 MONITOR_THREAD_CPU_USAGE); 1068 final AtomicLong mLastCpuTime = new AtomicLong(0); 1069 final AtomicBoolean mProcessCpuMutexFree = new AtomicBoolean(true); 1070 1071 long mLastWriteTime = 0; 1072 1073 /** 1074 * Used to retain an update lock when the foreground activity is in 1075 * immersive mode. 1076 */ 1077 final UpdateLock mUpdateLock = new UpdateLock("immersive"); 1078 1079 /** 1080 * Set to true after the system has finished booting. 1081 */ 1082 boolean mBooted = false; 1083 1084 int mProcessLimit = ProcessList.MAX_CACHED_APPS; 1085 int mProcessLimitOverride = -1; 1086 1087 WindowManagerService mWindowManager; 1088 1089 final ActivityThread mSystemThread; 1090 1091 int mCurrentUserId = 0; 1092 int[] mCurrentProfileIds = new int[] {UserHandle.USER_OWNER}; // Accessed by ActivityStack 1093 1094 /** 1095 * Mapping from each known user ID to the profile group ID it is associated with. 1096 */ 1097 SparseIntArray mUserProfileGroupIdsSelfLocked = new SparseIntArray(); 1098 1099 private UserManagerService mUserManager; 1100 1101 private final class AppDeathRecipient implements IBinder.DeathRecipient { 1102 final ProcessRecord mApp; 1103 final int mPid; 1104 final IApplicationThread mAppThread; 1105 1106 AppDeathRecipient(ProcessRecord app, int pid, 1107 IApplicationThread thread) { 1108 if (localLOGV) Slog.v( 1109 TAG, "New death recipient " + this 1110 + " for thread " + thread.asBinder()); 1111 mApp = app; 1112 mPid = pid; 1113 mAppThread = thread; 1114 } 1115 1116 @Override 1117 public void binderDied() { 1118 if (localLOGV) Slog.v( 1119 TAG, "Death received in " + this 1120 + " for thread " + mAppThread.asBinder()); 1121 synchronized(ActivityManagerService.this) { 1122 appDiedLocked(mApp, mPid, mAppThread); 1123 } 1124 } 1125 } 1126 1127 static final int SHOW_ERROR_MSG = 1; 1128 static final int SHOW_NOT_RESPONDING_MSG = 2; 1129 static final int SHOW_FACTORY_ERROR_MSG = 3; 1130 static final int UPDATE_CONFIGURATION_MSG = 4; 1131 static final int GC_BACKGROUND_PROCESSES_MSG = 5; 1132 static final int WAIT_FOR_DEBUGGER_MSG = 6; 1133 static final int SERVICE_TIMEOUT_MSG = 12; 1134 static final int UPDATE_TIME_ZONE = 13; 1135 static final int SHOW_UID_ERROR_MSG = 14; 1136 static final int IM_FEELING_LUCKY_MSG = 15; 1137 static final int PROC_START_TIMEOUT_MSG = 20; 1138 static final int DO_PENDING_ACTIVITY_LAUNCHES_MSG = 21; 1139 static final int KILL_APPLICATION_MSG = 22; 1140 static final int FINALIZE_PENDING_INTENT_MSG = 23; 1141 static final int POST_HEAVY_NOTIFICATION_MSG = 24; 1142 static final int CANCEL_HEAVY_NOTIFICATION_MSG = 25; 1143 static final int SHOW_STRICT_MODE_VIOLATION_MSG = 26; 1144 static final int CHECK_EXCESSIVE_WAKE_LOCKS_MSG = 27; 1145 static final int CLEAR_DNS_CACHE_MSG = 28; 1146 static final int UPDATE_HTTP_PROXY_MSG = 29; 1147 static final int SHOW_COMPAT_MODE_DIALOG_MSG = 30; 1148 static final int DISPATCH_PROCESSES_CHANGED = 31; 1149 static final int DISPATCH_PROCESS_DIED = 32; 1150 static final int REPORT_MEM_USAGE_MSG = 33; 1151 static final int REPORT_USER_SWITCH_MSG = 34; 1152 static final int CONTINUE_USER_SWITCH_MSG = 35; 1153 static final int USER_SWITCH_TIMEOUT_MSG = 36; 1154 static final int IMMERSIVE_MODE_LOCK_MSG = 37; 1155 static final int PERSIST_URI_GRANTS_MSG = 38; 1156 static final int REQUEST_ALL_PSS_MSG = 39; 1157 static final int START_PROFILES_MSG = 40; 1158 static final int UPDATE_TIME = 41; 1159 static final int SYSTEM_USER_START_MSG = 42; 1160 static final int SYSTEM_USER_CURRENT_MSG = 43; 1161 static final int ENTER_ANIMATION_COMPLETE_MSG = 44; 1162 static final int ENABLE_SCREEN_AFTER_BOOT_MSG = 45; 1163 1164 static final int FIRST_ACTIVITY_STACK_MSG = 100; 1165 static final int FIRST_BROADCAST_QUEUE_MSG = 200; 1166 static final int FIRST_COMPAT_MODE_MSG = 300; 1167 static final int FIRST_SUPERVISOR_STACK_MSG = 100; 1168 1169 AlertDialog mUidAlert; 1170 CompatModeDialog mCompatModeDialog; 1171 long mLastMemUsageReportTime = 0; 1172 1173 private LockToAppRequestDialog mLockToAppRequest; 1174 1175 /** 1176 * Flag whether the current user is a "monkey", i.e. whether 1177 * the UI is driven by a UI automation tool. 1178 */ 1179 private boolean mUserIsMonkey; 1180 1181 /** Flag whether the device has a recents UI */ 1182 final boolean mHasRecents; 1183 1184 final ServiceThread mHandlerThread; 1185 final MainHandler mHandler; 1186 1187 final class MainHandler extends Handler { 1188 public MainHandler(Looper looper) { 1189 super(looper, null, true); 1190 } 1191 1192 @Override 1193 public void handleMessage(Message msg) { 1194 switch (msg.what) { 1195 case SHOW_ERROR_MSG: { 1196 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1197 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 1198 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 1199 synchronized (ActivityManagerService.this) { 1200 ProcessRecord proc = (ProcessRecord)data.get("app"); 1201 AppErrorResult res = (AppErrorResult) data.get("result"); 1202 if (proc != null && proc.crashDialog != null) { 1203 Slog.e(TAG, "App already has crash dialog: " + proc); 1204 if (res != null) { 1205 res.set(0); 1206 } 1207 return; 1208 } 1209 if (!showBackground && UserHandle.getAppId(proc.uid) 1210 >= Process.FIRST_APPLICATION_UID && proc.userId != mCurrentUserId 1211 && proc.pid != MY_PID) { 1212 Slog.w(TAG, "Skipping crash dialog of " + proc + ": background"); 1213 if (res != null) { 1214 res.set(0); 1215 } 1216 return; 1217 } 1218 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1219 Dialog d = new AppErrorDialog(mContext, 1220 ActivityManagerService.this, res, proc); 1221 d.show(); 1222 proc.crashDialog = d; 1223 } else { 1224 // The device is asleep, so just pretend that the user 1225 // saw a crash dialog and hit "force quit". 1226 if (res != null) { 1227 res.set(0); 1228 } 1229 } 1230 } 1231 1232 ensureBootCompleted(); 1233 } break; 1234 case SHOW_NOT_RESPONDING_MSG: { 1235 synchronized (ActivityManagerService.this) { 1236 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1237 ProcessRecord proc = (ProcessRecord)data.get("app"); 1238 if (proc != null && proc.anrDialog != null) { 1239 Slog.e(TAG, "App already has anr dialog: " + proc); 1240 return; 1241 } 1242 1243 Intent intent = new Intent("android.intent.action.ANR"); 1244 if (!mProcessesReady) { 1245 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 1246 | Intent.FLAG_RECEIVER_FOREGROUND); 1247 } 1248 broadcastIntentLocked(null, null, intent, 1249 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 1250 false, false, MY_PID, Process.SYSTEM_UID, 0 /* TODO: Verify */); 1251 1252 if (mShowDialogs) { 1253 Dialog d = new AppNotRespondingDialog(ActivityManagerService.this, 1254 mContext, proc, (ActivityRecord)data.get("activity"), 1255 msg.arg1 != 0); 1256 d.show(); 1257 proc.anrDialog = d; 1258 } else { 1259 // Just kill the app if there is no dialog to be shown. 1260 killAppAtUsersRequest(proc, null); 1261 } 1262 } 1263 1264 ensureBootCompleted(); 1265 } break; 1266 case SHOW_STRICT_MODE_VIOLATION_MSG: { 1267 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1268 synchronized (ActivityManagerService.this) { 1269 ProcessRecord proc = (ProcessRecord) data.get("app"); 1270 if (proc == null) { 1271 Slog.e(TAG, "App not found when showing strict mode dialog."); 1272 break; 1273 } 1274 if (proc.crashDialog != null) { 1275 Slog.e(TAG, "App already has strict mode dialog: " + proc); 1276 return; 1277 } 1278 AppErrorResult res = (AppErrorResult) data.get("result"); 1279 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1280 Dialog d = new StrictModeViolationDialog(mContext, 1281 ActivityManagerService.this, res, proc); 1282 d.show(); 1283 proc.crashDialog = d; 1284 } else { 1285 // The device is asleep, so just pretend that the user 1286 // saw a crash dialog and hit "force quit". 1287 res.set(0); 1288 } 1289 } 1290 ensureBootCompleted(); 1291 } break; 1292 case SHOW_FACTORY_ERROR_MSG: { 1293 Dialog d = new FactoryErrorDialog( 1294 mContext, msg.getData().getCharSequence("msg")); 1295 d.show(); 1296 ensureBootCompleted(); 1297 } break; 1298 case UPDATE_CONFIGURATION_MSG: { 1299 final ContentResolver resolver = mContext.getContentResolver(); 1300 Settings.System.putConfiguration(resolver, (Configuration)msg.obj); 1301 } break; 1302 case GC_BACKGROUND_PROCESSES_MSG: { 1303 synchronized (ActivityManagerService.this) { 1304 performAppGcsIfAppropriateLocked(); 1305 } 1306 } break; 1307 case WAIT_FOR_DEBUGGER_MSG: { 1308 synchronized (ActivityManagerService.this) { 1309 ProcessRecord app = (ProcessRecord)msg.obj; 1310 if (msg.arg1 != 0) { 1311 if (!app.waitedForDebugger) { 1312 Dialog d = new AppWaitingForDebuggerDialog( 1313 ActivityManagerService.this, 1314 mContext, app); 1315 app.waitDialog = d; 1316 app.waitedForDebugger = true; 1317 d.show(); 1318 } 1319 } else { 1320 if (app.waitDialog != null) { 1321 app.waitDialog.dismiss(); 1322 app.waitDialog = null; 1323 } 1324 } 1325 } 1326 } break; 1327 case SERVICE_TIMEOUT_MSG: { 1328 if (mDidDexOpt) { 1329 mDidDexOpt = false; 1330 Message nmsg = mHandler.obtainMessage(SERVICE_TIMEOUT_MSG); 1331 nmsg.obj = msg.obj; 1332 mHandler.sendMessageDelayed(nmsg, ActiveServices.SERVICE_TIMEOUT); 1333 return; 1334 } 1335 mServices.serviceTimeout((ProcessRecord)msg.obj); 1336 } break; 1337 case UPDATE_TIME_ZONE: { 1338 synchronized (ActivityManagerService.this) { 1339 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1340 ProcessRecord r = mLruProcesses.get(i); 1341 if (r.thread != null) { 1342 try { 1343 r.thread.updateTimeZone(); 1344 } catch (RemoteException ex) { 1345 Slog.w(TAG, "Failed to update time zone for: " + r.info.processName); 1346 } 1347 } 1348 } 1349 } 1350 } break; 1351 case CLEAR_DNS_CACHE_MSG: { 1352 synchronized (ActivityManagerService.this) { 1353 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1354 ProcessRecord r = mLruProcesses.get(i); 1355 if (r.thread != null) { 1356 try { 1357 r.thread.clearDnsCache(); 1358 } catch (RemoteException ex) { 1359 Slog.w(TAG, "Failed to clear dns cache for: " + r.info.processName); 1360 } 1361 } 1362 } 1363 } 1364 } break; 1365 case UPDATE_HTTP_PROXY_MSG: { 1366 ProxyInfo proxy = (ProxyInfo)msg.obj; 1367 String host = ""; 1368 String port = ""; 1369 String exclList = ""; 1370 Uri pacFileUrl = Uri.EMPTY; 1371 if (proxy != null) { 1372 host = proxy.getHost(); 1373 port = Integer.toString(proxy.getPort()); 1374 exclList = proxy.getExclusionListAsString(); 1375 pacFileUrl = proxy.getPacFileUrl(); 1376 } 1377 synchronized (ActivityManagerService.this) { 1378 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1379 ProcessRecord r = mLruProcesses.get(i); 1380 if (r.thread != null) { 1381 try { 1382 r.thread.setHttpProxy(host, port, exclList, pacFileUrl); 1383 } catch (RemoteException ex) { 1384 Slog.w(TAG, "Failed to update http proxy for: " + 1385 r.info.processName); 1386 } 1387 } 1388 } 1389 } 1390 } break; 1391 case SHOW_UID_ERROR_MSG: { 1392 String title = "System UIDs Inconsistent"; 1393 String text = "UIDs on the system are inconsistent, you need to wipe your" 1394 + " data partition or your device will be unstable."; 1395 Log.e(TAG, title + ": " + text); 1396 if (mShowDialogs) { 1397 // XXX This is a temporary dialog, no need to localize. 1398 AlertDialog d = new BaseErrorDialog(mContext); 1399 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 1400 d.setCancelable(false); 1401 d.setTitle(title); 1402 d.setMessage(text); 1403 d.setButton(DialogInterface.BUTTON_POSITIVE, "I'm Feeling Lucky", 1404 mHandler.obtainMessage(IM_FEELING_LUCKY_MSG)); 1405 mUidAlert = d; 1406 d.show(); 1407 } 1408 } break; 1409 case IM_FEELING_LUCKY_MSG: { 1410 if (mUidAlert != null) { 1411 mUidAlert.dismiss(); 1412 mUidAlert = null; 1413 } 1414 } break; 1415 case PROC_START_TIMEOUT_MSG: { 1416 if (mDidDexOpt) { 1417 mDidDexOpt = false; 1418 Message nmsg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 1419 nmsg.obj = msg.obj; 1420 mHandler.sendMessageDelayed(nmsg, PROC_START_TIMEOUT); 1421 return; 1422 } 1423 ProcessRecord app = (ProcessRecord)msg.obj; 1424 synchronized (ActivityManagerService.this) { 1425 processStartTimedOutLocked(app); 1426 } 1427 } break; 1428 case DO_PENDING_ACTIVITY_LAUNCHES_MSG: { 1429 synchronized (ActivityManagerService.this) { 1430 mStackSupervisor.doPendingActivityLaunchesLocked(true); 1431 } 1432 } break; 1433 case KILL_APPLICATION_MSG: { 1434 synchronized (ActivityManagerService.this) { 1435 int appid = msg.arg1; 1436 boolean restart = (msg.arg2 == 1); 1437 Bundle bundle = (Bundle)msg.obj; 1438 String pkg = bundle.getString("pkg"); 1439 String reason = bundle.getString("reason"); 1440 forceStopPackageLocked(pkg, appid, restart, false, true, false, 1441 false, UserHandle.USER_ALL, reason); 1442 } 1443 } break; 1444 case FINALIZE_PENDING_INTENT_MSG: { 1445 ((PendingIntentRecord)msg.obj).completeFinalize(); 1446 } break; 1447 case POST_HEAVY_NOTIFICATION_MSG: { 1448 INotificationManager inm = NotificationManager.getService(); 1449 if (inm == null) { 1450 return; 1451 } 1452 1453 ActivityRecord root = (ActivityRecord)msg.obj; 1454 ProcessRecord process = root.app; 1455 if (process == null) { 1456 return; 1457 } 1458 1459 try { 1460 Context context = mContext.createPackageContext(process.info.packageName, 0); 1461 String text = mContext.getString(R.string.heavy_weight_notification, 1462 context.getApplicationInfo().loadLabel(context.getPackageManager())); 1463 Notification notification = new Notification(); 1464 notification.icon = com.android.internal.R.drawable.stat_sys_adb; //context.getApplicationInfo().icon; 1465 notification.when = 0; 1466 notification.flags = Notification.FLAG_ONGOING_EVENT; 1467 notification.tickerText = text; 1468 notification.defaults = 0; // please be quiet 1469 notification.sound = null; 1470 notification.vibrate = null; 1471 notification.setLatestEventInfo(context, text, 1472 mContext.getText(R.string.heavy_weight_notification_detail), 1473 PendingIntent.getActivityAsUser(mContext, 0, root.intent, 1474 PendingIntent.FLAG_CANCEL_CURRENT, null, 1475 new UserHandle(root.userId))); 1476 1477 try { 1478 int[] outId = new int[1]; 1479 inm.enqueueNotificationWithTag("android", "android", null, 1480 R.string.heavy_weight_notification, 1481 notification, outId, root.userId); 1482 } catch (RuntimeException e) { 1483 Slog.w(ActivityManagerService.TAG, 1484 "Error showing notification for heavy-weight app", e); 1485 } catch (RemoteException e) { 1486 } 1487 } catch (NameNotFoundException e) { 1488 Slog.w(TAG, "Unable to create context for heavy notification", e); 1489 } 1490 } break; 1491 case CANCEL_HEAVY_NOTIFICATION_MSG: { 1492 INotificationManager inm = NotificationManager.getService(); 1493 if (inm == null) { 1494 return; 1495 } 1496 try { 1497 inm.cancelNotificationWithTag("android", null, 1498 R.string.heavy_weight_notification, msg.arg1); 1499 } catch (RuntimeException e) { 1500 Slog.w(ActivityManagerService.TAG, 1501 "Error canceling notification for service", e); 1502 } catch (RemoteException e) { 1503 } 1504 } break; 1505 case CHECK_EXCESSIVE_WAKE_LOCKS_MSG: { 1506 synchronized (ActivityManagerService.this) { 1507 checkExcessivePowerUsageLocked(true); 1508 removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1509 Message nmsg = obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1510 sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 1511 } 1512 } break; 1513 case SHOW_COMPAT_MODE_DIALOG_MSG: { 1514 synchronized (ActivityManagerService.this) { 1515 ActivityRecord ar = (ActivityRecord)msg.obj; 1516 if (mCompatModeDialog != null) { 1517 if (mCompatModeDialog.mAppInfo.packageName.equals( 1518 ar.info.applicationInfo.packageName)) { 1519 return; 1520 } 1521 mCompatModeDialog.dismiss(); 1522 mCompatModeDialog = null; 1523 } 1524 if (ar != null && false) { 1525 if (mCompatModePackages.getPackageAskCompatModeLocked( 1526 ar.packageName)) { 1527 int mode = mCompatModePackages.computeCompatModeLocked( 1528 ar.info.applicationInfo); 1529 if (mode == ActivityManager.COMPAT_MODE_DISABLED 1530 || mode == ActivityManager.COMPAT_MODE_ENABLED) { 1531 mCompatModeDialog = new CompatModeDialog( 1532 ActivityManagerService.this, mContext, 1533 ar.info.applicationInfo); 1534 mCompatModeDialog.show(); 1535 } 1536 } 1537 } 1538 } 1539 break; 1540 } 1541 case DISPATCH_PROCESSES_CHANGED: { 1542 dispatchProcessesChanged(); 1543 break; 1544 } 1545 case DISPATCH_PROCESS_DIED: { 1546 final int pid = msg.arg1; 1547 final int uid = msg.arg2; 1548 dispatchProcessDied(pid, uid); 1549 break; 1550 } 1551 case REPORT_MEM_USAGE_MSG: { 1552 final ArrayList<ProcessMemInfo> memInfos = (ArrayList<ProcessMemInfo>)msg.obj; 1553 Thread thread = new Thread() { 1554 @Override public void run() { 1555 final SparseArray<ProcessMemInfo> infoMap 1556 = new SparseArray<ProcessMemInfo>(memInfos.size()); 1557 for (int i=0, N=memInfos.size(); i<N; i++) { 1558 ProcessMemInfo mi = memInfos.get(i); 1559 infoMap.put(mi.pid, mi); 1560 } 1561 updateCpuStatsNow(); 1562 synchronized (mProcessCpuThread) { 1563 final int N = mProcessCpuTracker.countStats(); 1564 for (int i=0; i<N; i++) { 1565 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 1566 if (st.vsize > 0) { 1567 long pss = Debug.getPss(st.pid, null); 1568 if (pss > 0) { 1569 if (infoMap.indexOfKey(st.pid) < 0) { 1570 ProcessMemInfo mi = new ProcessMemInfo(st.name, st.pid, 1571 ProcessList.NATIVE_ADJ, -1, "native", null); 1572 mi.pss = pss; 1573 memInfos.add(mi); 1574 } 1575 } 1576 } 1577 } 1578 } 1579 1580 long totalPss = 0; 1581 for (int i=0, N=memInfos.size(); i<N; i++) { 1582 ProcessMemInfo mi = memInfos.get(i); 1583 if (mi.pss == 0) { 1584 mi.pss = Debug.getPss(mi.pid, null); 1585 } 1586 totalPss += mi.pss; 1587 } 1588 Collections.sort(memInfos, new Comparator<ProcessMemInfo>() { 1589 @Override public int compare(ProcessMemInfo lhs, ProcessMemInfo rhs) { 1590 if (lhs.oomAdj != rhs.oomAdj) { 1591 return lhs.oomAdj < rhs.oomAdj ? -1 : 1; 1592 } 1593 if (lhs.pss != rhs.pss) { 1594 return lhs.pss < rhs.pss ? 1 : -1; 1595 } 1596 return 0; 1597 } 1598 }); 1599 1600 StringBuilder tag = new StringBuilder(128); 1601 StringBuilder stack = new StringBuilder(128); 1602 tag.append("Low on memory -- "); 1603 appendMemBucket(tag, totalPss, "total", false); 1604 appendMemBucket(stack, totalPss, "total", true); 1605 1606 StringBuilder logBuilder = new StringBuilder(1024); 1607 logBuilder.append("Low on memory:\n"); 1608 1609 boolean firstLine = true; 1610 int lastOomAdj = Integer.MIN_VALUE; 1611 for (int i=0, N=memInfos.size(); i<N; i++) { 1612 ProcessMemInfo mi = memInfos.get(i); 1613 1614 if (mi.oomAdj != ProcessList.NATIVE_ADJ 1615 && (mi.oomAdj < ProcessList.SERVICE_ADJ 1616 || mi.oomAdj == ProcessList.HOME_APP_ADJ 1617 || mi.oomAdj == ProcessList.PREVIOUS_APP_ADJ)) { 1618 if (lastOomAdj != mi.oomAdj) { 1619 lastOomAdj = mi.oomAdj; 1620 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1621 tag.append(" / "); 1622 } 1623 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ) { 1624 if (firstLine) { 1625 stack.append(":"); 1626 firstLine = false; 1627 } 1628 stack.append("\n\t at "); 1629 } else { 1630 stack.append("$"); 1631 } 1632 } else { 1633 tag.append(" "); 1634 stack.append("$"); 1635 } 1636 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1637 appendMemBucket(tag, mi.pss, mi.name, false); 1638 } 1639 appendMemBucket(stack, mi.pss, mi.name, true); 1640 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ 1641 && ((i+1) >= N || memInfos.get(i+1).oomAdj != lastOomAdj)) { 1642 stack.append("("); 1643 for (int k=0; k<DUMP_MEM_OOM_ADJ.length; k++) { 1644 if (DUMP_MEM_OOM_ADJ[k] == mi.oomAdj) { 1645 stack.append(DUMP_MEM_OOM_LABEL[k]); 1646 stack.append(":"); 1647 stack.append(DUMP_MEM_OOM_ADJ[k]); 1648 } 1649 } 1650 stack.append(")"); 1651 } 1652 } 1653 1654 logBuilder.append(" "); 1655 logBuilder.append(ProcessList.makeOomAdjString(mi.oomAdj)); 1656 logBuilder.append(' '); 1657 logBuilder.append(ProcessList.makeProcStateString(mi.procState)); 1658 logBuilder.append(' '); 1659 ProcessList.appendRamKb(logBuilder, mi.pss); 1660 logBuilder.append(" kB: "); 1661 logBuilder.append(mi.name); 1662 logBuilder.append(" ("); 1663 logBuilder.append(mi.pid); 1664 logBuilder.append(") "); 1665 logBuilder.append(mi.adjType); 1666 logBuilder.append('\n'); 1667 if (mi.adjReason != null) { 1668 logBuilder.append(" "); 1669 logBuilder.append(mi.adjReason); 1670 logBuilder.append('\n'); 1671 } 1672 } 1673 1674 logBuilder.append(" "); 1675 ProcessList.appendRamKb(logBuilder, totalPss); 1676 logBuilder.append(" kB: TOTAL\n"); 1677 1678 long[] infos = new long[Debug.MEMINFO_COUNT]; 1679 Debug.getMemInfo(infos); 1680 logBuilder.append(" MemInfo: "); 1681 logBuilder.append(infos[Debug.MEMINFO_SLAB]).append(" kB slab, "); 1682 logBuilder.append(infos[Debug.MEMINFO_SHMEM]).append(" kB shmem, "); 1683 logBuilder.append(infos[Debug.MEMINFO_BUFFERS]).append(" kB buffers, "); 1684 logBuilder.append(infos[Debug.MEMINFO_CACHED]).append(" kB cached, "); 1685 logBuilder.append(infos[Debug.MEMINFO_FREE]).append(" kB free\n"); 1686 if (infos[Debug.MEMINFO_ZRAM_TOTAL] != 0) { 1687 logBuilder.append(" ZRAM: "); 1688 logBuilder.append(infos[Debug.MEMINFO_ZRAM_TOTAL]); 1689 logBuilder.append(" kB RAM, "); 1690 logBuilder.append(infos[Debug.MEMINFO_SWAP_TOTAL]); 1691 logBuilder.append(" kB swap total, "); 1692 logBuilder.append(infos[Debug.MEMINFO_SWAP_FREE]); 1693 logBuilder.append(" kB swap free\n"); 1694 } 1695 Slog.i(TAG, logBuilder.toString()); 1696 1697 StringBuilder dropBuilder = new StringBuilder(1024); 1698 /* 1699 StringWriter oomSw = new StringWriter(); 1700 PrintWriter oomPw = new FastPrintWriter(oomSw, false, 256); 1701 StringWriter catSw = new StringWriter(); 1702 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1703 String[] emptyArgs = new String[] { }; 1704 dumpApplicationMemoryUsage(null, oomPw, " ", emptyArgs, true, catPw); 1705 oomPw.flush(); 1706 String oomString = oomSw.toString(); 1707 */ 1708 dropBuilder.append(stack); 1709 dropBuilder.append('\n'); 1710 dropBuilder.append('\n'); 1711 dropBuilder.append(logBuilder); 1712 dropBuilder.append('\n'); 1713 /* 1714 dropBuilder.append(oomString); 1715 dropBuilder.append('\n'); 1716 */ 1717 StringWriter catSw = new StringWriter(); 1718 synchronized (ActivityManagerService.this) { 1719 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1720 String[] emptyArgs = new String[] { }; 1721 catPw.println(); 1722 dumpProcessesLocked(null, catPw, emptyArgs, 0, false, null); 1723 catPw.println(); 1724 mServices.dumpServicesLocked(null, catPw, emptyArgs, 0, 1725 false, false, null); 1726 catPw.println(); 1727 dumpActivitiesLocked(null, catPw, emptyArgs, 0, false, false, null); 1728 catPw.flush(); 1729 } 1730 dropBuilder.append(catSw.toString()); 1731 addErrorToDropBox("lowmem", null, "system_server", null, 1732 null, tag.toString(), dropBuilder.toString(), null, null); 1733 //Slog.i(TAG, "Sent to dropbox:"); 1734 //Slog.i(TAG, dropBuilder.toString()); 1735 synchronized (ActivityManagerService.this) { 1736 long now = SystemClock.uptimeMillis(); 1737 if (mLastMemUsageReportTime < now) { 1738 mLastMemUsageReportTime = now; 1739 } 1740 } 1741 } 1742 }; 1743 thread.start(); 1744 break; 1745 } 1746 case REPORT_USER_SWITCH_MSG: { 1747 dispatchUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1748 break; 1749 } 1750 case CONTINUE_USER_SWITCH_MSG: { 1751 continueUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1752 break; 1753 } 1754 case USER_SWITCH_TIMEOUT_MSG: { 1755 timeoutUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1756 break; 1757 } 1758 case IMMERSIVE_MODE_LOCK_MSG: { 1759 final boolean nextState = (msg.arg1 != 0); 1760 if (mUpdateLock.isHeld() != nextState) { 1761 if (DEBUG_IMMERSIVE) { 1762 final ActivityRecord r = (ActivityRecord) msg.obj; 1763 Slog.d(TAG, "Applying new update lock state '" + nextState + "' for " + r); 1764 } 1765 if (nextState) { 1766 mUpdateLock.acquire(); 1767 } else { 1768 mUpdateLock.release(); 1769 } 1770 } 1771 break; 1772 } 1773 case PERSIST_URI_GRANTS_MSG: { 1774 writeGrantedUriPermissions(); 1775 break; 1776 } 1777 case REQUEST_ALL_PSS_MSG: { 1778 requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, false); 1779 break; 1780 } 1781 case START_PROFILES_MSG: { 1782 synchronized (ActivityManagerService.this) { 1783 startProfilesLocked(); 1784 } 1785 break; 1786 } 1787 case UPDATE_TIME: { 1788 synchronized (ActivityManagerService.this) { 1789 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1790 ProcessRecord r = mLruProcesses.get(i); 1791 if (r.thread != null) { 1792 try { 1793 r.thread.updateTimePrefs(msg.arg1 == 0 ? false : true); 1794 } catch (RemoteException ex) { 1795 Slog.w(TAG, "Failed to update preferences for: " + r.info.processName); 1796 } 1797 } 1798 } 1799 } 1800 break; 1801 } 1802 case SYSTEM_USER_START_MSG: { 1803 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 1804 Integer.toString(msg.arg1), msg.arg1); 1805 mSystemServiceManager.startUser(msg.arg1); 1806 break; 1807 } 1808 case SYSTEM_USER_CURRENT_MSG: { 1809 mBatteryStatsService.noteEvent( 1810 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_FINISH, 1811 Integer.toString(msg.arg2), msg.arg2); 1812 mBatteryStatsService.noteEvent( 1813 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 1814 Integer.toString(msg.arg1), msg.arg1); 1815 mSystemServiceManager.switchUser(msg.arg1); 1816 break; 1817 } 1818 case ENTER_ANIMATION_COMPLETE_MSG: { 1819 synchronized (ActivityManagerService.this) { 1820 ActivityRecord r = ActivityRecord.forToken((IBinder) msg.obj); 1821 if (r != null && r.app != null && r.app.thread != null) { 1822 try { 1823 r.app.thread.scheduleEnterAnimationComplete(r.appToken); 1824 } catch (RemoteException e) { 1825 } 1826 } 1827 } 1828 break; 1829 } 1830 case ENABLE_SCREEN_AFTER_BOOT_MSG: { 1831 enableScreenAfterBoot(); 1832 break; 1833 } 1834 } 1835 } 1836 }; 1837 1838 static final int COLLECT_PSS_BG_MSG = 1; 1839 1840 final Handler mBgHandler = new Handler(BackgroundThread.getHandler().getLooper()) { 1841 @Override 1842 public void handleMessage(Message msg) { 1843 switch (msg.what) { 1844 case COLLECT_PSS_BG_MSG: { 1845 long start = SystemClock.uptimeMillis(); 1846 MemInfoReader memInfo = null; 1847 synchronized (ActivityManagerService.this) { 1848 if (mFullPssPending) { 1849 mFullPssPending = false; 1850 memInfo = new MemInfoReader(); 1851 } 1852 } 1853 if (memInfo != null) { 1854 updateCpuStatsNow(); 1855 long nativeTotalPss = 0; 1856 synchronized (mProcessCpuThread) { 1857 final int N = mProcessCpuTracker.countStats(); 1858 for (int j=0; j<N; j++) { 1859 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(j); 1860 if (st.vsize <= 0 || st.uid >= Process.FIRST_APPLICATION_UID) { 1861 // This is definitely an application process; skip it. 1862 continue; 1863 } 1864 synchronized (mPidsSelfLocked) { 1865 if (mPidsSelfLocked.indexOfKey(st.pid) >= 0) { 1866 // This is one of our own processes; skip it. 1867 continue; 1868 } 1869 } 1870 nativeTotalPss += Debug.getPss(st.pid, null); 1871 } 1872 } 1873 memInfo.readMemInfo(); 1874 synchronized (this) { 1875 if (DEBUG_PSS) Slog.d(TAG, "Collected native and kernel memory in " 1876 + (SystemClock.uptimeMillis()-start) + "ms"); 1877 mProcessStats.addSysMemUsageLocked(memInfo.getCachedSizeKb(), 1878 memInfo.getFreeSizeKb(), memInfo.getZramTotalSizeKb(), 1879 memInfo.getBuffersSizeKb()+memInfo.getShmemSizeKb() 1880 +memInfo.getSlabSizeKb(), 1881 nativeTotalPss); 1882 } 1883 } 1884 1885 int i=0, num=0; 1886 long[] tmp = new long[1]; 1887 do { 1888 ProcessRecord proc; 1889 int procState; 1890 int pid; 1891 synchronized (ActivityManagerService.this) { 1892 if (i >= mPendingPssProcesses.size()) { 1893 if (DEBUG_PSS) Slog.d(TAG, "Collected PSS of " + num + " of " + i 1894 + " processes in " + (SystemClock.uptimeMillis()-start) + "ms"); 1895 mPendingPssProcesses.clear(); 1896 return; 1897 } 1898 proc = mPendingPssProcesses.get(i); 1899 procState = proc.pssProcState; 1900 if (proc.thread != null && procState == proc.setProcState) { 1901 pid = proc.pid; 1902 } else { 1903 proc = null; 1904 pid = 0; 1905 } 1906 i++; 1907 } 1908 if (proc != null) { 1909 long pss = Debug.getPss(pid, tmp); 1910 synchronized (ActivityManagerService.this) { 1911 if (proc.thread != null && proc.setProcState == procState 1912 && proc.pid == pid) { 1913 num++; 1914 proc.lastPssTime = SystemClock.uptimeMillis(); 1915 proc.baseProcessTracker.addPss(pss, tmp[0], true, proc.pkgList); 1916 if (DEBUG_PSS) Slog.d(TAG, "PSS of " + proc.toShortString() 1917 + ": " + pss + " lastPss=" + proc.lastPss 1918 + " state=" + ProcessList.makeProcStateString(procState)); 1919 if (proc.initialIdlePss == 0) { 1920 proc.initialIdlePss = pss; 1921 } 1922 proc.lastPss = pss; 1923 if (procState >= ActivityManager.PROCESS_STATE_HOME) { 1924 proc.lastCachedPss = pss; 1925 } 1926 } 1927 } 1928 } 1929 } while (true); 1930 } 1931 } 1932 } 1933 }; 1934 1935 /** 1936 * Monitor for package changes and update our internal state. 1937 */ 1938 private final PackageMonitor mPackageMonitor = new PackageMonitor() { 1939 @Override 1940 public void onPackageRemoved(String packageName, int uid) { 1941 // Remove all tasks with activities in the specified package from the list of recent tasks 1942 synchronized (ActivityManagerService.this) { 1943 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 1944 TaskRecord tr = mRecentTasks.get(i); 1945 ComponentName cn = tr.intent.getComponent(); 1946 if (cn != null && cn.getPackageName().equals(packageName)) { 1947 // If the package name matches, remove the task and kill the process 1948 removeTaskByIdLocked(tr.taskId, ActivityManager.REMOVE_TASK_KILL_PROCESS); 1949 } 1950 } 1951 } 1952 } 1953 1954 @Override 1955 public boolean onPackageChanged(String packageName, int uid, String[] components) { 1956 onPackageModified(packageName); 1957 return true; 1958 } 1959 1960 @Override 1961 public void onPackageModified(String packageName) { 1962 final PackageManager pm = mContext.getPackageManager(); 1963 final ArrayList<Pair<Intent, Integer>> recentTaskIntents = 1964 new ArrayList<Pair<Intent, Integer>>(); 1965 final ArrayList<Integer> tasksToRemove = new ArrayList<Integer>(); 1966 // Copy the list of recent tasks so that we don't hold onto the lock on 1967 // ActivityManagerService for long periods while checking if components exist. 1968 synchronized (ActivityManagerService.this) { 1969 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 1970 TaskRecord tr = mRecentTasks.get(i); 1971 recentTaskIntents.add(new Pair<Intent, Integer>(tr.intent, tr.taskId)); 1972 } 1973 } 1974 // Check the recent tasks and filter out all tasks with components that no longer exist. 1975 Intent tmpI = new Intent(); 1976 for (int i = recentTaskIntents.size() - 1; i >= 0; i--) { 1977 Pair<Intent, Integer> p = recentTaskIntents.get(i); 1978 ComponentName cn = p.first.getComponent(); 1979 if (cn != null && cn.getPackageName().equals(packageName)) { 1980 try { 1981 // Add the task to the list to remove if the component no longer exists 1982 tmpI.setComponent(cn); 1983 if (pm.queryIntentActivities(tmpI, PackageManager.MATCH_DEFAULT_ONLY).isEmpty()) { 1984 tasksToRemove.add(p.second); 1985 } 1986 } catch (Exception e) {} 1987 } 1988 } 1989 // Prune all the tasks with removed components from the list of recent tasks 1990 synchronized (ActivityManagerService.this) { 1991 for (int i = tasksToRemove.size() - 1; i >= 0; i--) { 1992 // Remove the task but don't kill the process (since other components in that 1993 // package may still be running and in the background) 1994 removeTaskByIdLocked(tasksToRemove.get(i), 0); 1995 } 1996 } 1997 } 1998 1999 @Override 2000 public boolean onHandleForceStop(Intent intent, String[] packages, int uid, boolean doit) { 2001 // Force stop the specified packages 2002 if (packages != null) { 2003 for (String pkg : packages) { 2004 synchronized (ActivityManagerService.this) { 2005 if (forceStopPackageLocked(pkg, -1, false, false, false, false, false, 0, 2006 "finished booting")) { 2007 return true; 2008 } 2009 } 2010 } 2011 } 2012 return false; 2013 } 2014 }; 2015 2016 public void setSystemProcess() { 2017 try { 2018 ServiceManager.addService(Context.ACTIVITY_SERVICE, this, true); 2019 ServiceManager.addService(ProcessStats.SERVICE_NAME, mProcessStats); 2020 ServiceManager.addService("meminfo", new MemBinder(this)); 2021 ServiceManager.addService("gfxinfo", new GraphicsBinder(this)); 2022 ServiceManager.addService("dbinfo", new DbBinder(this)); 2023 if (MONITOR_CPU_USAGE) { 2024 ServiceManager.addService("cpuinfo", new CpuBinder(this)); 2025 } 2026 ServiceManager.addService("permission", new PermissionController(this)); 2027 2028 ApplicationInfo info = mContext.getPackageManager().getApplicationInfo( 2029 "android", STOCK_PM_FLAGS); 2030 mSystemThread.installSystemApplicationInfo(info); 2031 2032 synchronized (this) { 2033 ProcessRecord app = newProcessRecordLocked(info, info.processName, false); 2034 app.persistent = true; 2035 app.pid = MY_PID; 2036 app.maxAdj = ProcessList.SYSTEM_ADJ; 2037 app.makeActive(mSystemThread.getApplicationThread(), mProcessStats); 2038 mProcessNames.put(app.processName, app.uid, app); 2039 synchronized (mPidsSelfLocked) { 2040 mPidsSelfLocked.put(app.pid, app); 2041 } 2042 updateLruProcessLocked(app, false, null); 2043 updateOomAdjLocked(); 2044 } 2045 } catch (PackageManager.NameNotFoundException e) { 2046 throw new RuntimeException( 2047 "Unable to find android system package", e); 2048 } 2049 } 2050 2051 public void setWindowManager(WindowManagerService wm) { 2052 mWindowManager = wm; 2053 mStackSupervisor.setWindowManager(wm); 2054 } 2055 2056 public void setUsageStatsManager(UsageStatsManagerInternal usageStatsManager) { 2057 mUsageStatsService = usageStatsManager; 2058 } 2059 2060 public void startObservingNativeCrashes() { 2061 final NativeCrashListener ncl = new NativeCrashListener(this); 2062 ncl.start(); 2063 } 2064 2065 public IAppOpsService getAppOpsService() { 2066 return mAppOpsService; 2067 } 2068 2069 static class MemBinder extends Binder { 2070 ActivityManagerService mActivityManagerService; 2071 MemBinder(ActivityManagerService activityManagerService) { 2072 mActivityManagerService = activityManagerService; 2073 } 2074 2075 @Override 2076 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2077 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2078 != PackageManager.PERMISSION_GRANTED) { 2079 pw.println("Permission Denial: can't dump meminfo from from pid=" 2080 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2081 + " without permission " + android.Manifest.permission.DUMP); 2082 return; 2083 } 2084 2085 mActivityManagerService.dumpApplicationMemoryUsage(fd, pw, " ", args, false, null); 2086 } 2087 } 2088 2089 static class GraphicsBinder extends Binder { 2090 ActivityManagerService mActivityManagerService; 2091 GraphicsBinder(ActivityManagerService activityManagerService) { 2092 mActivityManagerService = activityManagerService; 2093 } 2094 2095 @Override 2096 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2097 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2098 != PackageManager.PERMISSION_GRANTED) { 2099 pw.println("Permission Denial: can't dump gfxinfo from from pid=" 2100 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2101 + " without permission " + android.Manifest.permission.DUMP); 2102 return; 2103 } 2104 2105 mActivityManagerService.dumpGraphicsHardwareUsage(fd, pw, args); 2106 } 2107 } 2108 2109 static class DbBinder extends Binder { 2110 ActivityManagerService mActivityManagerService; 2111 DbBinder(ActivityManagerService activityManagerService) { 2112 mActivityManagerService = activityManagerService; 2113 } 2114 2115 @Override 2116 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2117 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2118 != PackageManager.PERMISSION_GRANTED) { 2119 pw.println("Permission Denial: can't dump dbinfo from from pid=" 2120 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2121 + " without permission " + android.Manifest.permission.DUMP); 2122 return; 2123 } 2124 2125 mActivityManagerService.dumpDbInfo(fd, pw, args); 2126 } 2127 } 2128 2129 static class CpuBinder extends Binder { 2130 ActivityManagerService mActivityManagerService; 2131 CpuBinder(ActivityManagerService activityManagerService) { 2132 mActivityManagerService = activityManagerService; 2133 } 2134 2135 @Override 2136 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2137 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2138 != PackageManager.PERMISSION_GRANTED) { 2139 pw.println("Permission Denial: can't dump cpuinfo from from pid=" 2140 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2141 + " without permission " + android.Manifest.permission.DUMP); 2142 return; 2143 } 2144 2145 synchronized (mActivityManagerService.mProcessCpuThread) { 2146 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentLoad()); 2147 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentState( 2148 SystemClock.uptimeMillis())); 2149 } 2150 } 2151 } 2152 2153 public static final class Lifecycle extends SystemService { 2154 private final ActivityManagerService mService; 2155 2156 public Lifecycle(Context context) { 2157 super(context); 2158 mService = new ActivityManagerService(context); 2159 } 2160 2161 @Override 2162 public void onStart() { 2163 mService.start(); 2164 } 2165 2166 public ActivityManagerService getService() { 2167 return mService; 2168 } 2169 } 2170 2171 // Note: This method is invoked on the main thread but may need to attach various 2172 // handlers to other threads. So take care to be explicit about the looper. 2173 public ActivityManagerService(Context systemContext) { 2174 mContext = systemContext; 2175 mFactoryTest = FactoryTest.getMode(); 2176 mSystemThread = ActivityThread.currentActivityThread(); 2177 2178 Slog.i(TAG, "Memory class: " + ActivityManager.staticGetMemoryClass()); 2179 2180 mHandlerThread = new ServiceThread(TAG, 2181 android.os.Process.THREAD_PRIORITY_FOREGROUND, false /*allowIo*/); 2182 mHandlerThread.start(); 2183 mHandler = new MainHandler(mHandlerThread.getLooper()); 2184 2185 mFgBroadcastQueue = new BroadcastQueue(this, mHandler, 2186 "foreground", BROADCAST_FG_TIMEOUT, false); 2187 mBgBroadcastQueue = new BroadcastQueue(this, mHandler, 2188 "background", BROADCAST_BG_TIMEOUT, true); 2189 mBroadcastQueues[0] = mFgBroadcastQueue; 2190 mBroadcastQueues[1] = mBgBroadcastQueue; 2191 2192 mServices = new ActiveServices(this); 2193 mProviderMap = new ProviderMap(this); 2194 2195 // TODO: Move creation of battery stats service outside of activity manager service. 2196 File dataDir = Environment.getDataDirectory(); 2197 File systemDir = new File(dataDir, "system"); 2198 systemDir.mkdirs(); 2199 mBatteryStatsService = new BatteryStatsService(new File( 2200 systemDir, "batterystats.bin").toString(), mHandler); 2201 mBatteryStatsService.getActiveStatistics().readLocked(); 2202 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2203 mOnBattery = DEBUG_POWER ? true 2204 : mBatteryStatsService.getActiveStatistics().getIsOnBattery(); 2205 mBatteryStatsService.getActiveStatistics().setCallback(this); 2206 2207 mProcessStats = new ProcessStatsService(this, new File(systemDir, "procstats")); 2208 2209 mAppOpsService = new AppOpsService(new File(systemDir, "appops.xml"), mHandler); 2210 2211 mGrantFile = new AtomicFile(new File(systemDir, "urigrants.xml")); 2212 2213 // User 0 is the first and only user that runs at boot. 2214 mStartedUsers.put(0, new UserStartedState(new UserHandle(0), true)); 2215 mUserLru.add(Integer.valueOf(0)); 2216 updateStartedUserArrayLocked(); 2217 2218 GL_ES_VERSION = SystemProperties.getInt("ro.opengles.version", 2219 ConfigurationInfo.GL_ES_VERSION_UNDEFINED); 2220 2221 mConfiguration.setToDefaults(); 2222 mConfiguration.setLocale(Locale.getDefault()); 2223 2224 mConfigurationSeq = mConfiguration.seq = 1; 2225 mProcessCpuTracker.init(); 2226 2227 mHasRecents = mContext.getResources().getBoolean( 2228 com.android.internal.R.bool.config_hasRecents); 2229 2230 mCompatModePackages = new CompatModePackages(this, systemDir, mHandler); 2231 mIntentFirewall = new IntentFirewall(new IntentFirewallInterface(), mHandler); 2232 mStackSupervisor = new ActivityStackSupervisor(this); 2233 mTaskPersister = new TaskPersister(systemDir, mStackSupervisor); 2234 2235 mProcessCpuThread = new Thread("CpuTracker") { 2236 @Override 2237 public void run() { 2238 while (true) { 2239 try { 2240 try { 2241 synchronized(this) { 2242 final long now = SystemClock.uptimeMillis(); 2243 long nextCpuDelay = (mLastCpuTime.get()+MONITOR_CPU_MAX_TIME)-now; 2244 long nextWriteDelay = (mLastWriteTime+BATTERY_STATS_TIME)-now; 2245 //Slog.i(TAG, "Cpu delay=" + nextCpuDelay 2246 // + ", write delay=" + nextWriteDelay); 2247 if (nextWriteDelay < nextCpuDelay) { 2248 nextCpuDelay = nextWriteDelay; 2249 } 2250 if (nextCpuDelay > 0) { 2251 mProcessCpuMutexFree.set(true); 2252 this.wait(nextCpuDelay); 2253 } 2254 } 2255 } catch (InterruptedException e) { 2256 } 2257 updateCpuStatsNow(); 2258 } catch (Exception e) { 2259 Slog.e(TAG, "Unexpected exception collecting process stats", e); 2260 } 2261 } 2262 } 2263 }; 2264 2265 mLockToAppRequest = new LockToAppRequestDialog(mContext, this); 2266 2267 Watchdog.getInstance().addMonitor(this); 2268 Watchdog.getInstance().addThread(mHandler); 2269 } 2270 2271 public void setSystemServiceManager(SystemServiceManager mgr) { 2272 mSystemServiceManager = mgr; 2273 } 2274 2275 private void start() { 2276 Process.removeAllProcessGroups(); 2277 mProcessCpuThread.start(); 2278 2279 mBatteryStatsService.publish(mContext); 2280 mAppOpsService.publish(mContext); 2281 Slog.d("AppOps", "AppOpsService published"); 2282 LocalServices.addService(ActivityManagerInternal.class, new LocalService()); 2283 } 2284 2285 public void initPowerManagement() { 2286 mStackSupervisor.initPowerManagement(); 2287 mBatteryStatsService.initPowerManagement(); 2288 } 2289 2290 @Override 2291 public boolean onTransact(int code, Parcel data, Parcel reply, int flags) 2292 throws RemoteException { 2293 if (code == SYSPROPS_TRANSACTION) { 2294 // We need to tell all apps about the system property change. 2295 ArrayList<IBinder> procs = new ArrayList<IBinder>(); 2296 synchronized(this) { 2297 final int NP = mProcessNames.getMap().size(); 2298 for (int ip=0; ip<NP; ip++) { 2299 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 2300 final int NA = apps.size(); 2301 for (int ia=0; ia<NA; ia++) { 2302 ProcessRecord app = apps.valueAt(ia); 2303 if (app.thread != null) { 2304 procs.add(app.thread.asBinder()); 2305 } 2306 } 2307 } 2308 } 2309 2310 int N = procs.size(); 2311 for (int i=0; i<N; i++) { 2312 Parcel data2 = Parcel.obtain(); 2313 try { 2314 procs.get(i).transact(IBinder.SYSPROPS_TRANSACTION, data2, null, 0); 2315 } catch (RemoteException e) { 2316 } 2317 data2.recycle(); 2318 } 2319 } 2320 try { 2321 return super.onTransact(code, data, reply, flags); 2322 } catch (RuntimeException e) { 2323 // The activity manager only throws security exceptions, so let's 2324 // log all others. 2325 if (!(e instanceof SecurityException)) { 2326 Slog.wtf(TAG, "Activity Manager Crash", e); 2327 } 2328 throw e; 2329 } 2330 } 2331 2332 void updateCpuStats() { 2333 final long now = SystemClock.uptimeMillis(); 2334 if (mLastCpuTime.get() >= now - MONITOR_CPU_MIN_TIME) { 2335 return; 2336 } 2337 if (mProcessCpuMutexFree.compareAndSet(true, false)) { 2338 synchronized (mProcessCpuThread) { 2339 mProcessCpuThread.notify(); 2340 } 2341 } 2342 } 2343 2344 void updateCpuStatsNow() { 2345 synchronized (mProcessCpuThread) { 2346 mProcessCpuMutexFree.set(false); 2347 final long now = SystemClock.uptimeMillis(); 2348 boolean haveNewCpuStats = false; 2349 2350 if (MONITOR_CPU_USAGE && 2351 mLastCpuTime.get() < (now-MONITOR_CPU_MIN_TIME)) { 2352 mLastCpuTime.set(now); 2353 haveNewCpuStats = true; 2354 mProcessCpuTracker.update(); 2355 //Slog.i(TAG, mProcessCpu.printCurrentState()); 2356 //Slog.i(TAG, "Total CPU usage: " 2357 // + mProcessCpu.getTotalCpuPercent() + "%"); 2358 2359 // Slog the cpu usage if the property is set. 2360 if ("true".equals(SystemProperties.get("events.cpu"))) { 2361 int user = mProcessCpuTracker.getLastUserTime(); 2362 int system = mProcessCpuTracker.getLastSystemTime(); 2363 int iowait = mProcessCpuTracker.getLastIoWaitTime(); 2364 int irq = mProcessCpuTracker.getLastIrqTime(); 2365 int softIrq = mProcessCpuTracker.getLastSoftIrqTime(); 2366 int idle = mProcessCpuTracker.getLastIdleTime(); 2367 2368 int total = user + system + iowait + irq + softIrq + idle; 2369 if (total == 0) total = 1; 2370 2371 EventLog.writeEvent(EventLogTags.CPU, 2372 ((user+system+iowait+irq+softIrq) * 100) / total, 2373 (user * 100) / total, 2374 (system * 100) / total, 2375 (iowait * 100) / total, 2376 (irq * 100) / total, 2377 (softIrq * 100) / total); 2378 } 2379 } 2380 2381 long[] cpuSpeedTimes = mProcessCpuTracker.getLastCpuSpeedTimes(); 2382 final BatteryStatsImpl bstats = mBatteryStatsService.getActiveStatistics(); 2383 synchronized(bstats) { 2384 synchronized(mPidsSelfLocked) { 2385 if (haveNewCpuStats) { 2386 if (mOnBattery) { 2387 int perc = bstats.startAddingCpuLocked(); 2388 int totalUTime = 0; 2389 int totalSTime = 0; 2390 final int N = mProcessCpuTracker.countStats(); 2391 for (int i=0; i<N; i++) { 2392 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 2393 if (!st.working) { 2394 continue; 2395 } 2396 ProcessRecord pr = mPidsSelfLocked.get(st.pid); 2397 int otherUTime = (st.rel_utime*perc)/100; 2398 int otherSTime = (st.rel_stime*perc)/100; 2399 totalUTime += otherUTime; 2400 totalSTime += otherSTime; 2401 if (pr != null) { 2402 BatteryStatsImpl.Uid.Proc ps = pr.curProcBatteryStats; 2403 if (ps == null || !ps.isActive()) { 2404 pr.curProcBatteryStats = ps = bstats.getProcessStatsLocked( 2405 pr.info.uid, pr.processName); 2406 } 2407 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2408 st.rel_stime-otherSTime); 2409 ps.addSpeedStepTimes(cpuSpeedTimes); 2410 pr.curCpuTime += (st.rel_utime+st.rel_stime) * 10; 2411 } else { 2412 BatteryStatsImpl.Uid.Proc ps = st.batteryStats; 2413 if (ps == null || !ps.isActive()) { 2414 st.batteryStats = ps = bstats.getProcessStatsLocked( 2415 bstats.mapUid(st.uid), st.name); 2416 } 2417 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2418 st.rel_stime-otherSTime); 2419 ps.addSpeedStepTimes(cpuSpeedTimes); 2420 } 2421 } 2422 bstats.finishAddingCpuLocked(perc, totalUTime, 2423 totalSTime, cpuSpeedTimes); 2424 } 2425 } 2426 } 2427 2428 if (mLastWriteTime < (now-BATTERY_STATS_TIME)) { 2429 mLastWriteTime = now; 2430 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2431 } 2432 } 2433 } 2434 } 2435 2436 @Override 2437 public void batteryNeedsCpuUpdate() { 2438 updateCpuStatsNow(); 2439 } 2440 2441 @Override 2442 public void batteryPowerChanged(boolean onBattery) { 2443 // When plugging in, update the CPU stats first before changing 2444 // the plug state. 2445 updateCpuStatsNow(); 2446 synchronized (this) { 2447 synchronized(mPidsSelfLocked) { 2448 mOnBattery = DEBUG_POWER ? true : onBattery; 2449 } 2450 } 2451 } 2452 2453 /** 2454 * Initialize the application bind args. These are passed to each 2455 * process when the bindApplication() IPC is sent to the process. They're 2456 * lazily setup to make sure the services are running when they're asked for. 2457 */ 2458 private HashMap<String, IBinder> getCommonServicesLocked() { 2459 if (mAppBindArgs == null) { 2460 mAppBindArgs = new HashMap<String, IBinder>(); 2461 2462 // Setup the application init args 2463 mAppBindArgs.put("package", ServiceManager.getService("package")); 2464 mAppBindArgs.put("window", ServiceManager.getService("window")); 2465 mAppBindArgs.put(Context.ALARM_SERVICE, 2466 ServiceManager.getService(Context.ALARM_SERVICE)); 2467 } 2468 return mAppBindArgs; 2469 } 2470 2471 final void setFocusedActivityLocked(ActivityRecord r) { 2472 if (mFocusedActivity != r) { 2473 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedActivityLocked: r=" + r); 2474 mFocusedActivity = r; 2475 if (r.task != null && r.task.voiceInteractor != null) { 2476 startRunningVoiceLocked(); 2477 } else { 2478 finishRunningVoiceLocked(); 2479 } 2480 mStackSupervisor.setFocusedStack(r); 2481 if (r != null) { 2482 mWindowManager.setFocusedApp(r.appToken, true); 2483 } 2484 applyUpdateLockStateLocked(r); 2485 } 2486 } 2487 2488 final void clearFocusedActivity(ActivityRecord r) { 2489 if (mFocusedActivity == r) { 2490 mFocusedActivity = null; 2491 } 2492 } 2493 2494 @Override 2495 public void setFocusedStack(int stackId) { 2496 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedStack: stackId=" + stackId); 2497 synchronized (ActivityManagerService.this) { 2498 ActivityStack stack = mStackSupervisor.getStack(stackId); 2499 if (stack != null) { 2500 ActivityRecord r = stack.topRunningActivityLocked(null); 2501 if (r != null) { 2502 setFocusedActivityLocked(r); 2503 } 2504 } 2505 } 2506 } 2507 2508 @Override 2509 public void notifyActivityDrawn(IBinder token) { 2510 if (DEBUG_VISBILITY) Slog.d(TAG, "notifyActivityDrawn: token=" + token); 2511 synchronized (this) { 2512 ActivityRecord r= mStackSupervisor.isInAnyStackLocked(token); 2513 if (r != null) { 2514 r.task.stack.notifyActivityDrawnLocked(r); 2515 } 2516 } 2517 } 2518 2519 final void applyUpdateLockStateLocked(ActivityRecord r) { 2520 // Modifications to the UpdateLock state are done on our handler, outside 2521 // the activity manager's locks. The new state is determined based on the 2522 // state *now* of the relevant activity record. The object is passed to 2523 // the handler solely for logging detail, not to be consulted/modified. 2524 final boolean nextState = r != null && r.immersive; 2525 mHandler.sendMessage( 2526 mHandler.obtainMessage(IMMERSIVE_MODE_LOCK_MSG, (nextState) ? 1 : 0, 0, r)); 2527 } 2528 2529 final void showAskCompatModeDialogLocked(ActivityRecord r) { 2530 Message msg = Message.obtain(); 2531 msg.what = SHOW_COMPAT_MODE_DIALOG_MSG; 2532 msg.obj = r.task.askedCompatMode ? null : r; 2533 mHandler.sendMessage(msg); 2534 } 2535 2536 private final int updateLruProcessInternalLocked(ProcessRecord app, long now, int index, 2537 String what, Object obj, ProcessRecord srcApp) { 2538 app.lastActivityTime = now; 2539 2540 if (app.activities.size() > 0) { 2541 // Don't want to touch dependent processes that are hosting activities. 2542 return index; 2543 } 2544 2545 int lrui = mLruProcesses.lastIndexOf(app); 2546 if (lrui < 0) { 2547 Slog.wtf(TAG, "Adding dependent process " + app + " not on LRU list: " 2548 + what + " " + obj + " from " + srcApp); 2549 return index; 2550 } 2551 2552 if (lrui >= index) { 2553 // Don't want to cause this to move dependent processes *back* in the 2554 // list as if they were less frequently used. 2555 return index; 2556 } 2557 2558 if (lrui >= mLruProcessActivityStart) { 2559 // Don't want to touch dependent processes that are hosting activities. 2560 return index; 2561 } 2562 2563 mLruProcesses.remove(lrui); 2564 if (index > 0) { 2565 index--; 2566 } 2567 if (DEBUG_LRU) Slog.d(TAG, "Moving dep from " + lrui + " to " + index 2568 + " in LRU list: " + app); 2569 mLruProcesses.add(index, app); 2570 return index; 2571 } 2572 2573 final void removeLruProcessLocked(ProcessRecord app) { 2574 int lrui = mLruProcesses.lastIndexOf(app); 2575 if (lrui >= 0) { 2576 if (lrui <= mLruProcessActivityStart) { 2577 mLruProcessActivityStart--; 2578 } 2579 if (lrui <= mLruProcessServiceStart) { 2580 mLruProcessServiceStart--; 2581 } 2582 mLruProcesses.remove(lrui); 2583 } 2584 } 2585 2586 final void updateLruProcessLocked(ProcessRecord app, boolean activityChange, 2587 ProcessRecord client) { 2588 final boolean hasActivity = app.activities.size() > 0 || app.hasClientActivities 2589 || app.treatLikeActivity; 2590 final boolean hasService = false; // not impl yet. app.services.size() > 0; 2591 if (!activityChange && hasActivity) { 2592 // The process has activities, so we are only allowing activity-based adjustments 2593 // to move it. It should be kept in the front of the list with other 2594 // processes that have activities, and we don't want those to change their 2595 // order except due to activity operations. 2596 return; 2597 } 2598 2599 mLruSeq++; 2600 final long now = SystemClock.uptimeMillis(); 2601 app.lastActivityTime = now; 2602 2603 // First a quick reject: if the app is already at the position we will 2604 // put it, then there is nothing to do. 2605 if (hasActivity) { 2606 final int N = mLruProcesses.size(); 2607 if (N > 0 && mLruProcesses.get(N-1) == app) { 2608 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top activity: " + app); 2609 return; 2610 } 2611 } else { 2612 if (mLruProcessServiceStart > 0 2613 && mLruProcesses.get(mLruProcessServiceStart-1) == app) { 2614 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top other: " + app); 2615 return; 2616 } 2617 } 2618 2619 int lrui = mLruProcesses.lastIndexOf(app); 2620 2621 if (app.persistent && lrui >= 0) { 2622 // We don't care about the position of persistent processes, as long as 2623 // they are in the list. 2624 if (DEBUG_LRU) Slog.d(TAG, "Not moving, persistent: " + app); 2625 return; 2626 } 2627 2628 /* In progress: compute new position first, so we can avoid doing work 2629 if the process is not actually going to move. Not yet working. 2630 int addIndex; 2631 int nextIndex; 2632 boolean inActivity = false, inService = false; 2633 if (hasActivity) { 2634 // Process has activities, put it at the very tipsy-top. 2635 addIndex = mLruProcesses.size(); 2636 nextIndex = mLruProcessServiceStart; 2637 inActivity = true; 2638 } else if (hasService) { 2639 // Process has services, put it at the top of the service list. 2640 addIndex = mLruProcessActivityStart; 2641 nextIndex = mLruProcessServiceStart; 2642 inActivity = true; 2643 inService = true; 2644 } else { 2645 // Process not otherwise of interest, it goes to the top of the non-service area. 2646 addIndex = mLruProcessServiceStart; 2647 if (client != null) { 2648 int clientIndex = mLruProcesses.lastIndexOf(client); 2649 if (clientIndex < 0) Slog.d(TAG, "Unknown client " + client + " when updating " 2650 + app); 2651 if (clientIndex >= 0 && addIndex > clientIndex) { 2652 addIndex = clientIndex; 2653 } 2654 } 2655 nextIndex = addIndex > 0 ? addIndex-1 : addIndex; 2656 } 2657 2658 Slog.d(TAG, "Update LRU at " + lrui + " to " + addIndex + " (act=" 2659 + mLruProcessActivityStart + "): " + app); 2660 */ 2661 2662 if (lrui >= 0) { 2663 if (lrui < mLruProcessActivityStart) { 2664 mLruProcessActivityStart--; 2665 } 2666 if (lrui < mLruProcessServiceStart) { 2667 mLruProcessServiceStart--; 2668 } 2669 /* 2670 if (addIndex > lrui) { 2671 addIndex--; 2672 } 2673 if (nextIndex > lrui) { 2674 nextIndex--; 2675 } 2676 */ 2677 mLruProcesses.remove(lrui); 2678 } 2679 2680 /* 2681 mLruProcesses.add(addIndex, app); 2682 if (inActivity) { 2683 mLruProcessActivityStart++; 2684 } 2685 if (inService) { 2686 mLruProcessActivityStart++; 2687 } 2688 */ 2689 2690 int nextIndex; 2691 if (hasActivity) { 2692 final int N = mLruProcesses.size(); 2693 if (app.activities.size() == 0 && mLruProcessActivityStart < (N-1)) { 2694 // Process doesn't have activities, but has clients with 2695 // activities... move it up, but one below the top (the top 2696 // should always have a real activity). 2697 if (DEBUG_LRU) Slog.d(TAG, "Adding to second-top of LRU activity list: " + app); 2698 mLruProcesses.add(N-1, app); 2699 // To keep it from spamming the LRU list (by making a bunch of clients), 2700 // we will push down any other entries owned by the app. 2701 final int uid = app.info.uid; 2702 for (int i=N-2; i>mLruProcessActivityStart; i--) { 2703 ProcessRecord subProc = mLruProcesses.get(i); 2704 if (subProc.info.uid == uid) { 2705 // We want to push this one down the list. If the process after 2706 // it is for the same uid, however, don't do so, because we don't 2707 // want them internally to be re-ordered. 2708 if (mLruProcesses.get(i-1).info.uid != uid) { 2709 if (DEBUG_LRU) Slog.d(TAG, "Pushing uid " + uid + " swapping at " + i 2710 + ": " + mLruProcesses.get(i) + " : " + mLruProcesses.get(i-1)); 2711 ProcessRecord tmp = mLruProcesses.get(i); 2712 mLruProcesses.set(i, mLruProcesses.get(i-1)); 2713 mLruProcesses.set(i-1, tmp); 2714 i--; 2715 } 2716 } else { 2717 // A gap, we can stop here. 2718 break; 2719 } 2720 } 2721 } else { 2722 // Process has activities, put it at the very tipsy-top. 2723 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU activity list: " + app); 2724 mLruProcesses.add(app); 2725 } 2726 nextIndex = mLruProcessServiceStart; 2727 } else if (hasService) { 2728 // Process has services, put it at the top of the service list. 2729 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU service list: " + app); 2730 mLruProcesses.add(mLruProcessActivityStart, app); 2731 nextIndex = mLruProcessServiceStart; 2732 mLruProcessActivityStart++; 2733 } else { 2734 // Process not otherwise of interest, it goes to the top of the non-service area. 2735 int index = mLruProcessServiceStart; 2736 if (client != null) { 2737 // If there is a client, don't allow the process to be moved up higher 2738 // in the list than that client. 2739 int clientIndex = mLruProcesses.lastIndexOf(client); 2740 if (DEBUG_LRU && clientIndex < 0) Slog.d(TAG, "Unknown client " + client 2741 + " when updating " + app); 2742 if (clientIndex <= lrui) { 2743 // Don't allow the client index restriction to push it down farther in the 2744 // list than it already is. 2745 clientIndex = lrui; 2746 } 2747 if (clientIndex >= 0 && index > clientIndex) { 2748 index = clientIndex; 2749 } 2750 } 2751 if (DEBUG_LRU) Slog.d(TAG, "Adding at " + index + " of LRU list: " + app); 2752 mLruProcesses.add(index, app); 2753 nextIndex = index-1; 2754 mLruProcessActivityStart++; 2755 mLruProcessServiceStart++; 2756 } 2757 2758 // If the app is currently using a content provider or service, 2759 // bump those processes as well. 2760 for (int j=app.connections.size()-1; j>=0; j--) { 2761 ConnectionRecord cr = app.connections.valueAt(j); 2762 if (cr.binding != null && !cr.serviceDead && cr.binding.service != null 2763 && cr.binding.service.app != null 2764 && cr.binding.service.app.lruSeq != mLruSeq 2765 && !cr.binding.service.app.persistent) { 2766 nextIndex = updateLruProcessInternalLocked(cr.binding.service.app, now, nextIndex, 2767 "service connection", cr, app); 2768 } 2769 } 2770 for (int j=app.conProviders.size()-1; j>=0; j--) { 2771 ContentProviderRecord cpr = app.conProviders.get(j).provider; 2772 if (cpr.proc != null && cpr.proc.lruSeq != mLruSeq && !cpr.proc.persistent) { 2773 nextIndex = updateLruProcessInternalLocked(cpr.proc, now, nextIndex, 2774 "provider reference", cpr, app); 2775 } 2776 } 2777 } 2778 2779 final ProcessRecord getProcessRecordLocked(String processName, int uid, boolean keepIfLarge) { 2780 if (uid == Process.SYSTEM_UID) { 2781 // The system gets to run in any process. If there are multiple 2782 // processes with the same uid, just pick the first (this 2783 // should never happen). 2784 SparseArray<ProcessRecord> procs = mProcessNames.getMap().get(processName); 2785 if (procs == null) return null; 2786 final int N = procs.size(); 2787 for (int i = 0; i < N; i++) { 2788 if (UserHandle.isSameUser(procs.keyAt(i), uid)) return procs.valueAt(i); 2789 } 2790 } 2791 ProcessRecord proc = mProcessNames.get(processName, uid); 2792 if (false && proc != null && !keepIfLarge 2793 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY 2794 && proc.lastCachedPss >= 4000) { 2795 // Turn this condition on to cause killing to happen regularly, for testing. 2796 if (proc.baseProcessTracker != null) { 2797 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2798 } 2799 killUnneededProcessLocked(proc, Long.toString(proc.lastCachedPss) 2800 + "k from cached"); 2801 } else if (proc != null && !keepIfLarge 2802 && mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 2803 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 2804 if (DEBUG_PSS) Slog.d(TAG, "May not keep " + proc + ": pss=" + proc.lastCachedPss); 2805 if (proc.lastCachedPss >= mProcessList.getCachedRestoreThresholdKb()) { 2806 if (proc.baseProcessTracker != null) { 2807 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2808 } 2809 killUnneededProcessLocked(proc, Long.toString(proc.lastCachedPss) 2810 + "k from cached"); 2811 } 2812 } 2813 return proc; 2814 } 2815 2816 void ensurePackageDexOpt(String packageName) { 2817 IPackageManager pm = AppGlobals.getPackageManager(); 2818 try { 2819 if (pm.performDexOptIfNeeded(packageName, null /* instruction set */)) { 2820 mDidDexOpt = true; 2821 } 2822 } catch (RemoteException e) { 2823 } 2824 } 2825 2826 boolean isNextTransitionForward() { 2827 int transit = mWindowManager.getPendingAppTransition(); 2828 return transit == AppTransition.TRANSIT_ACTIVITY_OPEN 2829 || transit == AppTransition.TRANSIT_TASK_OPEN 2830 || transit == AppTransition.TRANSIT_TASK_TO_FRONT; 2831 } 2832 2833 final ProcessRecord startProcessLocked(String processName, 2834 ApplicationInfo info, boolean knownToBeDead, int intentFlags, 2835 String hostingType, ComponentName hostingName, boolean allowWhileBooting, 2836 boolean isolated, boolean keepIfLarge) { 2837 ProcessRecord app; 2838 if (!isolated) { 2839 app = getProcessRecordLocked(processName, info.uid, keepIfLarge); 2840 } else { 2841 // If this is an isolated process, it can't re-use an existing process. 2842 app = null; 2843 } 2844 // We don't have to do anything more if: 2845 // (1) There is an existing application record; and 2846 // (2) The caller doesn't think it is dead, OR there is no thread 2847 // object attached to it so we know it couldn't have crashed; and 2848 // (3) There is a pid assigned to it, so it is either starting or 2849 // already running. 2850 if (DEBUG_PROCESSES) Slog.v(TAG, "startProcess: name=" + processName 2851 + " app=" + app + " knownToBeDead=" + knownToBeDead 2852 + " thread=" + (app != null ? app.thread : null) 2853 + " pid=" + (app != null ? app.pid : -1)); 2854 if (app != null && app.pid > 0) { 2855 if (!knownToBeDead || app.thread == null) { 2856 // We already have the app running, or are waiting for it to 2857 // come up (we have a pid but not yet its thread), so keep it. 2858 if (DEBUG_PROCESSES) Slog.v(TAG, "App already running: " + app); 2859 // If this is a new package in the process, add the package to the list 2860 app.addPackage(info.packageName, info.versionCode, mProcessStats); 2861 return app; 2862 } 2863 2864 // An application record is attached to a previous process, 2865 // clean it up now. 2866 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, "App died: " + app); 2867 Process.killProcessGroup(app.info.uid, app.pid); 2868 handleAppDiedLocked(app, true, true); 2869 } 2870 2871 String hostingNameStr = hostingName != null 2872 ? hostingName.flattenToShortString() : null; 2873 2874 if (!isolated) { 2875 if ((intentFlags&Intent.FLAG_FROM_BACKGROUND) != 0) { 2876 // If we are in the background, then check to see if this process 2877 // is bad. If so, we will just silently fail. 2878 if (mBadProcesses.get(info.processName, info.uid) != null) { 2879 if (DEBUG_PROCESSES) Slog.v(TAG, "Bad process: " + info.uid 2880 + "/" + info.processName); 2881 return null; 2882 } 2883 } else { 2884 // When the user is explicitly starting a process, then clear its 2885 // crash count so that we won't make it bad until they see at 2886 // least one crash dialog again, and make the process good again 2887 // if it had been bad. 2888 if (DEBUG_PROCESSES) Slog.v(TAG, "Clearing bad process: " + info.uid 2889 + "/" + info.processName); 2890 mProcessCrashTimes.remove(info.processName, info.uid); 2891 if (mBadProcesses.get(info.processName, info.uid) != null) { 2892 EventLog.writeEvent(EventLogTags.AM_PROC_GOOD, 2893 UserHandle.getUserId(info.uid), info.uid, 2894 info.processName); 2895 mBadProcesses.remove(info.processName, info.uid); 2896 if (app != null) { 2897 app.bad = false; 2898 } 2899 } 2900 } 2901 } 2902 2903 if (app == null) { 2904 app = newProcessRecordLocked(info, processName, isolated); 2905 if (app == null) { 2906 Slog.w(TAG, "Failed making new process record for " 2907 + processName + "/" + info.uid + " isolated=" + isolated); 2908 return null; 2909 } 2910 mProcessNames.put(processName, app.uid, app); 2911 if (isolated) { 2912 mIsolatedProcesses.put(app.uid, app); 2913 } 2914 } else { 2915 // If this is a new package in the process, add the package to the list 2916 app.addPackage(info.packageName, info.versionCode, mProcessStats); 2917 } 2918 2919 // If the system is not ready yet, then hold off on starting this 2920 // process until it is. 2921 if (!mProcessesReady 2922 && !isAllowedWhileBooting(info) 2923 && !allowWhileBooting) { 2924 if (!mProcessesOnHold.contains(app)) { 2925 mProcessesOnHold.add(app); 2926 } 2927 if (DEBUG_PROCESSES) Slog.v(TAG, "System not ready, putting on hold: " + app); 2928 return app; 2929 } 2930 2931 startProcessLocked(app, hostingType, hostingNameStr, null /* ABI override */); 2932 return (app.pid != 0) ? app : null; 2933 } 2934 2935 boolean isAllowedWhileBooting(ApplicationInfo ai) { 2936 return (ai.flags&ApplicationInfo.FLAG_PERSISTENT) != 0; 2937 } 2938 2939 private final void startProcessLocked(ProcessRecord app, 2940 String hostingType, String hostingNameStr, String abiOverride) { 2941 if (app.pid > 0 && app.pid != MY_PID) { 2942 synchronized (mPidsSelfLocked) { 2943 mPidsSelfLocked.remove(app.pid); 2944 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 2945 } 2946 app.setPid(0); 2947 } 2948 2949 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 2950 "startProcessLocked removing on hold: " + app); 2951 mProcessesOnHold.remove(app); 2952 2953 updateCpuStats(); 2954 2955 try { 2956 int uid = app.uid; 2957 2958 int[] gids = null; 2959 int mountExternal = Zygote.MOUNT_EXTERNAL_NONE; 2960 if (!app.isolated) { 2961 int[] permGids = null; 2962 try { 2963 final PackageManager pm = mContext.getPackageManager(); 2964 permGids = pm.getPackageGids(app.info.packageName); 2965 2966 if (Environment.isExternalStorageEmulated()) { 2967 if (pm.checkPermission( 2968 android.Manifest.permission.ACCESS_ALL_EXTERNAL_STORAGE, 2969 app.info.packageName) == PERMISSION_GRANTED) { 2970 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER_ALL; 2971 } else { 2972 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER; 2973 } 2974 } 2975 } catch (PackageManager.NameNotFoundException e) { 2976 Slog.w(TAG, "Unable to retrieve gids", e); 2977 } 2978 2979 /* 2980 * Add shared application and profile GIDs so applications can share some 2981 * resources like shared libraries and access user-wide resources 2982 */ 2983 if (permGids == null) { 2984 gids = new int[2]; 2985 } else { 2986 gids = new int[permGids.length + 2]; 2987 System.arraycopy(permGids, 0, gids, 2, permGids.length); 2988 } 2989 gids[0] = UserHandle.getSharedAppGid(UserHandle.getAppId(uid)); 2990 gids[1] = UserHandle.getUserGid(UserHandle.getUserId(uid)); 2991 } 2992 if (mFactoryTest != FactoryTest.FACTORY_TEST_OFF) { 2993 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 2994 && mTopComponent != null 2995 && app.processName.equals(mTopComponent.getPackageName())) { 2996 uid = 0; 2997 } 2998 if (mFactoryTest == FactoryTest.FACTORY_TEST_HIGH_LEVEL 2999 && (app.info.flags&ApplicationInfo.FLAG_FACTORY_TEST) != 0) { 3000 uid = 0; 3001 } 3002 } 3003 int debugFlags = 0; 3004 if ((app.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 3005 debugFlags |= Zygote.DEBUG_ENABLE_DEBUGGER; 3006 // Also turn on CheckJNI for debuggable apps. It's quite 3007 // awkward to turn on otherwise. 3008 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 3009 } 3010 // Run the app in safe mode if its manifest requests so or the 3011 // system is booted in safe mode. 3012 if ((app.info.flags & ApplicationInfo.FLAG_VM_SAFE_MODE) != 0 || 3013 mSafeMode == true) { 3014 debugFlags |= Zygote.DEBUG_ENABLE_SAFEMODE; 3015 } 3016 if ("1".equals(SystemProperties.get("debug.checkjni"))) { 3017 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 3018 } 3019 if ("1".equals(SystemProperties.get("debug.jni.logging"))) { 3020 debugFlags |= Zygote.DEBUG_ENABLE_JNI_LOGGING; 3021 } 3022 if ("1".equals(SystemProperties.get("debug.assert"))) { 3023 debugFlags |= Zygote.DEBUG_ENABLE_ASSERT; 3024 } 3025 3026 String requiredAbi = (abiOverride != null) ? abiOverride : app.info.primaryCpuAbi; 3027 if (requiredAbi == null) { 3028 requiredAbi = Build.SUPPORTED_ABIS[0]; 3029 } 3030 3031 // Start the process. It will either succeed and return a result containing 3032 // the PID of the new process, or else throw a RuntimeException. 3033 Process.ProcessStartResult startResult = Process.start("android.app.ActivityThread", 3034 app.processName, uid, uid, gids, debugFlags, mountExternal, 3035 app.info.targetSdkVersion, app.info.seinfo, requiredAbi, null); 3036 3037 if (app.isolated) { 3038 mBatteryStatsService.addIsolatedUid(app.uid, app.info.uid); 3039 } 3040 mBatteryStatsService.noteProcessStart(app.processName, app.info.uid); 3041 3042 EventLog.writeEvent(EventLogTags.AM_PROC_START, 3043 UserHandle.getUserId(uid), startResult.pid, uid, 3044 app.processName, hostingType, 3045 hostingNameStr != null ? hostingNameStr : ""); 3046 3047 if (app.persistent) { 3048 Watchdog.getInstance().processStarted(app.processName, startResult.pid); 3049 } 3050 3051 StringBuilder buf = mStringBuilder; 3052 buf.setLength(0); 3053 buf.append("Start proc "); 3054 buf.append(app.processName); 3055 buf.append(" for "); 3056 buf.append(hostingType); 3057 if (hostingNameStr != null) { 3058 buf.append(" "); 3059 buf.append(hostingNameStr); 3060 } 3061 buf.append(": pid="); 3062 buf.append(startResult.pid); 3063 buf.append(" uid="); 3064 buf.append(uid); 3065 buf.append(" gids={"); 3066 if (gids != null) { 3067 for (int gi=0; gi<gids.length; gi++) { 3068 if (gi != 0) buf.append(", "); 3069 buf.append(gids[gi]); 3070 3071 } 3072 } 3073 buf.append("}"); 3074 if (requiredAbi != null) { 3075 buf.append(" abi="); 3076 buf.append(requiredAbi); 3077 } 3078 Slog.i(TAG, buf.toString()); 3079 app.setPid(startResult.pid); 3080 app.usingWrapper = startResult.usingWrapper; 3081 app.removed = false; 3082 app.killedByAm = false; 3083 synchronized (mPidsSelfLocked) { 3084 this.mPidsSelfLocked.put(startResult.pid, app); 3085 Message msg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 3086 msg.obj = app; 3087 mHandler.sendMessageDelayed(msg, startResult.usingWrapper 3088 ? PROC_START_TIMEOUT_WITH_WRAPPER : PROC_START_TIMEOUT); 3089 } 3090 } catch (RuntimeException e) { 3091 // XXX do better error recovery. 3092 app.setPid(0); 3093 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 3094 if (app.isolated) { 3095 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 3096 } 3097 Slog.e(TAG, "Failure starting process " + app.processName, e); 3098 } 3099 } 3100 3101 void updateUsageStats(ActivityRecord component, boolean resumed) { 3102 if (DEBUG_SWITCH) Slog.d(TAG, "updateUsageStats: comp=" + component + "res=" + resumed); 3103 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 3104 if (resumed) { 3105 if (mUsageStatsService != null) { 3106 mUsageStatsService.reportEvent(component.realActivity, component.userId, 3107 System.currentTimeMillis(), 3108 UsageStats.Event.MOVE_TO_FOREGROUND); 3109 } 3110 synchronized (stats) { 3111 stats.noteActivityResumedLocked(component.app.uid); 3112 } 3113 } else { 3114 if (mUsageStatsService != null) { 3115 mUsageStatsService.reportEvent(component.realActivity, component.userId, 3116 System.currentTimeMillis(), 3117 UsageStats.Event.MOVE_TO_BACKGROUND); 3118 } 3119 synchronized (stats) { 3120 stats.noteActivityPausedLocked(component.app.uid); 3121 } 3122 } 3123 } 3124 3125 Intent getHomeIntent() { 3126 Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null); 3127 intent.setComponent(mTopComponent); 3128 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 3129 intent.addCategory(Intent.CATEGORY_HOME); 3130 } 3131 return intent; 3132 } 3133 3134 boolean startHomeActivityLocked(int userId) { 3135 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3136 && mTopAction == null) { 3137 // We are running in factory test mode, but unable to find 3138 // the factory test app, so just sit around displaying the 3139 // error message and don't try to start anything. 3140 return false; 3141 } 3142 Intent intent = getHomeIntent(); 3143 ActivityInfo aInfo = 3144 resolveActivityInfo(intent, STOCK_PM_FLAGS, userId); 3145 if (aInfo != null) { 3146 intent.setComponent(new ComponentName( 3147 aInfo.applicationInfo.packageName, aInfo.name)); 3148 // Don't do this if the home app is currently being 3149 // instrumented. 3150 aInfo = new ActivityInfo(aInfo); 3151 aInfo.applicationInfo = getAppInfoForUser(aInfo.applicationInfo, userId); 3152 ProcessRecord app = getProcessRecordLocked(aInfo.processName, 3153 aInfo.applicationInfo.uid, true); 3154 if (app == null || app.instrumentationClass == null) { 3155 intent.setFlags(intent.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK); 3156 mStackSupervisor.startHomeActivity(intent, aInfo); 3157 } 3158 } 3159 3160 return true; 3161 } 3162 3163 private ActivityInfo resolveActivityInfo(Intent intent, int flags, int userId) { 3164 ActivityInfo ai = null; 3165 ComponentName comp = intent.getComponent(); 3166 try { 3167 if (comp != null) { 3168 ai = AppGlobals.getPackageManager().getActivityInfo(comp, flags, userId); 3169 } else { 3170 ResolveInfo info = AppGlobals.getPackageManager().resolveIntent( 3171 intent, 3172 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 3173 flags, userId); 3174 3175 if (info != null) { 3176 ai = info.activityInfo; 3177 } 3178 } 3179 } catch (RemoteException e) { 3180 // ignore 3181 } 3182 3183 return ai; 3184 } 3185 3186 /** 3187 * Starts the "new version setup screen" if appropriate. 3188 */ 3189 void startSetupActivityLocked() { 3190 // Only do this once per boot. 3191 if (mCheckedForSetup) { 3192 return; 3193 } 3194 3195 // We will show this screen if the current one is a different 3196 // version than the last one shown, and we are not running in 3197 // low-level factory test mode. 3198 final ContentResolver resolver = mContext.getContentResolver(); 3199 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL && 3200 Settings.Global.getInt(resolver, 3201 Settings.Global.DEVICE_PROVISIONED, 0) != 0) { 3202 mCheckedForSetup = true; 3203 3204 // See if we should be showing the platform update setup UI. 3205 Intent intent = new Intent(Intent.ACTION_UPGRADE_SETUP); 3206 List<ResolveInfo> ris = mContext.getPackageManager() 3207 .queryIntentActivities(intent, PackageManager.GET_META_DATA); 3208 3209 // We don't allow third party apps to replace this. 3210 ResolveInfo ri = null; 3211 for (int i=0; ris != null && i<ris.size(); i++) { 3212 if ((ris.get(i).activityInfo.applicationInfo.flags 3213 & ApplicationInfo.FLAG_SYSTEM) != 0) { 3214 ri = ris.get(i); 3215 break; 3216 } 3217 } 3218 3219 if (ri != null) { 3220 String vers = ri.activityInfo.metaData != null 3221 ? ri.activityInfo.metaData.getString(Intent.METADATA_SETUP_VERSION) 3222 : null; 3223 if (vers == null && ri.activityInfo.applicationInfo.metaData != null) { 3224 vers = ri.activityInfo.applicationInfo.metaData.getString( 3225 Intent.METADATA_SETUP_VERSION); 3226 } 3227 String lastVers = Settings.Secure.getString( 3228 resolver, Settings.Secure.LAST_SETUP_SHOWN); 3229 if (vers != null && !vers.equals(lastVers)) { 3230 intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 3231 intent.setComponent(new ComponentName( 3232 ri.activityInfo.packageName, ri.activityInfo.name)); 3233 mStackSupervisor.startActivityLocked(null, intent, null, ri.activityInfo, 3234 null, null, null, null, 0, 0, 0, null, 0, null, false, null, null); 3235 } 3236 } 3237 } 3238 } 3239 3240 CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) { 3241 return mCompatModePackages.compatibilityInfoForPackageLocked(ai); 3242 } 3243 3244 void enforceNotIsolatedCaller(String caller) { 3245 if (UserHandle.isIsolated(Binder.getCallingUid())) { 3246 throw new SecurityException("Isolated process not allowed to call " + caller); 3247 } 3248 } 3249 3250 @Override 3251 public int getFrontActivityScreenCompatMode() { 3252 enforceNotIsolatedCaller("getFrontActivityScreenCompatMode"); 3253 synchronized (this) { 3254 return mCompatModePackages.getFrontActivityScreenCompatModeLocked(); 3255 } 3256 } 3257 3258 @Override 3259 public void setFrontActivityScreenCompatMode(int mode) { 3260 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3261 "setFrontActivityScreenCompatMode"); 3262 synchronized (this) { 3263 mCompatModePackages.setFrontActivityScreenCompatModeLocked(mode); 3264 } 3265 } 3266 3267 @Override 3268 public int getPackageScreenCompatMode(String packageName) { 3269 enforceNotIsolatedCaller("getPackageScreenCompatMode"); 3270 synchronized (this) { 3271 return mCompatModePackages.getPackageScreenCompatModeLocked(packageName); 3272 } 3273 } 3274 3275 @Override 3276 public void setPackageScreenCompatMode(String packageName, int mode) { 3277 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3278 "setPackageScreenCompatMode"); 3279 synchronized (this) { 3280 mCompatModePackages.setPackageScreenCompatModeLocked(packageName, mode); 3281 } 3282 } 3283 3284 @Override 3285 public boolean getPackageAskScreenCompat(String packageName) { 3286 enforceNotIsolatedCaller("getPackageAskScreenCompat"); 3287 synchronized (this) { 3288 return mCompatModePackages.getPackageAskCompatModeLocked(packageName); 3289 } 3290 } 3291 3292 @Override 3293 public void setPackageAskScreenCompat(String packageName, boolean ask) { 3294 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3295 "setPackageAskScreenCompat"); 3296 synchronized (this) { 3297 mCompatModePackages.setPackageAskCompatModeLocked(packageName, ask); 3298 } 3299 } 3300 3301 private void dispatchProcessesChanged() { 3302 int N; 3303 synchronized (this) { 3304 N = mPendingProcessChanges.size(); 3305 if (mActiveProcessChanges.length < N) { 3306 mActiveProcessChanges = new ProcessChangeItem[N]; 3307 } 3308 mPendingProcessChanges.toArray(mActiveProcessChanges); 3309 mAvailProcessChanges.addAll(mPendingProcessChanges); 3310 mPendingProcessChanges.clear(); 3311 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "*** Delivering " + N + " process changes"); 3312 } 3313 3314 int i = mProcessObservers.beginBroadcast(); 3315 while (i > 0) { 3316 i--; 3317 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3318 if (observer != null) { 3319 try { 3320 for (int j=0; j<N; j++) { 3321 ProcessChangeItem item = mActiveProcessChanges[j]; 3322 if ((item.changes&ProcessChangeItem.CHANGE_ACTIVITIES) != 0) { 3323 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "ACTIVITIES CHANGED pid=" 3324 + item.pid + " uid=" + item.uid + ": " 3325 + item.foregroundActivities); 3326 observer.onForegroundActivitiesChanged(item.pid, item.uid, 3327 item.foregroundActivities); 3328 } 3329 if ((item.changes&ProcessChangeItem.CHANGE_PROCESS_STATE) != 0) { 3330 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "PROCSTATE CHANGED pid=" 3331 + item.pid + " uid=" + item.uid + ": " + item.processState); 3332 observer.onProcessStateChanged(item.pid, item.uid, item.processState); 3333 } 3334 } 3335 } catch (RemoteException e) { 3336 } 3337 } 3338 } 3339 mProcessObservers.finishBroadcast(); 3340 } 3341 3342 private void dispatchProcessDied(int pid, int uid) { 3343 int i = mProcessObservers.beginBroadcast(); 3344 while (i > 0) { 3345 i--; 3346 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3347 if (observer != null) { 3348 try { 3349 observer.onProcessDied(pid, uid); 3350 } catch (RemoteException e) { 3351 } 3352 } 3353 } 3354 mProcessObservers.finishBroadcast(); 3355 } 3356 3357 @Override 3358 public final int startActivity(IApplicationThread caller, String callingPackage, 3359 Intent intent, String resolvedType, IBinder resultTo, 3360 String resultWho, int requestCode, int startFlags, 3361 String profileFile, ParcelFileDescriptor profileFd, Bundle options) { 3362 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo, 3363 resultWho, requestCode, 3364 startFlags, profileFile, profileFd, options, UserHandle.getCallingUserId()); 3365 } 3366 3367 @Override 3368 public final int startActivityAsUser(IApplicationThread caller, String callingPackage, 3369 Intent intent, String resolvedType, IBinder resultTo, 3370 String resultWho, int requestCode, int startFlags, 3371 String profileFile, ParcelFileDescriptor profileFd, Bundle options, int userId) { 3372 enforceNotIsolatedCaller("startActivity"); 3373 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3374 false, ALLOW_FULL_ONLY, "startActivity", null); 3375 // TODO: Switch to user app stacks here. 3376 return mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 3377 null, null, resultTo, resultWho, requestCode, startFlags, profileFile, profileFd, 3378 null, null, options, userId, null); 3379 } 3380 3381 @Override 3382 public final WaitResult startActivityAndWait(IApplicationThread caller, String callingPackage, 3383 Intent intent, String resolvedType, IBinder resultTo, 3384 String resultWho, int requestCode, int startFlags, String profileFile, 3385 ParcelFileDescriptor profileFd, Bundle options, int userId) { 3386 enforceNotIsolatedCaller("startActivityAndWait"); 3387 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3388 false, ALLOW_FULL_ONLY, "startActivityAndWait", null); 3389 WaitResult res = new WaitResult(); 3390 // TODO: Switch to user app stacks here. 3391 mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 3392 null, null, resultTo, resultWho, requestCode, startFlags, profileFile, profileFd, 3393 res, null, options, userId, null); 3394 return res; 3395 } 3396 3397 @Override 3398 public final int startActivityWithConfig(IApplicationThread caller, String callingPackage, 3399 Intent intent, String resolvedType, IBinder resultTo, 3400 String resultWho, int requestCode, int startFlags, Configuration config, 3401 Bundle options, int userId) { 3402 enforceNotIsolatedCaller("startActivityWithConfig"); 3403 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3404 false, ALLOW_FULL_ONLY, "startActivityWithConfig", null); 3405 // TODO: Switch to user app stacks here. 3406 int ret = mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, 3407 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3408 null, null, null, config, options, userId, null); 3409 return ret; 3410 } 3411 3412 @Override 3413 public int startActivityIntentSender(IApplicationThread caller, 3414 IntentSender intent, Intent fillInIntent, String resolvedType, 3415 IBinder resultTo, String resultWho, int requestCode, 3416 int flagsMask, int flagsValues, Bundle options) { 3417 enforceNotIsolatedCaller("startActivityIntentSender"); 3418 // Refuse possible leaked file descriptors 3419 if (fillInIntent != null && fillInIntent.hasFileDescriptors()) { 3420 throw new IllegalArgumentException("File descriptors passed in Intent"); 3421 } 3422 3423 IIntentSender sender = intent.getTarget(); 3424 if (!(sender instanceof PendingIntentRecord)) { 3425 throw new IllegalArgumentException("Bad PendingIntent object"); 3426 } 3427 3428 PendingIntentRecord pir = (PendingIntentRecord)sender; 3429 3430 synchronized (this) { 3431 // If this is coming from the currently resumed activity, it is 3432 // effectively saying that app switches are allowed at this point. 3433 final ActivityStack stack = getFocusedStack(); 3434 if (stack.mResumedActivity != null && 3435 stack.mResumedActivity.info.applicationInfo.uid == Binder.getCallingUid()) { 3436 mAppSwitchesAllowedTime = 0; 3437 } 3438 } 3439 int ret = pir.sendInner(0, fillInIntent, resolvedType, null, null, 3440 resultTo, resultWho, requestCode, flagsMask, flagsValues, options, null); 3441 return ret; 3442 } 3443 3444 @Override 3445 public int startVoiceActivity(String callingPackage, int callingPid, int callingUid, 3446 Intent intent, String resolvedType, IVoiceInteractionSession session, 3447 IVoiceInteractor interactor, int startFlags, String profileFile, 3448 ParcelFileDescriptor profileFd, Bundle options, int userId) { 3449 if (checkCallingPermission(Manifest.permission.BIND_VOICE_INTERACTION) 3450 != PackageManager.PERMISSION_GRANTED) { 3451 String msg = "Permission Denial: startVoiceActivity() from pid=" 3452 + Binder.getCallingPid() 3453 + ", uid=" + Binder.getCallingUid() 3454 + " requires " + android.Manifest.permission.BIND_VOICE_INTERACTION; 3455 Slog.w(TAG, msg); 3456 throw new SecurityException(msg); 3457 } 3458 if (session == null || interactor == null) { 3459 throw new NullPointerException("null session or interactor"); 3460 } 3461 userId = handleIncomingUser(callingPid, callingUid, userId, 3462 false, ALLOW_FULL_ONLY, "startVoiceActivity", null); 3463 // TODO: Switch to user app stacks here. 3464 return mStackSupervisor.startActivityMayWait(null, callingUid, callingPackage, intent, 3465 resolvedType, session, interactor, null, null, 0, startFlags, 3466 profileFile, profileFd, null, null, options, userId, null); 3467 } 3468 3469 @Override 3470 public boolean startNextMatchingActivity(IBinder callingActivity, 3471 Intent intent, Bundle options) { 3472 // Refuse possible leaked file descriptors 3473 if (intent != null && intent.hasFileDescriptors() == true) { 3474 throw new IllegalArgumentException("File descriptors passed in Intent"); 3475 } 3476 3477 synchronized (this) { 3478 final ActivityRecord r = ActivityRecord.isInStackLocked(callingActivity); 3479 if (r == null) { 3480 ActivityOptions.abort(options); 3481 return false; 3482 } 3483 if (r.app == null || r.app.thread == null) { 3484 // The caller is not running... d'oh! 3485 ActivityOptions.abort(options); 3486 return false; 3487 } 3488 intent = new Intent(intent); 3489 // The caller is not allowed to change the data. 3490 intent.setDataAndType(r.intent.getData(), r.intent.getType()); 3491 // And we are resetting to find the next component... 3492 intent.setComponent(null); 3493 3494 final boolean debug = ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0); 3495 3496 ActivityInfo aInfo = null; 3497 try { 3498 List<ResolveInfo> resolves = 3499 AppGlobals.getPackageManager().queryIntentActivities( 3500 intent, r.resolvedType, 3501 PackageManager.MATCH_DEFAULT_ONLY | STOCK_PM_FLAGS, 3502 UserHandle.getCallingUserId()); 3503 3504 // Look for the original activity in the list... 3505 final int N = resolves != null ? resolves.size() : 0; 3506 for (int i=0; i<N; i++) { 3507 ResolveInfo rInfo = resolves.get(i); 3508 if (rInfo.activityInfo.packageName.equals(r.packageName) 3509 && rInfo.activityInfo.name.equals(r.info.name)) { 3510 // We found the current one... the next matching is 3511 // after it. 3512 i++; 3513 if (i<N) { 3514 aInfo = resolves.get(i).activityInfo; 3515 } 3516 if (debug) { 3517 Slog.v(TAG, "Next matching activity: found current " + r.packageName 3518 + "/" + r.info.name); 3519 Slog.v(TAG, "Next matching activity: next is " + aInfo.packageName 3520 + "/" + aInfo.name); 3521 } 3522 break; 3523 } 3524 } 3525 } catch (RemoteException e) { 3526 } 3527 3528 if (aInfo == null) { 3529 // Nobody who is next! 3530 ActivityOptions.abort(options); 3531 if (debug) Slog.d(TAG, "Next matching activity: nothing found"); 3532 return false; 3533 } 3534 3535 intent.setComponent(new ComponentName( 3536 aInfo.applicationInfo.packageName, aInfo.name)); 3537 intent.setFlags(intent.getFlags()&~( 3538 Intent.FLAG_ACTIVITY_FORWARD_RESULT| 3539 Intent.FLAG_ACTIVITY_CLEAR_TOP| 3540 Intent.FLAG_ACTIVITY_MULTIPLE_TASK| 3541 Intent.FLAG_ACTIVITY_NEW_TASK)); 3542 3543 // Okay now we need to start the new activity, replacing the 3544 // currently running activity. This is a little tricky because 3545 // we want to start the new one as if the current one is finished, 3546 // but not finish the current one first so that there is no flicker. 3547 // And thus... 3548 final boolean wasFinishing = r.finishing; 3549 r.finishing = true; 3550 3551 // Propagate reply information over to the new activity. 3552 final ActivityRecord resultTo = r.resultTo; 3553 final String resultWho = r.resultWho; 3554 final int requestCode = r.requestCode; 3555 r.resultTo = null; 3556 if (resultTo != null) { 3557 resultTo.removeResultsLocked(r, resultWho, requestCode); 3558 } 3559 3560 final long origId = Binder.clearCallingIdentity(); 3561 int res = mStackSupervisor.startActivityLocked(r.app.thread, intent, 3562 r.resolvedType, aInfo, null, null, resultTo != null ? resultTo.appToken : null, 3563 resultWho, requestCode, -1, r.launchedFromUid, r.launchedFromPackage, 0, 3564 options, false, null, null); 3565 Binder.restoreCallingIdentity(origId); 3566 3567 r.finishing = wasFinishing; 3568 if (res != ActivityManager.START_SUCCESS) { 3569 return false; 3570 } 3571 return true; 3572 } 3573 } 3574 3575 @Override 3576 public final int startActivityFromRecents(int taskId, Bundle options) { 3577 if (checkCallingPermission(START_TASKS_FROM_RECENTS) != PackageManager.PERMISSION_GRANTED) { 3578 String msg = "Permission Denial: startActivityFromRecents called without " + 3579 START_TASKS_FROM_RECENTS; 3580 Slog.w(TAG, msg); 3581 throw new SecurityException(msg); 3582 } 3583 final int callingUid; 3584 final String callingPackage; 3585 final Intent intent; 3586 final int userId; 3587 synchronized (this) { 3588 final TaskRecord task = recentTaskForIdLocked(taskId); 3589 if (task == null) { 3590 throw new ActivityNotFoundException("Task " + taskId + " not found."); 3591 } 3592 callingUid = task.mCallingUid; 3593 callingPackage = task.mCallingPackage; 3594 intent = task.intent; 3595 userId = task.userId; 3596 } 3597 return startActivityInPackage(callingUid, callingPackage, intent, null, null, null, 0, 0, 3598 options, userId, null); 3599 } 3600 3601 final int startActivityInPackage(int uid, String callingPackage, 3602 Intent intent, String resolvedType, IBinder resultTo, 3603 String resultWho, int requestCode, int startFlags, Bundle options, int userId, 3604 IActivityContainer container) { 3605 3606 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3607 false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 3608 3609 // TODO: Switch to user app stacks here. 3610 int ret = mStackSupervisor.startActivityMayWait(null, uid, callingPackage, intent, resolvedType, 3611 null, null, resultTo, resultWho, requestCode, startFlags, 3612 null, null, null, null, options, userId, container); 3613 return ret; 3614 } 3615 3616 @Override 3617 public final int startActivities(IApplicationThread caller, String callingPackage, 3618 Intent[] intents, String[] resolvedTypes, IBinder resultTo, Bundle options, 3619 int userId) { 3620 enforceNotIsolatedCaller("startActivities"); 3621 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3622 false, ALLOW_FULL_ONLY, "startActivity", null); 3623 // TODO: Switch to user app stacks here. 3624 int ret = mStackSupervisor.startActivities(caller, -1, callingPackage, intents, 3625 resolvedTypes, resultTo, options, userId); 3626 return ret; 3627 } 3628 3629 final int startActivitiesInPackage(int uid, String callingPackage, 3630 Intent[] intents, String[] resolvedTypes, IBinder resultTo, 3631 Bundle options, int userId) { 3632 3633 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3634 false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 3635 // TODO: Switch to user app stacks here. 3636 int ret = mStackSupervisor.startActivities(null, uid, callingPackage, intents, resolvedTypes, 3637 resultTo, options, userId); 3638 return ret; 3639 } 3640 3641 final void addRecentTaskLocked(TaskRecord task) { 3642 int N = mRecentTasks.size(); 3643 // Quick case: check if the top-most recent task is the same. 3644 if (N > 0 && mRecentTasks.get(0) == task) { 3645 return; 3646 } 3647 // Another quick case: never add voice sessions. 3648 if (task.voiceSession != null) { 3649 return; 3650 } 3651 // Remove any existing entries that are the same kind of task. 3652 final Intent intent = task.intent; 3653 final boolean document = intent != null && intent.isDocument(); 3654 final ComponentName comp = intent.getComponent(); 3655 3656 int maxRecents = task.maxRecents - 1; 3657 for (int i=0; i<N; i++) { 3658 final TaskRecord tr = mRecentTasks.get(i); 3659 if (task != tr) { 3660 if (task.userId != tr.userId) { 3661 continue; 3662 } 3663 if (i > MAX_RECENT_BITMAPS) { 3664 tr.freeLastThumbnail(); 3665 } 3666 final Intent trIntent = tr.intent; 3667 if ((task.affinity == null || !task.affinity.equals(tr.affinity)) && 3668 (intent == null || !intent.filterEquals(trIntent))) { 3669 continue; 3670 } 3671 final boolean trIsDocument = trIntent != null && trIntent.isDocument(); 3672 if (document && trIsDocument) { 3673 // These are the same document activity (not necessarily the same doc). 3674 if (maxRecents > 0) { 3675 --maxRecents; 3676 continue; 3677 } 3678 // Hit the maximum number of documents for this task. Fall through 3679 // and remove this document from recents. 3680 } else if (document || trIsDocument) { 3681 // Only one of these is a document. Not the droid we're looking for. 3682 continue; 3683 } 3684 } 3685 3686 // Either task and tr are the same or, their affinities match or their intents match 3687 // and neither of them is a document, or they are documents using the same activity 3688 // and their maxRecents has been reached. 3689 tr.disposeThumbnail(); 3690 mRecentTasks.remove(i); 3691 if (task != tr) { 3692 tr.closeRecentsChain(); 3693 } 3694 i--; 3695 N--; 3696 if (task.intent == null) { 3697 // If the new recent task we are adding is not fully 3698 // specified, then replace it with the existing recent task. 3699 task = tr; 3700 } 3701 notifyTaskPersisterLocked(tr, false); 3702 } 3703 if (N >= MAX_RECENT_TASKS) { 3704 final TaskRecord tr = mRecentTasks.remove(N - 1); 3705 tr.disposeThumbnail(); 3706 tr.closeRecentsChain(); 3707 } 3708 mRecentTasks.add(0, task); 3709 } 3710 3711 @Override 3712 public void reportActivityFullyDrawn(IBinder token) { 3713 synchronized (this) { 3714 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3715 if (r == null) { 3716 return; 3717 } 3718 r.reportFullyDrawnLocked(); 3719 } 3720 } 3721 3722 @Override 3723 public void setRequestedOrientation(IBinder token, int requestedOrientation) { 3724 synchronized (this) { 3725 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3726 if (r == null) { 3727 return; 3728 } 3729 final long origId = Binder.clearCallingIdentity(); 3730 mWindowManager.setAppOrientation(r.appToken, requestedOrientation); 3731 Configuration config = mWindowManager.updateOrientationFromAppTokens( 3732 mConfiguration, r.mayFreezeScreenLocked(r.app) ? r.appToken : null); 3733 if (config != null) { 3734 r.frozenBeforeDestroy = true; 3735 if (!updateConfigurationLocked(config, r, false, false)) { 3736 mStackSupervisor.resumeTopActivitiesLocked(); 3737 } 3738 } 3739 Binder.restoreCallingIdentity(origId); 3740 } 3741 } 3742 3743 @Override 3744 public int getRequestedOrientation(IBinder token) { 3745 synchronized (this) { 3746 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3747 if (r == null) { 3748 return ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED; 3749 } 3750 return mWindowManager.getAppOrientation(r.appToken); 3751 } 3752 } 3753 3754 /** 3755 * This is the internal entry point for handling Activity.finish(). 3756 * 3757 * @param token The Binder token referencing the Activity we want to finish. 3758 * @param resultCode Result code, if any, from this Activity. 3759 * @param resultData Result data (Intent), if any, from this Activity. 3760 * @param finishTask Whether to finish the task associated with this Activity. Only applies to 3761 * the root Activity in the task. 3762 * 3763 * @return Returns true if the activity successfully finished, or false if it is still running. 3764 */ 3765 @Override 3766 public final boolean finishActivity(IBinder token, int resultCode, Intent resultData, 3767 boolean finishTask) { 3768 // Refuse possible leaked file descriptors 3769 if (resultData != null && resultData.hasFileDescriptors() == true) { 3770 throw new IllegalArgumentException("File descriptors passed in Intent"); 3771 } 3772 3773 synchronized(this) { 3774 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3775 if (r == null) { 3776 return true; 3777 } 3778 // Keep track of the root activity of the task before we finish it 3779 TaskRecord tr = r.task; 3780 ActivityRecord rootR = tr.getRootActivity(); 3781 // Do not allow task to finish in Lock Task mode. 3782 if (tr == mStackSupervisor.mLockTaskModeTask) { 3783 if (rootR == r) { 3784 mStackSupervisor.showLockTaskToast(); 3785 return false; 3786 } 3787 } 3788 if (mController != null) { 3789 // Find the first activity that is not finishing. 3790 ActivityRecord next = r.task.stack.topRunningActivityLocked(token, 0); 3791 if (next != null) { 3792 // ask watcher if this is allowed 3793 boolean resumeOK = true; 3794 try { 3795 resumeOK = mController.activityResuming(next.packageName); 3796 } catch (RemoteException e) { 3797 mController = null; 3798 Watchdog.getInstance().setActivityController(null); 3799 } 3800 3801 if (!resumeOK) { 3802 return false; 3803 } 3804 } 3805 } 3806 final long origId = Binder.clearCallingIdentity(); 3807 try { 3808 boolean res; 3809 if (finishTask && r == rootR) { 3810 // If requested, remove the task that is associated to this activity only if it 3811 // was the root activity in the task. The result code and data is ignored because 3812 // we don't support returning them across task boundaries. 3813 res = removeTaskByIdLocked(tr.taskId, 0); 3814 } else { 3815 res = tr.stack.requestFinishActivityLocked(token, resultCode, 3816 resultData, "app-request", true); 3817 } 3818 return res; 3819 } finally { 3820 Binder.restoreCallingIdentity(origId); 3821 } 3822 } 3823 } 3824 3825 @Override 3826 public final void finishHeavyWeightApp() { 3827 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 3828 != PackageManager.PERMISSION_GRANTED) { 3829 String msg = "Permission Denial: finishHeavyWeightApp() from pid=" 3830 + Binder.getCallingPid() 3831 + ", uid=" + Binder.getCallingUid() 3832 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 3833 Slog.w(TAG, msg); 3834 throw new SecurityException(msg); 3835 } 3836 3837 synchronized(this) { 3838 if (mHeavyWeightProcess == null) { 3839 return; 3840 } 3841 3842 ArrayList<ActivityRecord> activities = new ArrayList<ActivityRecord>( 3843 mHeavyWeightProcess.activities); 3844 for (int i=0; i<activities.size(); i++) { 3845 ActivityRecord r = activities.get(i); 3846 if (!r.finishing) { 3847 r.task.stack.finishActivityLocked(r, Activity.RESULT_CANCELED, 3848 null, "finish-heavy", true); 3849 } 3850 } 3851 3852 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 3853 mHeavyWeightProcess.userId, 0)); 3854 mHeavyWeightProcess = null; 3855 } 3856 } 3857 3858 @Override 3859 public void crashApplication(int uid, int initialPid, String packageName, 3860 String message) { 3861 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 3862 != PackageManager.PERMISSION_GRANTED) { 3863 String msg = "Permission Denial: crashApplication() from pid=" 3864 + Binder.getCallingPid() 3865 + ", uid=" + Binder.getCallingUid() 3866 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 3867 Slog.w(TAG, msg); 3868 throw new SecurityException(msg); 3869 } 3870 3871 synchronized(this) { 3872 ProcessRecord proc = null; 3873 3874 // Figure out which process to kill. We don't trust that initialPid 3875 // still has any relation to current pids, so must scan through the 3876 // list. 3877 synchronized (mPidsSelfLocked) { 3878 for (int i=0; i<mPidsSelfLocked.size(); i++) { 3879 ProcessRecord p = mPidsSelfLocked.valueAt(i); 3880 if (p.uid != uid) { 3881 continue; 3882 } 3883 if (p.pid == initialPid) { 3884 proc = p; 3885 break; 3886 } 3887 if (p.pkgList.containsKey(packageName)) { 3888 proc = p; 3889 } 3890 } 3891 } 3892 3893 if (proc == null) { 3894 Slog.w(TAG, "crashApplication: nothing for uid=" + uid 3895 + " initialPid=" + initialPid 3896 + " packageName=" + packageName); 3897 return; 3898 } 3899 3900 if (proc.thread != null) { 3901 if (proc.pid == Process.myPid()) { 3902 Log.w(TAG, "crashApplication: trying to crash self!"); 3903 return; 3904 } 3905 long ident = Binder.clearCallingIdentity(); 3906 try { 3907 proc.thread.scheduleCrash(message); 3908 } catch (RemoteException e) { 3909 } 3910 Binder.restoreCallingIdentity(ident); 3911 } 3912 } 3913 } 3914 3915 @Override 3916 public final void finishSubActivity(IBinder token, String resultWho, 3917 int requestCode) { 3918 synchronized(this) { 3919 final long origId = Binder.clearCallingIdentity(); 3920 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3921 if (r != null) { 3922 r.task.stack.finishSubActivityLocked(r, resultWho, requestCode); 3923 } 3924 Binder.restoreCallingIdentity(origId); 3925 } 3926 } 3927 3928 @Override 3929 public boolean finishActivityAffinity(IBinder token) { 3930 synchronized(this) { 3931 final long origId = Binder.clearCallingIdentity(); 3932 try { 3933 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3934 3935 ActivityRecord rootR = r.task.getRootActivity(); 3936 // Do not allow task to finish in Lock Task mode. 3937 if (r.task == mStackSupervisor.mLockTaskModeTask) { 3938 if (rootR == r) { 3939 mStackSupervisor.showLockTaskToast(); 3940 return false; 3941 } 3942 } 3943 boolean res = false; 3944 if (r != null) { 3945 res = r.task.stack.finishActivityAffinityLocked(r); 3946 } 3947 return res; 3948 } finally { 3949 Binder.restoreCallingIdentity(origId); 3950 } 3951 } 3952 } 3953 3954 @Override 3955 public void finishVoiceTask(IVoiceInteractionSession session) { 3956 synchronized(this) { 3957 final long origId = Binder.clearCallingIdentity(); 3958 try { 3959 mStackSupervisor.finishVoiceTask(session); 3960 } finally { 3961 Binder.restoreCallingIdentity(origId); 3962 } 3963 } 3964 3965 } 3966 3967 @Override 3968 public boolean willActivityBeVisible(IBinder token) { 3969 synchronized(this) { 3970 ActivityStack stack = ActivityRecord.getStackLocked(token); 3971 if (stack != null) { 3972 return stack.willActivityBeVisibleLocked(token); 3973 } 3974 return false; 3975 } 3976 } 3977 3978 @Override 3979 public void overridePendingTransition(IBinder token, String packageName, 3980 int enterAnim, int exitAnim) { 3981 synchronized(this) { 3982 ActivityRecord self = ActivityRecord.isInStackLocked(token); 3983 if (self == null) { 3984 return; 3985 } 3986 3987 final long origId = Binder.clearCallingIdentity(); 3988 3989 if (self.state == ActivityState.RESUMED 3990 || self.state == ActivityState.PAUSING) { 3991 mWindowManager.overridePendingAppTransition(packageName, 3992 enterAnim, exitAnim, null); 3993 } 3994 3995 Binder.restoreCallingIdentity(origId); 3996 } 3997 } 3998 3999 /** 4000 * Main function for removing an existing process from the activity manager 4001 * as a result of that process going away. Clears out all connections 4002 * to the process. 4003 */ 4004 private final void handleAppDiedLocked(ProcessRecord app, 4005 boolean restarting, boolean allowRestart) { 4006 int pid = app.pid; 4007 cleanUpApplicationRecordLocked(app, restarting, allowRestart, -1); 4008 if (!restarting) { 4009 removeLruProcessLocked(app); 4010 if (pid > 0) { 4011 ProcessList.remove(pid); 4012 } 4013 } 4014 4015 if (mProfileProc == app) { 4016 clearProfilerLocked(); 4017 } 4018 4019 // Remove this application's activities from active lists. 4020 boolean hasVisibleActivities = mStackSupervisor.handleAppDiedLocked(app); 4021 4022 app.activities.clear(); 4023 4024 if (app.instrumentationClass != null) { 4025 Slog.w(TAG, "Crash of app " + app.processName 4026 + " running instrumentation " + app.instrumentationClass); 4027 Bundle info = new Bundle(); 4028 info.putString("shortMsg", "Process crashed."); 4029 finishInstrumentationLocked(app, Activity.RESULT_CANCELED, info); 4030 } 4031 4032 if (!restarting) { 4033 if (!mStackSupervisor.resumeTopActivitiesLocked()) { 4034 // If there was nothing to resume, and we are not already 4035 // restarting this process, but there is a visible activity that 4036 // is hosted by the process... then make sure all visible 4037 // activities are running, taking care of restarting this 4038 // process. 4039 if (hasVisibleActivities) { 4040 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 4041 } 4042 } 4043 } 4044 } 4045 4046 private final int getLRURecordIndexForAppLocked(IApplicationThread thread) { 4047 IBinder threadBinder = thread.asBinder(); 4048 // Find the application record. 4049 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4050 ProcessRecord rec = mLruProcesses.get(i); 4051 if (rec.thread != null && rec.thread.asBinder() == threadBinder) { 4052 return i; 4053 } 4054 } 4055 return -1; 4056 } 4057 4058 final ProcessRecord getRecordForAppLocked( 4059 IApplicationThread thread) { 4060 if (thread == null) { 4061 return null; 4062 } 4063 4064 int appIndex = getLRURecordIndexForAppLocked(thread); 4065 return appIndex >= 0 ? mLruProcesses.get(appIndex) : null; 4066 } 4067 4068 final void doLowMemReportIfNeededLocked(ProcessRecord dyingProc) { 4069 // If there are no longer any background processes running, 4070 // and the app that died was not running instrumentation, 4071 // then tell everyone we are now low on memory. 4072 boolean haveBg = false; 4073 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4074 ProcessRecord rec = mLruProcesses.get(i); 4075 if (rec.thread != null 4076 && rec.setProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 4077 haveBg = true; 4078 break; 4079 } 4080 } 4081 4082 if (!haveBg) { 4083 boolean doReport = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 4084 if (doReport) { 4085 long now = SystemClock.uptimeMillis(); 4086 if (now < (mLastMemUsageReportTime+5*60*1000)) { 4087 doReport = false; 4088 } else { 4089 mLastMemUsageReportTime = now; 4090 } 4091 } 4092 final ArrayList<ProcessMemInfo> memInfos 4093 = doReport ? new ArrayList<ProcessMemInfo>(mLruProcesses.size()) : null; 4094 EventLog.writeEvent(EventLogTags.AM_LOW_MEMORY, mLruProcesses.size()); 4095 long now = SystemClock.uptimeMillis(); 4096 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4097 ProcessRecord rec = mLruProcesses.get(i); 4098 if (rec == dyingProc || rec.thread == null) { 4099 continue; 4100 } 4101 if (doReport) { 4102 memInfos.add(new ProcessMemInfo(rec.processName, rec.pid, rec.setAdj, 4103 rec.setProcState, rec.adjType, rec.makeAdjReason())); 4104 } 4105 if ((rec.lastLowMemory+GC_MIN_INTERVAL) <= now) { 4106 // The low memory report is overriding any current 4107 // state for a GC request. Make sure to do 4108 // heavy/important/visible/foreground processes first. 4109 if (rec.setAdj <= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 4110 rec.lastRequestedGc = 0; 4111 } else { 4112 rec.lastRequestedGc = rec.lastLowMemory; 4113 } 4114 rec.reportLowMemory = true; 4115 rec.lastLowMemory = now; 4116 mProcessesToGc.remove(rec); 4117 addProcessToGcListLocked(rec); 4118 } 4119 } 4120 if (doReport) { 4121 Message msg = mHandler.obtainMessage(REPORT_MEM_USAGE_MSG, memInfos); 4122 mHandler.sendMessage(msg); 4123 } 4124 scheduleAppGcsLocked(); 4125 } 4126 } 4127 4128 final void appDiedLocked(ProcessRecord app, int pid, 4129 IApplicationThread thread) { 4130 4131 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 4132 synchronized (stats) { 4133 stats.noteProcessDiedLocked(app.info.uid, pid); 4134 } 4135 4136 Process.killProcessGroup(app.info.uid, pid); 4137 4138 // Clean up already done if the process has been re-started. 4139 if (app.pid == pid && app.thread != null && 4140 app.thread.asBinder() == thread.asBinder()) { 4141 boolean doLowMem = app.instrumentationClass == null; 4142 boolean doOomAdj = doLowMem; 4143 if (!app.killedByAm) { 4144 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4145 + ") has died."); 4146 mAllowLowerMemLevel = true; 4147 } else { 4148 // Note that we always want to do oom adj to update our state with the 4149 // new number of procs. 4150 mAllowLowerMemLevel = false; 4151 doLowMem = false; 4152 } 4153 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4154 if (DEBUG_CLEANUP) Slog.v( 4155 TAG, "Dying app: " + app + ", pid: " + pid 4156 + ", thread: " + thread.asBinder()); 4157 handleAppDiedLocked(app, false, true); 4158 4159 if (doOomAdj) { 4160 updateOomAdjLocked(); 4161 } 4162 if (doLowMem) { 4163 doLowMemReportIfNeededLocked(app); 4164 } 4165 } else if (app.pid != pid) { 4166 // A new process has already been started. 4167 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4168 + ") has died and restarted (pid " + app.pid + ")."); 4169 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4170 } else if (DEBUG_PROCESSES) { 4171 Slog.d(TAG, "Received spurious death notification for thread " 4172 + thread.asBinder()); 4173 } 4174 } 4175 4176 /** 4177 * If a stack trace dump file is configured, dump process stack traces. 4178 * @param clearTraces causes the dump file to be erased prior to the new 4179 * traces being written, if true; when false, the new traces will be 4180 * appended to any existing file content. 4181 * @param firstPids of dalvik VM processes to dump stack traces for first 4182 * @param lastPids of dalvik VM processes to dump stack traces for last 4183 * @param nativeProcs optional list of native process names to dump stack crawls 4184 * @return file containing stack traces, or null if no dump file is configured 4185 */ 4186 public static File dumpStackTraces(boolean clearTraces, ArrayList<Integer> firstPids, 4187 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4188 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4189 if (tracesPath == null || tracesPath.length() == 0) { 4190 return null; 4191 } 4192 4193 File tracesFile = new File(tracesPath); 4194 try { 4195 File tracesDir = tracesFile.getParentFile(); 4196 if (!tracesDir.exists()) { 4197 tracesFile.mkdirs(); 4198 if (!SELinux.restorecon(tracesDir)) { 4199 return null; 4200 } 4201 } 4202 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4203 4204 if (clearTraces && tracesFile.exists()) tracesFile.delete(); 4205 tracesFile.createNewFile(); 4206 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4207 } catch (IOException e) { 4208 Slog.w(TAG, "Unable to prepare ANR traces file: " + tracesPath, e); 4209 return null; 4210 } 4211 4212 dumpStackTraces(tracesPath, firstPids, processCpuTracker, lastPids, nativeProcs); 4213 return tracesFile; 4214 } 4215 4216 private static void dumpStackTraces(String tracesPath, ArrayList<Integer> firstPids, 4217 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4218 // Use a FileObserver to detect when traces finish writing. 4219 // The order of traces is considered important to maintain for legibility. 4220 FileObserver observer = new FileObserver(tracesPath, FileObserver.CLOSE_WRITE) { 4221 @Override 4222 public synchronized void onEvent(int event, String path) { notify(); } 4223 }; 4224 4225 try { 4226 observer.startWatching(); 4227 4228 // First collect all of the stacks of the most important pids. 4229 if (firstPids != null) { 4230 try { 4231 int num = firstPids.size(); 4232 for (int i = 0; i < num; i++) { 4233 synchronized (observer) { 4234 Process.sendSignal(firstPids.get(i), Process.SIGNAL_QUIT); 4235 observer.wait(200); // Wait for write-close, give up after 200msec 4236 } 4237 } 4238 } catch (InterruptedException e) { 4239 Log.wtf(TAG, e); 4240 } 4241 } 4242 4243 // Next collect the stacks of the native pids 4244 if (nativeProcs != null) { 4245 int[] pids = Process.getPidsForCommands(nativeProcs); 4246 if (pids != null) { 4247 for (int pid : pids) { 4248 Debug.dumpNativeBacktraceToFile(pid, tracesPath); 4249 } 4250 } 4251 } 4252 4253 // Lastly, measure CPU usage. 4254 if (processCpuTracker != null) { 4255 processCpuTracker.init(); 4256 System.gc(); 4257 processCpuTracker.update(); 4258 try { 4259 synchronized (processCpuTracker) { 4260 processCpuTracker.wait(500); // measure over 1/2 second. 4261 } 4262 } catch (InterruptedException e) { 4263 } 4264 processCpuTracker.update(); 4265 4266 // We'll take the stack crawls of just the top apps using CPU. 4267 final int N = processCpuTracker.countWorkingStats(); 4268 int numProcs = 0; 4269 for (int i=0; i<N && numProcs<5; i++) { 4270 ProcessCpuTracker.Stats stats = processCpuTracker.getWorkingStats(i); 4271 if (lastPids.indexOfKey(stats.pid) >= 0) { 4272 numProcs++; 4273 try { 4274 synchronized (observer) { 4275 Process.sendSignal(stats.pid, Process.SIGNAL_QUIT); 4276 observer.wait(200); // Wait for write-close, give up after 200msec 4277 } 4278 } catch (InterruptedException e) { 4279 Log.wtf(TAG, e); 4280 } 4281 4282 } 4283 } 4284 } 4285 } finally { 4286 observer.stopWatching(); 4287 } 4288 } 4289 4290 final void logAppTooSlow(ProcessRecord app, long startTime, String msg) { 4291 if (true || IS_USER_BUILD) { 4292 return; 4293 } 4294 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4295 if (tracesPath == null || tracesPath.length() == 0) { 4296 return; 4297 } 4298 4299 StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads(); 4300 StrictMode.allowThreadDiskWrites(); 4301 try { 4302 final File tracesFile = new File(tracesPath); 4303 final File tracesDir = tracesFile.getParentFile(); 4304 final File tracesTmp = new File(tracesDir, "__tmp__"); 4305 try { 4306 if (!tracesDir.exists()) { 4307 tracesFile.mkdirs(); 4308 if (!SELinux.restorecon(tracesDir.getPath())) { 4309 return; 4310 } 4311 } 4312 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4313 4314 if (tracesFile.exists()) { 4315 tracesTmp.delete(); 4316 tracesFile.renameTo(tracesTmp); 4317 } 4318 StringBuilder sb = new StringBuilder(); 4319 Time tobj = new Time(); 4320 tobj.set(System.currentTimeMillis()); 4321 sb.append(tobj.format("%Y-%m-%d %H:%M:%S")); 4322 sb.append(": "); 4323 TimeUtils.formatDuration(SystemClock.uptimeMillis()-startTime, sb); 4324 sb.append(" since "); 4325 sb.append(msg); 4326 FileOutputStream fos = new FileOutputStream(tracesFile); 4327 fos.write(sb.toString().getBytes()); 4328 if (app == null) { 4329 fos.write("\n*** No application process!".getBytes()); 4330 } 4331 fos.close(); 4332 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4333 } catch (IOException e) { 4334 Slog.w(TAG, "Unable to prepare slow app traces file: " + tracesPath, e); 4335 return; 4336 } 4337 4338 if (app != null) { 4339 ArrayList<Integer> firstPids = new ArrayList<Integer>(); 4340 firstPids.add(app.pid); 4341 dumpStackTraces(tracesPath, firstPids, null, null, null); 4342 } 4343 4344 File lastTracesFile = null; 4345 File curTracesFile = null; 4346 for (int i=9; i>=0; i--) { 4347 String name = String.format(Locale.US, "slow%02d.txt", i); 4348 curTracesFile = new File(tracesDir, name); 4349 if (curTracesFile.exists()) { 4350 if (lastTracesFile != null) { 4351 curTracesFile.renameTo(lastTracesFile); 4352 } else { 4353 curTracesFile.delete(); 4354 } 4355 } 4356 lastTracesFile = curTracesFile; 4357 } 4358 tracesFile.renameTo(curTracesFile); 4359 if (tracesTmp.exists()) { 4360 tracesTmp.renameTo(tracesFile); 4361 } 4362 } finally { 4363 StrictMode.setThreadPolicy(oldPolicy); 4364 } 4365 } 4366 4367 final void appNotResponding(ProcessRecord app, ActivityRecord activity, 4368 ActivityRecord parent, boolean aboveSystem, final String annotation) { 4369 ArrayList<Integer> firstPids = new ArrayList<Integer>(5); 4370 SparseArray<Boolean> lastPids = new SparseArray<Boolean>(20); 4371 4372 if (mController != null) { 4373 try { 4374 // 0 == continue, -1 = kill process immediately 4375 int res = mController.appEarlyNotResponding(app.processName, app.pid, annotation); 4376 if (res < 0 && app.pid != MY_PID) { 4377 Process.killProcess(app.pid); 4378 Process.killProcessGroup(app.info.uid, app.pid); 4379 } 4380 } catch (RemoteException e) { 4381 mController = null; 4382 Watchdog.getInstance().setActivityController(null); 4383 } 4384 } 4385 4386 long anrTime = SystemClock.uptimeMillis(); 4387 if (MONITOR_CPU_USAGE) { 4388 updateCpuStatsNow(); 4389 } 4390 4391 synchronized (this) { 4392 // PowerManager.reboot() can block for a long time, so ignore ANRs while shutting down. 4393 if (mShuttingDown) { 4394 Slog.i(TAG, "During shutdown skipping ANR: " + app + " " + annotation); 4395 return; 4396 } else if (app.notResponding) { 4397 Slog.i(TAG, "Skipping duplicate ANR: " + app + " " + annotation); 4398 return; 4399 } else if (app.crashing) { 4400 Slog.i(TAG, "Crashing app skipping ANR: " + app + " " + annotation); 4401 return; 4402 } 4403 4404 // In case we come through here for the same app before completing 4405 // this one, mark as anring now so we will bail out. 4406 app.notResponding = true; 4407 4408 // Log the ANR to the event log. 4409 EventLog.writeEvent(EventLogTags.AM_ANR, app.userId, app.pid, 4410 app.processName, app.info.flags, annotation); 4411 4412 // Dump thread traces as quickly as we can, starting with "interesting" processes. 4413 firstPids.add(app.pid); 4414 4415 int parentPid = app.pid; 4416 if (parent != null && parent.app != null && parent.app.pid > 0) parentPid = parent.app.pid; 4417 if (parentPid != app.pid) firstPids.add(parentPid); 4418 4419 if (MY_PID != app.pid && MY_PID != parentPid) firstPids.add(MY_PID); 4420 4421 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 4422 ProcessRecord r = mLruProcesses.get(i); 4423 if (r != null && r.thread != null) { 4424 int pid = r.pid; 4425 if (pid > 0 && pid != app.pid && pid != parentPid && pid != MY_PID) { 4426 if (r.persistent) { 4427 firstPids.add(pid); 4428 } else { 4429 lastPids.put(pid, Boolean.TRUE); 4430 } 4431 } 4432 } 4433 } 4434 } 4435 4436 // Log the ANR to the main log. 4437 StringBuilder info = new StringBuilder(); 4438 info.setLength(0); 4439 info.append("ANR in ").append(app.processName); 4440 if (activity != null && activity.shortComponentName != null) { 4441 info.append(" (").append(activity.shortComponentName).append(")"); 4442 } 4443 info.append("\n"); 4444 info.append("PID: ").append(app.pid).append("\n"); 4445 if (annotation != null) { 4446 info.append("Reason: ").append(annotation).append("\n"); 4447 } 4448 if (parent != null && parent != activity) { 4449 info.append("Parent: ").append(parent.shortComponentName).append("\n"); 4450 } 4451 4452 final ProcessCpuTracker processCpuTracker = new ProcessCpuTracker(true); 4453 4454 File tracesFile = dumpStackTraces(true, firstPids, processCpuTracker, lastPids, 4455 NATIVE_STACKS_OF_INTEREST); 4456 4457 String cpuInfo = null; 4458 if (MONITOR_CPU_USAGE) { 4459 updateCpuStatsNow(); 4460 synchronized (mProcessCpuThread) { 4461 cpuInfo = mProcessCpuTracker.printCurrentState(anrTime); 4462 } 4463 info.append(processCpuTracker.printCurrentLoad()); 4464 info.append(cpuInfo); 4465 } 4466 4467 info.append(processCpuTracker.printCurrentState(anrTime)); 4468 4469 Slog.e(TAG, info.toString()); 4470 if (tracesFile == null) { 4471 // There is no trace file, so dump (only) the alleged culprit's threads to the log 4472 Process.sendSignal(app.pid, Process.SIGNAL_QUIT); 4473 } 4474 4475 addErrorToDropBox("anr", app, app.processName, activity, parent, annotation, 4476 cpuInfo, tracesFile, null); 4477 4478 if (mController != null) { 4479 try { 4480 // 0 == show dialog, 1 = keep waiting, -1 = kill process immediately 4481 int res = mController.appNotResponding(app.processName, app.pid, info.toString()); 4482 if (res != 0) { 4483 if (res < 0 && app.pid != MY_PID) { 4484 Process.killProcess(app.pid); 4485 Process.killProcessGroup(app.info.uid, app.pid); 4486 } else { 4487 synchronized (this) { 4488 mServices.scheduleServiceTimeoutLocked(app); 4489 } 4490 } 4491 return; 4492 } 4493 } catch (RemoteException e) { 4494 mController = null; 4495 Watchdog.getInstance().setActivityController(null); 4496 } 4497 } 4498 4499 // Unless configured otherwise, swallow ANRs in background processes & kill the process. 4500 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 4501 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 4502 4503 synchronized (this) { 4504 if (!showBackground && !app.isInterestingToUserLocked() && app.pid != MY_PID) { 4505 killUnneededProcessLocked(app, "background ANR"); 4506 return; 4507 } 4508 4509 // Set the app's notResponding state, and look up the errorReportReceiver 4510 makeAppNotRespondingLocked(app, 4511 activity != null ? activity.shortComponentName : null, 4512 annotation != null ? "ANR " + annotation : "ANR", 4513 info.toString()); 4514 4515 // Bring up the infamous App Not Responding dialog 4516 Message msg = Message.obtain(); 4517 HashMap<String, Object> map = new HashMap<String, Object>(); 4518 msg.what = SHOW_NOT_RESPONDING_MSG; 4519 msg.obj = map; 4520 msg.arg1 = aboveSystem ? 1 : 0; 4521 map.put("app", app); 4522 if (activity != null) { 4523 map.put("activity", activity); 4524 } 4525 4526 mHandler.sendMessage(msg); 4527 } 4528 } 4529 4530 final void showLaunchWarningLocked(final ActivityRecord cur, final ActivityRecord next) { 4531 if (!mLaunchWarningShown) { 4532 mLaunchWarningShown = true; 4533 mHandler.post(new Runnable() { 4534 @Override 4535 public void run() { 4536 synchronized (ActivityManagerService.this) { 4537 final Dialog d = new LaunchWarningWindow(mContext, cur, next); 4538 d.show(); 4539 mHandler.postDelayed(new Runnable() { 4540 @Override 4541 public void run() { 4542 synchronized (ActivityManagerService.this) { 4543 d.dismiss(); 4544 mLaunchWarningShown = false; 4545 } 4546 } 4547 }, 4000); 4548 } 4549 } 4550 }); 4551 } 4552 } 4553 4554 @Override 4555 public boolean clearApplicationUserData(final String packageName, 4556 final IPackageDataObserver observer, int userId) { 4557 enforceNotIsolatedCaller("clearApplicationUserData"); 4558 int uid = Binder.getCallingUid(); 4559 int pid = Binder.getCallingPid(); 4560 userId = handleIncomingUser(pid, uid, 4561 userId, false, ALLOW_FULL_ONLY, "clearApplicationUserData", null); 4562 long callingId = Binder.clearCallingIdentity(); 4563 try { 4564 IPackageManager pm = AppGlobals.getPackageManager(); 4565 int pkgUid = -1; 4566 synchronized(this) { 4567 try { 4568 pkgUid = pm.getPackageUid(packageName, userId); 4569 } catch (RemoteException e) { 4570 } 4571 if (pkgUid == -1) { 4572 Slog.w(TAG, "Invalid packageName: " + packageName); 4573 if (observer != null) { 4574 try { 4575 observer.onRemoveCompleted(packageName, false); 4576 } catch (RemoteException e) { 4577 Slog.i(TAG, "Observer no longer exists."); 4578 } 4579 } 4580 return false; 4581 } 4582 if (uid == pkgUid || checkComponentPermission( 4583 android.Manifest.permission.CLEAR_APP_USER_DATA, 4584 pid, uid, -1, true) 4585 == PackageManager.PERMISSION_GRANTED) { 4586 forceStopPackageLocked(packageName, pkgUid, "clear data"); 4587 } else { 4588 throw new SecurityException("PID " + pid + " does not have permission " 4589 + android.Manifest.permission.CLEAR_APP_USER_DATA + " to clear data" 4590 + " of package " + packageName); 4591 } 4592 } 4593 4594 try { 4595 // Clear application user data 4596 pm.clearApplicationUserData(packageName, observer, userId); 4597 4598 // Remove all permissions granted from/to this package 4599 removeUriPermissionsForPackageLocked(packageName, userId, true); 4600 4601 Intent intent = new Intent(Intent.ACTION_PACKAGE_DATA_CLEARED, 4602 Uri.fromParts("package", packageName, null)); 4603 intent.putExtra(Intent.EXTRA_UID, pkgUid); 4604 broadcastIntentInPackage("android", Process.SYSTEM_UID, intent, 4605 null, null, 0, null, null, null, false, false, userId); 4606 } catch (RemoteException e) { 4607 } 4608 } finally { 4609 Binder.restoreCallingIdentity(callingId); 4610 } 4611 return true; 4612 } 4613 4614 @Override 4615 public void killBackgroundProcesses(final String packageName, int userId) { 4616 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 4617 != PackageManager.PERMISSION_GRANTED && 4618 checkCallingPermission(android.Manifest.permission.RESTART_PACKAGES) 4619 != PackageManager.PERMISSION_GRANTED) { 4620 String msg = "Permission Denial: killBackgroundProcesses() from pid=" 4621 + Binder.getCallingPid() 4622 + ", uid=" + Binder.getCallingUid() 4623 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 4624 Slog.w(TAG, msg); 4625 throw new SecurityException(msg); 4626 } 4627 4628 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4629 userId, true, ALLOW_FULL_ONLY, "killBackgroundProcesses", null); 4630 long callingId = Binder.clearCallingIdentity(); 4631 try { 4632 IPackageManager pm = AppGlobals.getPackageManager(); 4633 synchronized(this) { 4634 int appId = -1; 4635 try { 4636 appId = UserHandle.getAppId(pm.getPackageUid(packageName, 0)); 4637 } catch (RemoteException e) { 4638 } 4639 if (appId == -1) { 4640 Slog.w(TAG, "Invalid packageName: " + packageName); 4641 return; 4642 } 4643 killPackageProcessesLocked(packageName, appId, userId, 4644 ProcessList.SERVICE_ADJ, false, true, true, false, "kill background"); 4645 } 4646 } finally { 4647 Binder.restoreCallingIdentity(callingId); 4648 } 4649 } 4650 4651 @Override 4652 public void killAllBackgroundProcesses() { 4653 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 4654 != PackageManager.PERMISSION_GRANTED) { 4655 String msg = "Permission Denial: killAllBackgroundProcesses() from pid=" 4656 + Binder.getCallingPid() 4657 + ", uid=" + Binder.getCallingUid() 4658 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 4659 Slog.w(TAG, msg); 4660 throw new SecurityException(msg); 4661 } 4662 4663 long callingId = Binder.clearCallingIdentity(); 4664 try { 4665 synchronized(this) { 4666 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 4667 final int NP = mProcessNames.getMap().size(); 4668 for (int ip=0; ip<NP; ip++) { 4669 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 4670 final int NA = apps.size(); 4671 for (int ia=0; ia<NA; ia++) { 4672 ProcessRecord app = apps.valueAt(ia); 4673 if (app.persistent) { 4674 // we don't kill persistent processes 4675 continue; 4676 } 4677 if (app.removed) { 4678 procs.add(app); 4679 } else if (app.setAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 4680 app.removed = true; 4681 procs.add(app); 4682 } 4683 } 4684 } 4685 4686 int N = procs.size(); 4687 for (int i=0; i<N; i++) { 4688 removeProcessLocked(procs.get(i), false, true, "kill all background"); 4689 } 4690 mAllowLowerMemLevel = true; 4691 updateOomAdjLocked(); 4692 doLowMemReportIfNeededLocked(null); 4693 } 4694 } finally { 4695 Binder.restoreCallingIdentity(callingId); 4696 } 4697 } 4698 4699 @Override 4700 public void forceStopPackage(final String packageName, int userId) { 4701 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4702 != PackageManager.PERMISSION_GRANTED) { 4703 String msg = "Permission Denial: forceStopPackage() from pid=" 4704 + Binder.getCallingPid() 4705 + ", uid=" + Binder.getCallingUid() 4706 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4707 Slog.w(TAG, msg); 4708 throw new SecurityException(msg); 4709 } 4710 final int callingPid = Binder.getCallingPid(); 4711 userId = handleIncomingUser(callingPid, Binder.getCallingUid(), 4712 userId, true, ALLOW_FULL_ONLY, "forceStopPackage", null); 4713 long callingId = Binder.clearCallingIdentity(); 4714 try { 4715 IPackageManager pm = AppGlobals.getPackageManager(); 4716 synchronized(this) { 4717 int[] users = userId == UserHandle.USER_ALL 4718 ? getUsersLocked() : new int[] { userId }; 4719 for (int user : users) { 4720 int pkgUid = -1; 4721 try { 4722 pkgUid = pm.getPackageUid(packageName, user); 4723 } catch (RemoteException e) { 4724 } 4725 if (pkgUid == -1) { 4726 Slog.w(TAG, "Invalid packageName: " + packageName); 4727 continue; 4728 } 4729 try { 4730 pm.setPackageStoppedState(packageName, true, user); 4731 } catch (RemoteException e) { 4732 } catch (IllegalArgumentException e) { 4733 Slog.w(TAG, "Failed trying to unstop package " 4734 + packageName + ": " + e); 4735 } 4736 if (isUserRunningLocked(user, false)) { 4737 forceStopPackageLocked(packageName, pkgUid, "from pid " + callingPid); 4738 } 4739 } 4740 } 4741 } finally { 4742 Binder.restoreCallingIdentity(callingId); 4743 } 4744 } 4745 4746 @Override 4747 public void addPackageDependency(String packageName) { 4748 synchronized (this) { 4749 int callingPid = Binder.getCallingPid(); 4750 if (callingPid == Process.myPid()) { 4751 // Yeah, um, no. 4752 Slog.w(TAG, "Can't addPackageDependency on system process"); 4753 return; 4754 } 4755 ProcessRecord proc; 4756 synchronized (mPidsSelfLocked) { 4757 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 4758 } 4759 if (proc != null) { 4760 if (proc.pkgDeps == null) { 4761 proc.pkgDeps = new ArraySet<String>(1); 4762 } 4763 proc.pkgDeps.add(packageName); 4764 } 4765 } 4766 } 4767 4768 /* 4769 * The pkg name and app id have to be specified. 4770 */ 4771 @Override 4772 public void killApplicationWithAppId(String pkg, int appid, String reason) { 4773 if (pkg == null) { 4774 return; 4775 } 4776 // Make sure the uid is valid. 4777 if (appid < 0) { 4778 Slog.w(TAG, "Invalid appid specified for pkg : " + pkg); 4779 return; 4780 } 4781 int callerUid = Binder.getCallingUid(); 4782 // Only the system server can kill an application 4783 if (callerUid == Process.SYSTEM_UID) { 4784 // Post an aysnc message to kill the application 4785 Message msg = mHandler.obtainMessage(KILL_APPLICATION_MSG); 4786 msg.arg1 = appid; 4787 msg.arg2 = 0; 4788 Bundle bundle = new Bundle(); 4789 bundle.putString("pkg", pkg); 4790 bundle.putString("reason", reason); 4791 msg.obj = bundle; 4792 mHandler.sendMessage(msg); 4793 } else { 4794 throw new SecurityException(callerUid + " cannot kill pkg: " + 4795 pkg); 4796 } 4797 } 4798 4799 @Override 4800 public void closeSystemDialogs(String reason) { 4801 enforceNotIsolatedCaller("closeSystemDialogs"); 4802 4803 final int pid = Binder.getCallingPid(); 4804 final int uid = Binder.getCallingUid(); 4805 final long origId = Binder.clearCallingIdentity(); 4806 try { 4807 synchronized (this) { 4808 // Only allow this from foreground processes, so that background 4809 // applications can't abuse it to prevent system UI from being shown. 4810 if (uid >= Process.FIRST_APPLICATION_UID) { 4811 ProcessRecord proc; 4812 synchronized (mPidsSelfLocked) { 4813 proc = mPidsSelfLocked.get(pid); 4814 } 4815 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 4816 Slog.w(TAG, "Ignoring closeSystemDialogs " + reason 4817 + " from background process " + proc); 4818 return; 4819 } 4820 } 4821 closeSystemDialogsLocked(reason); 4822 } 4823 } finally { 4824 Binder.restoreCallingIdentity(origId); 4825 } 4826 } 4827 4828 void closeSystemDialogsLocked(String reason) { 4829 Intent intent = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS); 4830 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4831 | Intent.FLAG_RECEIVER_FOREGROUND); 4832 if (reason != null) { 4833 intent.putExtra("reason", reason); 4834 } 4835 mWindowManager.closeSystemDialogs(reason); 4836 4837 mStackSupervisor.closeSystemDialogsLocked(); 4838 4839 broadcastIntentLocked(null, null, intent, null, 4840 null, 0, null, null, null, AppOpsManager.OP_NONE, false, false, -1, 4841 Process.SYSTEM_UID, UserHandle.USER_ALL); 4842 } 4843 4844 @Override 4845 public Debug.MemoryInfo[] getProcessMemoryInfo(int[] pids) { 4846 enforceNotIsolatedCaller("getProcessMemoryInfo"); 4847 Debug.MemoryInfo[] infos = new Debug.MemoryInfo[pids.length]; 4848 for (int i=pids.length-1; i>=0; i--) { 4849 ProcessRecord proc; 4850 int oomAdj; 4851 synchronized (this) { 4852 synchronized (mPidsSelfLocked) { 4853 proc = mPidsSelfLocked.get(pids[i]); 4854 oomAdj = proc != null ? proc.setAdj : 0; 4855 } 4856 } 4857 infos[i] = new Debug.MemoryInfo(); 4858 Debug.getMemoryInfo(pids[i], infos[i]); 4859 if (proc != null) { 4860 synchronized (this) { 4861 if (proc.thread != null && proc.setAdj == oomAdj) { 4862 // Record this for posterity if the process has been stable. 4863 proc.baseProcessTracker.addPss(infos[i].getTotalPss(), 4864 infos[i].getTotalUss(), false, proc.pkgList); 4865 } 4866 } 4867 } 4868 } 4869 return infos; 4870 } 4871 4872 @Override 4873 public long[] getProcessPss(int[] pids) { 4874 enforceNotIsolatedCaller("getProcessPss"); 4875 long[] pss = new long[pids.length]; 4876 for (int i=pids.length-1; i>=0; i--) { 4877 ProcessRecord proc; 4878 int oomAdj; 4879 synchronized (this) { 4880 synchronized (mPidsSelfLocked) { 4881 proc = mPidsSelfLocked.get(pids[i]); 4882 oomAdj = proc != null ? proc.setAdj : 0; 4883 } 4884 } 4885 long[] tmpUss = new long[1]; 4886 pss[i] = Debug.getPss(pids[i], tmpUss); 4887 if (proc != null) { 4888 synchronized (this) { 4889 if (proc.thread != null && proc.setAdj == oomAdj) { 4890 // Record this for posterity if the process has been stable. 4891 proc.baseProcessTracker.addPss(pss[i], tmpUss[0], false, proc.pkgList); 4892 } 4893 } 4894 } 4895 } 4896 return pss; 4897 } 4898 4899 @Override 4900 public void killApplicationProcess(String processName, int uid) { 4901 if (processName == null) { 4902 return; 4903 } 4904 4905 int callerUid = Binder.getCallingUid(); 4906 // Only the system server can kill an application 4907 if (callerUid == Process.SYSTEM_UID) { 4908 synchronized (this) { 4909 ProcessRecord app = getProcessRecordLocked(processName, uid, true); 4910 if (app != null && app.thread != null) { 4911 try { 4912 app.thread.scheduleSuicide(); 4913 } catch (RemoteException e) { 4914 // If the other end already died, then our work here is done. 4915 } 4916 } else { 4917 Slog.w(TAG, "Process/uid not found attempting kill of " 4918 + processName + " / " + uid); 4919 } 4920 } 4921 } else { 4922 throw new SecurityException(callerUid + " cannot kill app process: " + 4923 processName); 4924 } 4925 } 4926 4927 private void forceStopPackageLocked(final String packageName, int uid, String reason) { 4928 forceStopPackageLocked(packageName, UserHandle.getAppId(uid), false, 4929 false, true, false, false, UserHandle.getUserId(uid), reason); 4930 Intent intent = new Intent(Intent.ACTION_PACKAGE_RESTARTED, 4931 Uri.fromParts("package", packageName, null)); 4932 if (!mProcessesReady) { 4933 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4934 | Intent.FLAG_RECEIVER_FOREGROUND); 4935 } 4936 intent.putExtra(Intent.EXTRA_UID, uid); 4937 intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(uid)); 4938 broadcastIntentLocked(null, null, intent, 4939 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 4940 false, false, 4941 MY_PID, Process.SYSTEM_UID, UserHandle.getUserId(uid)); 4942 } 4943 4944 private void forceStopUserLocked(int userId, String reason) { 4945 forceStopPackageLocked(null, -1, false, false, true, false, false, userId, reason); 4946 Intent intent = new Intent(Intent.ACTION_USER_STOPPED); 4947 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4948 | Intent.FLAG_RECEIVER_FOREGROUND); 4949 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 4950 broadcastIntentLocked(null, null, intent, 4951 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 4952 false, false, 4953 MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 4954 } 4955 4956 private final boolean killPackageProcessesLocked(String packageName, int appId, 4957 int userId, int minOomAdj, boolean callerWillRestart, boolean allowRestart, 4958 boolean doit, boolean evenPersistent, String reason) { 4959 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 4960 4961 // Remove all processes this package may have touched: all with the 4962 // same UID (except for the system or root user), and all whose name 4963 // matches the package name. 4964 final int NP = mProcessNames.getMap().size(); 4965 for (int ip=0; ip<NP; ip++) { 4966 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 4967 final int NA = apps.size(); 4968 for (int ia=0; ia<NA; ia++) { 4969 ProcessRecord app = apps.valueAt(ia); 4970 if (app.persistent && !evenPersistent) { 4971 // we don't kill persistent processes 4972 continue; 4973 } 4974 if (app.removed) { 4975 if (doit) { 4976 procs.add(app); 4977 } 4978 continue; 4979 } 4980 4981 // Skip process if it doesn't meet our oom adj requirement. 4982 if (app.setAdj < minOomAdj) { 4983 continue; 4984 } 4985 4986 // If no package is specified, we call all processes under the 4987 // give user id. 4988 if (packageName == null) { 4989 if (app.userId != userId) { 4990 continue; 4991 } 4992 if (appId >= 0 && UserHandle.getAppId(app.uid) != appId) { 4993 continue; 4994 } 4995 // Package has been specified, we want to hit all processes 4996 // that match it. We need to qualify this by the processes 4997 // that are running under the specified app and user ID. 4998 } else { 4999 final boolean isDep = app.pkgDeps != null 5000 && app.pkgDeps.contains(packageName); 5001 if (!isDep && UserHandle.getAppId(app.uid) != appId) { 5002 continue; 5003 } 5004 if (userId != UserHandle.USER_ALL && app.userId != userId) { 5005 continue; 5006 } 5007 if (!app.pkgList.containsKey(packageName) && !isDep) { 5008 continue; 5009 } 5010 } 5011 5012 // Process has passed all conditions, kill it! 5013 if (!doit) { 5014 return true; 5015 } 5016 app.removed = true; 5017 procs.add(app); 5018 } 5019 } 5020 5021 int N = procs.size(); 5022 for (int i=0; i<N; i++) { 5023 removeProcessLocked(procs.get(i), callerWillRestart, allowRestart, reason); 5024 } 5025 updateOomAdjLocked(); 5026 return N > 0; 5027 } 5028 5029 private final boolean forceStopPackageLocked(String name, int appId, 5030 boolean callerWillRestart, boolean purgeCache, boolean doit, 5031 boolean evenPersistent, boolean uninstalling, int userId, String reason) { 5032 int i; 5033 int N; 5034 5035 if (userId == UserHandle.USER_ALL && name == null) { 5036 Slog.w(TAG, "Can't force stop all processes of all users, that is insane!"); 5037 } 5038 5039 if (appId < 0 && name != null) { 5040 try { 5041 appId = UserHandle.getAppId( 5042 AppGlobals.getPackageManager().getPackageUid(name, 0)); 5043 } catch (RemoteException e) { 5044 } 5045 } 5046 5047 if (doit) { 5048 if (name != null) { 5049 Slog.i(TAG, "Force stopping " + name + " appid=" + appId 5050 + " user=" + userId + ": " + reason); 5051 } else { 5052 Slog.i(TAG, "Force stopping u" + userId + ": " + reason); 5053 } 5054 5055 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 5056 for (int ip=pmap.size()-1; ip>=0; ip--) { 5057 SparseArray<Long> ba = pmap.valueAt(ip); 5058 for (i=ba.size()-1; i>=0; i--) { 5059 boolean remove = false; 5060 final int entUid = ba.keyAt(i); 5061 if (name != null) { 5062 if (userId == UserHandle.USER_ALL) { 5063 if (UserHandle.getAppId(entUid) == appId) { 5064 remove = true; 5065 } 5066 } else { 5067 if (entUid == UserHandle.getUid(userId, appId)) { 5068 remove = true; 5069 } 5070 } 5071 } else if (UserHandle.getUserId(entUid) == userId) { 5072 remove = true; 5073 } 5074 if (remove) { 5075 ba.removeAt(i); 5076 } 5077 } 5078 if (ba.size() == 0) { 5079 pmap.removeAt(ip); 5080 } 5081 } 5082 } 5083 5084 boolean didSomething = killPackageProcessesLocked(name, appId, userId, 5085 -100, callerWillRestart, true, doit, evenPersistent, 5086 name == null ? ("stop user " + userId) : ("stop " + name)); 5087 5088 if (mStackSupervisor.forceStopPackageLocked(name, doit, evenPersistent, userId)) { 5089 if (!doit) { 5090 return true; 5091 } 5092 didSomething = true; 5093 } 5094 5095 if (mServices.forceStopLocked(name, userId, evenPersistent, doit)) { 5096 if (!doit) { 5097 return true; 5098 } 5099 didSomething = true; 5100 } 5101 5102 if (name == null) { 5103 // Remove all sticky broadcasts from this user. 5104 mStickyBroadcasts.remove(userId); 5105 } 5106 5107 ArrayList<ContentProviderRecord> providers = new ArrayList<ContentProviderRecord>(); 5108 if (mProviderMap.collectForceStopProviders(name, appId, doit, evenPersistent, 5109 userId, providers)) { 5110 if (!doit) { 5111 return true; 5112 } 5113 didSomething = true; 5114 } 5115 N = providers.size(); 5116 for (i=0; i<N; i++) { 5117 removeDyingProviderLocked(null, providers.get(i), true); 5118 } 5119 5120 // Remove transient permissions granted from/to this package/user 5121 removeUriPermissionsForPackageLocked(name, userId, false); 5122 5123 if (name == null || uninstalling) { 5124 // Remove pending intents. For now we only do this when force 5125 // stopping users, because we have some problems when doing this 5126 // for packages -- app widgets are not currently cleaned up for 5127 // such packages, so they can be left with bad pending intents. 5128 if (mIntentSenderRecords.size() > 0) { 5129 Iterator<WeakReference<PendingIntentRecord>> it 5130 = mIntentSenderRecords.values().iterator(); 5131 while (it.hasNext()) { 5132 WeakReference<PendingIntentRecord> wpir = it.next(); 5133 if (wpir == null) { 5134 it.remove(); 5135 continue; 5136 } 5137 PendingIntentRecord pir = wpir.get(); 5138 if (pir == null) { 5139 it.remove(); 5140 continue; 5141 } 5142 if (name == null) { 5143 // Stopping user, remove all objects for the user. 5144 if (pir.key.userId != userId) { 5145 // Not the same user, skip it. 5146 continue; 5147 } 5148 } else { 5149 if (UserHandle.getAppId(pir.uid) != appId) { 5150 // Different app id, skip it. 5151 continue; 5152 } 5153 if (userId != UserHandle.USER_ALL && pir.key.userId != userId) { 5154 // Different user, skip it. 5155 continue; 5156 } 5157 if (!pir.key.packageName.equals(name)) { 5158 // Different package, skip it. 5159 continue; 5160 } 5161 } 5162 if (!doit) { 5163 return true; 5164 } 5165 didSomething = true; 5166 it.remove(); 5167 pir.canceled = true; 5168 if (pir.key.activity != null) { 5169 pir.key.activity.pendingResults.remove(pir.ref); 5170 } 5171 } 5172 } 5173 } 5174 5175 if (doit) { 5176 if (purgeCache && name != null) { 5177 AttributeCache ac = AttributeCache.instance(); 5178 if (ac != null) { 5179 ac.removePackage(name); 5180 } 5181 } 5182 if (mBooted) { 5183 mStackSupervisor.resumeTopActivitiesLocked(); 5184 mStackSupervisor.scheduleIdleLocked(); 5185 } 5186 } 5187 5188 return didSomething; 5189 } 5190 5191 private final boolean removeProcessLocked(ProcessRecord app, 5192 boolean callerWillRestart, boolean allowRestart, String reason) { 5193 final String name = app.processName; 5194 final int uid = app.uid; 5195 if (DEBUG_PROCESSES) Slog.d( 5196 TAG, "Force removing proc " + app.toShortString() + " (" + name 5197 + "/" + uid + ")"); 5198 5199 mProcessNames.remove(name, uid); 5200 mIsolatedProcesses.remove(app.uid); 5201 if (mHeavyWeightProcess == app) { 5202 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5203 mHeavyWeightProcess.userId, 0)); 5204 mHeavyWeightProcess = null; 5205 } 5206 boolean needRestart = false; 5207 if (app.pid > 0 && app.pid != MY_PID) { 5208 int pid = app.pid; 5209 synchronized (mPidsSelfLocked) { 5210 mPidsSelfLocked.remove(pid); 5211 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5212 } 5213 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 5214 if (app.isolated) { 5215 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5216 } 5217 killUnneededProcessLocked(app, reason); 5218 Process.killProcessGroup(app.info.uid, app.pid); 5219 handleAppDiedLocked(app, true, allowRestart); 5220 removeLruProcessLocked(app); 5221 5222 if (app.persistent && !app.isolated) { 5223 if (!callerWillRestart) { 5224 addAppLocked(app.info, false, null /* ABI override */); 5225 } else { 5226 needRestart = true; 5227 } 5228 } 5229 } else { 5230 mRemovedProcesses.add(app); 5231 } 5232 5233 return needRestart; 5234 } 5235 5236 private final void processStartTimedOutLocked(ProcessRecord app) { 5237 final int pid = app.pid; 5238 boolean gone = false; 5239 synchronized (mPidsSelfLocked) { 5240 ProcessRecord knownApp = mPidsSelfLocked.get(pid); 5241 if (knownApp != null && knownApp.thread == null) { 5242 mPidsSelfLocked.remove(pid); 5243 gone = true; 5244 } 5245 } 5246 5247 if (gone) { 5248 Slog.w(TAG, "Process " + app + " failed to attach"); 5249 EventLog.writeEvent(EventLogTags.AM_PROCESS_START_TIMEOUT, app.userId, 5250 pid, app.uid, app.processName); 5251 mProcessNames.remove(app.processName, app.uid); 5252 mIsolatedProcesses.remove(app.uid); 5253 if (mHeavyWeightProcess == app) { 5254 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5255 mHeavyWeightProcess.userId, 0)); 5256 mHeavyWeightProcess = null; 5257 } 5258 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 5259 if (app.isolated) { 5260 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5261 } 5262 // Take care of any launching providers waiting for this process. 5263 checkAppInLaunchingProvidersLocked(app, true); 5264 // Take care of any services that are waiting for the process. 5265 mServices.processStartTimedOutLocked(app); 5266 killUnneededProcessLocked(app, "start timeout"); 5267 if (mBackupTarget != null && mBackupTarget.app.pid == pid) { 5268 Slog.w(TAG, "Unattached app died before backup, skipping"); 5269 try { 5270 IBackupManager bm = IBackupManager.Stub.asInterface( 5271 ServiceManager.getService(Context.BACKUP_SERVICE)); 5272 bm.agentDisconnected(app.info.packageName); 5273 } catch (RemoteException e) { 5274 // Can't happen; the backup manager is local 5275 } 5276 } 5277 if (isPendingBroadcastProcessLocked(pid)) { 5278 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 5279 skipPendingBroadcastLocked(pid); 5280 } 5281 } else { 5282 Slog.w(TAG, "Spurious process start timeout - pid not known for " + app); 5283 } 5284 } 5285 5286 private final boolean attachApplicationLocked(IApplicationThread thread, 5287 int pid) { 5288 5289 // Find the application record that is being attached... either via 5290 // the pid if we are running in multiple processes, or just pull the 5291 // next app record if we are emulating process with anonymous threads. 5292 ProcessRecord app; 5293 if (pid != MY_PID && pid >= 0) { 5294 synchronized (mPidsSelfLocked) { 5295 app = mPidsSelfLocked.get(pid); 5296 } 5297 } else { 5298 app = null; 5299 } 5300 5301 if (app == null) { 5302 Slog.w(TAG, "No pending application record for pid " + pid 5303 + " (IApplicationThread " + thread + "); dropping process"); 5304 EventLog.writeEvent(EventLogTags.AM_DROP_PROCESS, pid); 5305 if (pid > 0 && pid != MY_PID) { 5306 Process.killProcessQuiet(pid); 5307 //TODO: Process.killProcessGroup(app.info.uid, pid); 5308 } else { 5309 try { 5310 thread.scheduleExit(); 5311 } catch (Exception e) { 5312 // Ignore exceptions. 5313 } 5314 } 5315 return false; 5316 } 5317 5318 // If this application record is still attached to a previous 5319 // process, clean it up now. 5320 if (app.thread != null) { 5321 handleAppDiedLocked(app, true, true); 5322 } 5323 5324 // Tell the process all about itself. 5325 5326 if (localLOGV) Slog.v( 5327 TAG, "Binding process pid " + pid + " to record " + app); 5328 5329 final String processName = app.processName; 5330 try { 5331 AppDeathRecipient adr = new AppDeathRecipient( 5332 app, pid, thread); 5333 thread.asBinder().linkToDeath(adr, 0); 5334 app.deathRecipient = adr; 5335 } catch (RemoteException e) { 5336 app.resetPackageList(mProcessStats); 5337 startProcessLocked(app, "link fail", processName, null /* ABI override */); 5338 return false; 5339 } 5340 5341 EventLog.writeEvent(EventLogTags.AM_PROC_BOUND, app.userId, app.pid, app.processName); 5342 5343 app.makeActive(thread, mProcessStats); 5344 app.curAdj = app.setAdj = -100; 5345 app.curSchedGroup = app.setSchedGroup = Process.THREAD_GROUP_DEFAULT; 5346 app.forcingToForeground = null; 5347 updateProcessForegroundLocked(app, false, false); 5348 app.hasShownUi = false; 5349 app.debugging = false; 5350 app.cached = false; 5351 5352 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5353 5354 boolean normalMode = mProcessesReady || isAllowedWhileBooting(app.info); 5355 List<ProviderInfo> providers = normalMode ? generateApplicationProvidersLocked(app) : null; 5356 5357 if (!normalMode) { 5358 Slog.i(TAG, "Launching preboot mode app: " + app); 5359 } 5360 5361 if (localLOGV) Slog.v( 5362 TAG, "New app record " + app 5363 + " thread=" + thread.asBinder() + " pid=" + pid); 5364 try { 5365 int testMode = IApplicationThread.DEBUG_OFF; 5366 if (mDebugApp != null && mDebugApp.equals(processName)) { 5367 testMode = mWaitForDebugger 5368 ? IApplicationThread.DEBUG_WAIT 5369 : IApplicationThread.DEBUG_ON; 5370 app.debugging = true; 5371 if (mDebugTransient) { 5372 mDebugApp = mOrigDebugApp; 5373 mWaitForDebugger = mOrigWaitForDebugger; 5374 } 5375 } 5376 String profileFile = app.instrumentationProfileFile; 5377 ParcelFileDescriptor profileFd = null; 5378 boolean profileAutoStop = false; 5379 if (mProfileApp != null && mProfileApp.equals(processName)) { 5380 mProfileProc = app; 5381 profileFile = mProfileFile; 5382 profileFd = mProfileFd; 5383 profileAutoStop = mAutoStopProfiler; 5384 } 5385 boolean enableOpenGlTrace = false; 5386 if (mOpenGlTraceApp != null && mOpenGlTraceApp.equals(processName)) { 5387 enableOpenGlTrace = true; 5388 mOpenGlTraceApp = null; 5389 } 5390 5391 // If the app is being launched for restore or full backup, set it up specially 5392 boolean isRestrictedBackupMode = false; 5393 if (mBackupTarget != null && mBackupAppName.equals(processName)) { 5394 isRestrictedBackupMode = (mBackupTarget.backupMode == BackupRecord.RESTORE) 5395 || (mBackupTarget.backupMode == BackupRecord.RESTORE_FULL) 5396 || (mBackupTarget.backupMode == BackupRecord.BACKUP_FULL); 5397 } 5398 5399 ensurePackageDexOpt(app.instrumentationInfo != null 5400 ? app.instrumentationInfo.packageName 5401 : app.info.packageName); 5402 if (app.instrumentationClass != null) { 5403 ensurePackageDexOpt(app.instrumentationClass.getPackageName()); 5404 } 5405 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Binding proc " 5406 + processName + " with config " + mConfiguration); 5407 ApplicationInfo appInfo = app.instrumentationInfo != null 5408 ? app.instrumentationInfo : app.info; 5409 app.compat = compatibilityInfoForPackageLocked(appInfo); 5410 if (profileFd != null) { 5411 profileFd = profileFd.dup(); 5412 } 5413 thread.bindApplication(processName, appInfo, providers, 5414 app.instrumentationClass, profileFile, profileFd, profileAutoStop, 5415 app.instrumentationArguments, app.instrumentationWatcher, 5416 app.instrumentationUiAutomationConnection, testMode, enableOpenGlTrace, 5417 isRestrictedBackupMode || !normalMode, app.persistent, 5418 new Configuration(mConfiguration), app.compat, getCommonServicesLocked(), 5419 mCoreSettingsObserver.getCoreSettingsLocked()); 5420 updateLruProcessLocked(app, false, null); 5421 app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis(); 5422 } catch (Exception e) { 5423 // todo: Yikes! What should we do? For now we will try to 5424 // start another process, but that could easily get us in 5425 // an infinite loop of restarting processes... 5426 Slog.w(TAG, "Exception thrown during bind!", e); 5427 5428 app.resetPackageList(mProcessStats); 5429 app.unlinkDeathRecipient(); 5430 startProcessLocked(app, "bind fail", processName, null /* ABI override */); 5431 return false; 5432 } 5433 5434 // Remove this record from the list of starting applications. 5435 mPersistentStartingProcesses.remove(app); 5436 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 5437 "Attach application locked removing on hold: " + app); 5438 mProcessesOnHold.remove(app); 5439 5440 boolean badApp = false; 5441 boolean didSomething = false; 5442 5443 // See if the top visible activity is waiting to run in this process... 5444 if (normalMode) { 5445 try { 5446 if (mStackSupervisor.attachApplicationLocked(app)) { 5447 didSomething = true; 5448 } 5449 } catch (Exception e) { 5450 badApp = true; 5451 } 5452 } 5453 5454 // Find any services that should be running in this process... 5455 if (!badApp) { 5456 try { 5457 didSomething |= mServices.attachApplicationLocked(app, processName); 5458 } catch (Exception e) { 5459 badApp = true; 5460 } 5461 } 5462 5463 // Check if a next-broadcast receiver is in this process... 5464 if (!badApp && isPendingBroadcastProcessLocked(pid)) { 5465 try { 5466 didSomething |= sendPendingBroadcastsLocked(app); 5467 } catch (Exception e) { 5468 // If the app died trying to launch the receiver we declare it 'bad' 5469 badApp = true; 5470 } 5471 } 5472 5473 // Check whether the next backup agent is in this process... 5474 if (!badApp && mBackupTarget != null && mBackupTarget.appInfo.uid == app.uid) { 5475 if (DEBUG_BACKUP) Slog.v(TAG, "New app is backup target, launching agent for " + app); 5476 ensurePackageDexOpt(mBackupTarget.appInfo.packageName); 5477 try { 5478 thread.scheduleCreateBackupAgent(mBackupTarget.appInfo, 5479 compatibilityInfoForPackageLocked(mBackupTarget.appInfo), 5480 mBackupTarget.backupMode); 5481 } catch (Exception e) { 5482 Slog.w(TAG, "Exception scheduling backup agent creation: "); 5483 e.printStackTrace(); 5484 } 5485 } 5486 5487 if (badApp) { 5488 // todo: Also need to kill application to deal with all 5489 // kinds of exceptions. 5490 handleAppDiedLocked(app, false, true); 5491 return false; 5492 } 5493 5494 if (!didSomething) { 5495 updateOomAdjLocked(); 5496 } 5497 5498 return true; 5499 } 5500 5501 @Override 5502 public final void attachApplication(IApplicationThread thread) { 5503 synchronized (this) { 5504 int callingPid = Binder.getCallingPid(); 5505 final long origId = Binder.clearCallingIdentity(); 5506 attachApplicationLocked(thread, callingPid); 5507 Binder.restoreCallingIdentity(origId); 5508 } 5509 } 5510 5511 @Override 5512 public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) { 5513 final long origId = Binder.clearCallingIdentity(); 5514 synchronized (this) { 5515 ActivityStack stack = ActivityRecord.getStackLocked(token); 5516 if (stack != null) { 5517 ActivityRecord r = 5518 mStackSupervisor.activityIdleInternalLocked(token, false, config); 5519 if (stopProfiling) { 5520 if ((mProfileProc == r.app) && (mProfileFd != null)) { 5521 try { 5522 mProfileFd.close(); 5523 } catch (IOException e) { 5524 } 5525 clearProfilerLocked(); 5526 } 5527 } 5528 } 5529 } 5530 Binder.restoreCallingIdentity(origId); 5531 } 5532 5533 void postEnableScreenAfterBootLocked() { 5534 mHandler.sendEmptyMessage(ENABLE_SCREEN_AFTER_BOOT_MSG); 5535 } 5536 5537 void enableScreenAfterBoot() { 5538 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN, 5539 SystemClock.uptimeMillis()); 5540 mWindowManager.enableScreenAfterBoot(); 5541 5542 synchronized (this) { 5543 updateEventDispatchingLocked(); 5544 } 5545 } 5546 5547 @Override 5548 public void showBootMessage(final CharSequence msg, final boolean always) { 5549 enforceNotIsolatedCaller("showBootMessage"); 5550 mWindowManager.showBootMessage(msg, always); 5551 } 5552 5553 @Override 5554 public void dismissKeyguardOnNextActivity() { 5555 enforceNotIsolatedCaller("dismissKeyguardOnNextActivity"); 5556 final long token = Binder.clearCallingIdentity(); 5557 try { 5558 synchronized (this) { 5559 if (DEBUG_LOCKSCREEN) logLockScreen(""); 5560 if (mLockScreenShown) { 5561 mLockScreenShown = false; 5562 comeOutOfSleepIfNeededLocked(); 5563 } 5564 mStackSupervisor.setDismissKeyguard(true); 5565 } 5566 } finally { 5567 Binder.restoreCallingIdentity(token); 5568 } 5569 } 5570 5571 final void finishBooting() { 5572 // Register receivers to handle package update events 5573 mPackageMonitor.register(mContext, Looper.getMainLooper(), false); 5574 5575 synchronized (this) { 5576 // Ensure that any processes we had put on hold are now started 5577 // up. 5578 final int NP = mProcessesOnHold.size(); 5579 if (NP > 0) { 5580 ArrayList<ProcessRecord> procs = 5581 new ArrayList<ProcessRecord>(mProcessesOnHold); 5582 for (int ip=0; ip<NP; ip++) { 5583 if (DEBUG_PROCESSES) Slog.v(TAG, "Starting process on hold: " 5584 + procs.get(ip)); 5585 startProcessLocked(procs.get(ip), "on-hold", null, null /* ABI override */); 5586 } 5587 } 5588 5589 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 5590 // Start looking for apps that are abusing wake locks. 5591 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 5592 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 5593 // Tell anyone interested that we are done booting! 5594 SystemProperties.set("sys.boot_completed", "1"); 5595 SystemProperties.set("dev.bootcomplete", "1"); 5596 for (int i=0; i<mStartedUsers.size(); i++) { 5597 UserStartedState uss = mStartedUsers.valueAt(i); 5598 if (uss.mState == UserStartedState.STATE_BOOTING) { 5599 uss.mState = UserStartedState.STATE_RUNNING; 5600 final int userId = mStartedUsers.keyAt(i); 5601 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 5602 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 5603 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 5604 broadcastIntentLocked(null, null, intent, null, 5605 new IIntentReceiver.Stub() { 5606 @Override 5607 public void performReceive(Intent intent, int resultCode, 5608 String data, Bundle extras, boolean ordered, 5609 boolean sticky, int sendingUser) { 5610 synchronized (ActivityManagerService.this) { 5611 requestPssAllProcsLocked(SystemClock.uptimeMillis(), 5612 true, false); 5613 } 5614 } 5615 }, 5616 0, null, null, 5617 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, 5618 AppOpsManager.OP_NONE, true, false, MY_PID, Process.SYSTEM_UID, 5619 userId); 5620 } 5621 } 5622 scheduleStartProfilesLocked(); 5623 } 5624 } 5625 } 5626 5627 final void ensureBootCompleted() { 5628 boolean booting; 5629 boolean enableScreen; 5630 synchronized (this) { 5631 booting = mBooting; 5632 mBooting = false; 5633 enableScreen = !mBooted; 5634 mBooted = true; 5635 } 5636 5637 if (booting) { 5638 finishBooting(); 5639 } 5640 5641 if (enableScreen) { 5642 enableScreenAfterBoot(); 5643 } 5644 } 5645 5646 @Override 5647 public final void activityResumed(IBinder token) { 5648 final long origId = Binder.clearCallingIdentity(); 5649 synchronized(this) { 5650 ActivityStack stack = ActivityRecord.getStackLocked(token); 5651 if (stack != null) { 5652 ActivityRecord.activityResumedLocked(token); 5653 } 5654 } 5655 Binder.restoreCallingIdentity(origId); 5656 } 5657 5658 @Override 5659 public final void activityPaused(IBinder token, PersistableBundle persistentState) { 5660 final long origId = Binder.clearCallingIdentity(); 5661 synchronized(this) { 5662 ActivityStack stack = ActivityRecord.getStackLocked(token); 5663 if (stack != null) { 5664 stack.activityPausedLocked(token, false, persistentState); 5665 } 5666 } 5667 Binder.restoreCallingIdentity(origId); 5668 } 5669 5670 @Override 5671 public final void activityStopped(IBinder token, Bundle icicle, 5672 PersistableBundle persistentState, CharSequence description) { 5673 if (localLOGV) Slog.v(TAG, "Activity stopped: token=" + token); 5674 5675 // Refuse possible leaked file descriptors 5676 if (icicle != null && icicle.hasFileDescriptors()) { 5677 throw new IllegalArgumentException("File descriptors passed in Bundle"); 5678 } 5679 5680 final long origId = Binder.clearCallingIdentity(); 5681 5682 synchronized (this) { 5683 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5684 if (r != null) { 5685 r.task.stack.activityStoppedLocked(r, icicle, persistentState, description); 5686 } 5687 } 5688 5689 trimApplications(); 5690 5691 Binder.restoreCallingIdentity(origId); 5692 } 5693 5694 @Override 5695 public final void activityDestroyed(IBinder token) { 5696 if (DEBUG_SWITCH) Slog.v(TAG, "ACTIVITY DESTROYED: " + token); 5697 synchronized (this) { 5698 ActivityStack stack = ActivityRecord.getStackLocked(token); 5699 if (stack != null) { 5700 stack.activityDestroyedLocked(token); 5701 } 5702 } 5703 } 5704 5705 @Override 5706 public final void mediaResourcesReleased(IBinder token) { 5707 final long origId = Binder.clearCallingIdentity(); 5708 try { 5709 synchronized (this) { 5710 ActivityStack stack = ActivityRecord.getStackLocked(token); 5711 if (stack != null) { 5712 stack.mediaResourcesReleased(token); 5713 } 5714 } 5715 } finally { 5716 Binder.restoreCallingIdentity(origId); 5717 } 5718 } 5719 5720 @Override 5721 public final void notifyLaunchTaskBehindComplete(IBinder token) { 5722 mStackSupervisor.scheduleLaunchTaskBehindComplete(token); 5723 } 5724 5725 @Override 5726 public final void notifyEnterAnimationComplete(IBinder token) { 5727 mHandler.sendMessage(mHandler.obtainMessage(ENTER_ANIMATION_COMPLETE_MSG, token)); 5728 } 5729 5730 @Override 5731 public String getCallingPackage(IBinder token) { 5732 synchronized (this) { 5733 ActivityRecord r = getCallingRecordLocked(token); 5734 return r != null ? r.info.packageName : null; 5735 } 5736 } 5737 5738 @Override 5739 public ComponentName getCallingActivity(IBinder token) { 5740 synchronized (this) { 5741 ActivityRecord r = getCallingRecordLocked(token); 5742 return r != null ? r.intent.getComponent() : null; 5743 } 5744 } 5745 5746 private ActivityRecord getCallingRecordLocked(IBinder token) { 5747 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5748 if (r == null) { 5749 return null; 5750 } 5751 return r.resultTo; 5752 } 5753 5754 @Override 5755 public ComponentName getActivityClassForToken(IBinder token) { 5756 synchronized(this) { 5757 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5758 if (r == null) { 5759 return null; 5760 } 5761 return r.intent.getComponent(); 5762 } 5763 } 5764 5765 @Override 5766 public String getPackageForToken(IBinder token) { 5767 synchronized(this) { 5768 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5769 if (r == null) { 5770 return null; 5771 } 5772 return r.packageName; 5773 } 5774 } 5775 5776 @Override 5777 public IIntentSender getIntentSender(int type, 5778 String packageName, IBinder token, String resultWho, 5779 int requestCode, Intent[] intents, String[] resolvedTypes, 5780 int flags, Bundle options, int userId) { 5781 enforceNotIsolatedCaller("getIntentSender"); 5782 // Refuse possible leaked file descriptors 5783 if (intents != null) { 5784 if (intents.length < 1) { 5785 throw new IllegalArgumentException("Intents array length must be >= 1"); 5786 } 5787 for (int i=0; i<intents.length; i++) { 5788 Intent intent = intents[i]; 5789 if (intent != null) { 5790 if (intent.hasFileDescriptors()) { 5791 throw new IllegalArgumentException("File descriptors passed in Intent"); 5792 } 5793 if (type == ActivityManager.INTENT_SENDER_BROADCAST && 5794 (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 5795 throw new IllegalArgumentException( 5796 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 5797 } 5798 intents[i] = new Intent(intent); 5799 } 5800 } 5801 if (resolvedTypes != null && resolvedTypes.length != intents.length) { 5802 throw new IllegalArgumentException( 5803 "Intent array length does not match resolvedTypes length"); 5804 } 5805 } 5806 if (options != null) { 5807 if (options.hasFileDescriptors()) { 5808 throw new IllegalArgumentException("File descriptors passed in options"); 5809 } 5810 } 5811 5812 synchronized(this) { 5813 int callingUid = Binder.getCallingUid(); 5814 int origUserId = userId; 5815 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 5816 type == ActivityManager.INTENT_SENDER_BROADCAST, 5817 ALLOW_NON_FULL, "getIntentSender", null); 5818 if (origUserId == UserHandle.USER_CURRENT) { 5819 // We don't want to evaluate this until the pending intent is 5820 // actually executed. However, we do want to always do the 5821 // security checking for it above. 5822 userId = UserHandle.USER_CURRENT; 5823 } 5824 try { 5825 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 5826 int uid = AppGlobals.getPackageManager() 5827 .getPackageUid(packageName, UserHandle.getUserId(callingUid)); 5828 if (!UserHandle.isSameApp(callingUid, uid)) { 5829 String msg = "Permission Denial: getIntentSender() from pid=" 5830 + Binder.getCallingPid() 5831 + ", uid=" + Binder.getCallingUid() 5832 + ", (need uid=" + uid + ")" 5833 + " is not allowed to send as package " + packageName; 5834 Slog.w(TAG, msg); 5835 throw new SecurityException(msg); 5836 } 5837 } 5838 5839 return getIntentSenderLocked(type, packageName, callingUid, userId, 5840 token, resultWho, requestCode, intents, resolvedTypes, flags, options); 5841 5842 } catch (RemoteException e) { 5843 throw new SecurityException(e); 5844 } 5845 } 5846 } 5847 5848 IIntentSender getIntentSenderLocked(int type, String packageName, 5849 int callingUid, int userId, IBinder token, String resultWho, 5850 int requestCode, Intent[] intents, String[] resolvedTypes, int flags, 5851 Bundle options) { 5852 if (DEBUG_MU) 5853 Slog.v(TAG_MU, "getIntentSenderLocked(): uid=" + callingUid); 5854 ActivityRecord activity = null; 5855 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 5856 activity = ActivityRecord.isInStackLocked(token); 5857 if (activity == null) { 5858 return null; 5859 } 5860 if (activity.finishing) { 5861 return null; 5862 } 5863 } 5864 5865 final boolean noCreate = (flags&PendingIntent.FLAG_NO_CREATE) != 0; 5866 final boolean cancelCurrent = (flags&PendingIntent.FLAG_CANCEL_CURRENT) != 0; 5867 final boolean updateCurrent = (flags&PendingIntent.FLAG_UPDATE_CURRENT) != 0; 5868 flags &= ~(PendingIntent.FLAG_NO_CREATE|PendingIntent.FLAG_CANCEL_CURRENT 5869 |PendingIntent.FLAG_UPDATE_CURRENT); 5870 5871 PendingIntentRecord.Key key = new PendingIntentRecord.Key( 5872 type, packageName, activity, resultWho, 5873 requestCode, intents, resolvedTypes, flags, options, userId); 5874 WeakReference<PendingIntentRecord> ref; 5875 ref = mIntentSenderRecords.get(key); 5876 PendingIntentRecord rec = ref != null ? ref.get() : null; 5877 if (rec != null) { 5878 if (!cancelCurrent) { 5879 if (updateCurrent) { 5880 if (rec.key.requestIntent != null) { 5881 rec.key.requestIntent.replaceExtras(intents != null ? 5882 intents[intents.length - 1] : null); 5883 } 5884 if (intents != null) { 5885 intents[intents.length-1] = rec.key.requestIntent; 5886 rec.key.allIntents = intents; 5887 rec.key.allResolvedTypes = resolvedTypes; 5888 } else { 5889 rec.key.allIntents = null; 5890 rec.key.allResolvedTypes = null; 5891 } 5892 } 5893 return rec; 5894 } 5895 rec.canceled = true; 5896 mIntentSenderRecords.remove(key); 5897 } 5898 if (noCreate) { 5899 return rec; 5900 } 5901 rec = new PendingIntentRecord(this, key, callingUid); 5902 mIntentSenderRecords.put(key, rec.ref); 5903 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 5904 if (activity.pendingResults == null) { 5905 activity.pendingResults 5906 = new HashSet<WeakReference<PendingIntentRecord>>(); 5907 } 5908 activity.pendingResults.add(rec.ref); 5909 } 5910 return rec; 5911 } 5912 5913 @Override 5914 public void cancelIntentSender(IIntentSender sender) { 5915 if (!(sender instanceof PendingIntentRecord)) { 5916 return; 5917 } 5918 synchronized(this) { 5919 PendingIntentRecord rec = (PendingIntentRecord)sender; 5920 try { 5921 int uid = AppGlobals.getPackageManager() 5922 .getPackageUid(rec.key.packageName, UserHandle.getCallingUserId()); 5923 if (!UserHandle.isSameApp(uid, Binder.getCallingUid())) { 5924 String msg = "Permission Denial: cancelIntentSender() from pid=" 5925 + Binder.getCallingPid() 5926 + ", uid=" + Binder.getCallingUid() 5927 + " is not allowed to cancel packges " 5928 + rec.key.packageName; 5929 Slog.w(TAG, msg); 5930 throw new SecurityException(msg); 5931 } 5932 } catch (RemoteException e) { 5933 throw new SecurityException(e); 5934 } 5935 cancelIntentSenderLocked(rec, true); 5936 } 5937 } 5938 5939 void cancelIntentSenderLocked(PendingIntentRecord rec, boolean cleanActivity) { 5940 rec.canceled = true; 5941 mIntentSenderRecords.remove(rec.key); 5942 if (cleanActivity && rec.key.activity != null) { 5943 rec.key.activity.pendingResults.remove(rec.ref); 5944 } 5945 } 5946 5947 @Override 5948 public String getPackageForIntentSender(IIntentSender pendingResult) { 5949 if (!(pendingResult instanceof PendingIntentRecord)) { 5950 return null; 5951 } 5952 try { 5953 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5954 return res.key.packageName; 5955 } catch (ClassCastException e) { 5956 } 5957 return null; 5958 } 5959 5960 @Override 5961 public int getUidForIntentSender(IIntentSender sender) { 5962 if (sender instanceof PendingIntentRecord) { 5963 try { 5964 PendingIntentRecord res = (PendingIntentRecord)sender; 5965 return res.uid; 5966 } catch (ClassCastException e) { 5967 } 5968 } 5969 return -1; 5970 } 5971 5972 @Override 5973 public boolean isIntentSenderTargetedToPackage(IIntentSender pendingResult) { 5974 if (!(pendingResult instanceof PendingIntentRecord)) { 5975 return false; 5976 } 5977 try { 5978 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5979 if (res.key.allIntents == null) { 5980 return false; 5981 } 5982 for (int i=0; i<res.key.allIntents.length; i++) { 5983 Intent intent = res.key.allIntents[i]; 5984 if (intent.getPackage() != null && intent.getComponent() != null) { 5985 return false; 5986 } 5987 } 5988 return true; 5989 } catch (ClassCastException e) { 5990 } 5991 return false; 5992 } 5993 5994 @Override 5995 public boolean isIntentSenderAnActivity(IIntentSender pendingResult) { 5996 if (!(pendingResult instanceof PendingIntentRecord)) { 5997 return false; 5998 } 5999 try { 6000 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6001 if (res.key.type == ActivityManager.INTENT_SENDER_ACTIVITY) { 6002 return true; 6003 } 6004 return false; 6005 } catch (ClassCastException e) { 6006 } 6007 return false; 6008 } 6009 6010 @Override 6011 public Intent getIntentForIntentSender(IIntentSender pendingResult) { 6012 if (!(pendingResult instanceof PendingIntentRecord)) { 6013 return null; 6014 } 6015 try { 6016 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6017 return res.key.requestIntent != null ? new Intent(res.key.requestIntent) : null; 6018 } catch (ClassCastException e) { 6019 } 6020 return null; 6021 } 6022 6023 @Override 6024 public String getTagForIntentSender(IIntentSender pendingResult, String prefix) { 6025 if (!(pendingResult instanceof PendingIntentRecord)) { 6026 return null; 6027 } 6028 try { 6029 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6030 Intent intent = res.key.requestIntent; 6031 if (intent != null) { 6032 if (res.lastTag != null && res.lastTagPrefix == prefix && (res.lastTagPrefix == null 6033 || res.lastTagPrefix.equals(prefix))) { 6034 return res.lastTag; 6035 } 6036 res.lastTagPrefix = prefix; 6037 StringBuilder sb = new StringBuilder(128); 6038 if (prefix != null) { 6039 sb.append(prefix); 6040 } 6041 if (intent.getAction() != null) { 6042 sb.append(intent.getAction()); 6043 } else if (intent.getComponent() != null) { 6044 intent.getComponent().appendShortString(sb); 6045 } else { 6046 sb.append("?"); 6047 } 6048 return res.lastTag = sb.toString(); 6049 } 6050 } catch (ClassCastException e) { 6051 } 6052 return null; 6053 } 6054 6055 @Override 6056 public void setProcessLimit(int max) { 6057 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 6058 "setProcessLimit()"); 6059 synchronized (this) { 6060 mProcessLimit = max < 0 ? ProcessList.MAX_CACHED_APPS : max; 6061 mProcessLimitOverride = max; 6062 } 6063 trimApplications(); 6064 } 6065 6066 @Override 6067 public int getProcessLimit() { 6068 synchronized (this) { 6069 return mProcessLimitOverride; 6070 } 6071 } 6072 6073 void foregroundTokenDied(ForegroundToken token) { 6074 synchronized (ActivityManagerService.this) { 6075 synchronized (mPidsSelfLocked) { 6076 ForegroundToken cur 6077 = mForegroundProcesses.get(token.pid); 6078 if (cur != token) { 6079 return; 6080 } 6081 mForegroundProcesses.remove(token.pid); 6082 ProcessRecord pr = mPidsSelfLocked.get(token.pid); 6083 if (pr == null) { 6084 return; 6085 } 6086 pr.forcingToForeground = null; 6087 updateProcessForegroundLocked(pr, false, false); 6088 } 6089 updateOomAdjLocked(); 6090 } 6091 } 6092 6093 @Override 6094 public void setProcessForeground(IBinder token, int pid, boolean isForeground) { 6095 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 6096 "setProcessForeground()"); 6097 synchronized(this) { 6098 boolean changed = false; 6099 6100 synchronized (mPidsSelfLocked) { 6101 ProcessRecord pr = mPidsSelfLocked.get(pid); 6102 if (pr == null && isForeground) { 6103 Slog.w(TAG, "setProcessForeground called on unknown pid: " + pid); 6104 return; 6105 } 6106 ForegroundToken oldToken = mForegroundProcesses.get(pid); 6107 if (oldToken != null) { 6108 oldToken.token.unlinkToDeath(oldToken, 0); 6109 mForegroundProcesses.remove(pid); 6110 if (pr != null) { 6111 pr.forcingToForeground = null; 6112 } 6113 changed = true; 6114 } 6115 if (isForeground && token != null) { 6116 ForegroundToken newToken = new ForegroundToken() { 6117 @Override 6118 public void binderDied() { 6119 foregroundTokenDied(this); 6120 } 6121 }; 6122 newToken.pid = pid; 6123 newToken.token = token; 6124 try { 6125 token.linkToDeath(newToken, 0); 6126 mForegroundProcesses.put(pid, newToken); 6127 pr.forcingToForeground = token; 6128 changed = true; 6129 } catch (RemoteException e) { 6130 // If the process died while doing this, we will later 6131 // do the cleanup with the process death link. 6132 } 6133 } 6134 } 6135 6136 if (changed) { 6137 updateOomAdjLocked(); 6138 } 6139 } 6140 } 6141 6142 // ========================================================= 6143 // PERMISSIONS 6144 // ========================================================= 6145 6146 static class PermissionController extends IPermissionController.Stub { 6147 ActivityManagerService mActivityManagerService; 6148 PermissionController(ActivityManagerService activityManagerService) { 6149 mActivityManagerService = activityManagerService; 6150 } 6151 6152 @Override 6153 public boolean checkPermission(String permission, int pid, int uid) { 6154 return mActivityManagerService.checkPermission(permission, pid, 6155 uid) == PackageManager.PERMISSION_GRANTED; 6156 } 6157 } 6158 6159 class IntentFirewallInterface implements IntentFirewall.AMSInterface { 6160 @Override 6161 public int checkComponentPermission(String permission, int pid, int uid, 6162 int owningUid, boolean exported) { 6163 return ActivityManagerService.this.checkComponentPermission(permission, pid, uid, 6164 owningUid, exported); 6165 } 6166 6167 @Override 6168 public Object getAMSLock() { 6169 return ActivityManagerService.this; 6170 } 6171 } 6172 6173 /** 6174 * This can be called with or without the global lock held. 6175 */ 6176 int checkComponentPermission(String permission, int pid, int uid, 6177 int owningUid, boolean exported) { 6178 // We might be performing an operation on behalf of an indirect binder 6179 // invocation, e.g. via {@link #openContentUri}. Check and adjust the 6180 // client identity accordingly before proceeding. 6181 Identity tlsIdentity = sCallerIdentity.get(); 6182 if (tlsIdentity != null) { 6183 Slog.d(TAG, "checkComponentPermission() adjusting {pid,uid} to {" 6184 + tlsIdentity.pid + "," + tlsIdentity.uid + "}"); 6185 uid = tlsIdentity.uid; 6186 pid = tlsIdentity.pid; 6187 } 6188 6189 if (pid == MY_PID) { 6190 return PackageManager.PERMISSION_GRANTED; 6191 } 6192 6193 return ActivityManager.checkComponentPermission(permission, uid, 6194 owningUid, exported); 6195 } 6196 6197 /** 6198 * As the only public entry point for permissions checking, this method 6199 * can enforce the semantic that requesting a check on a null global 6200 * permission is automatically denied. (Internally a null permission 6201 * string is used when calling {@link #checkComponentPermission} in cases 6202 * when only uid-based security is needed.) 6203 * 6204 * This can be called with or without the global lock held. 6205 */ 6206 @Override 6207 public int checkPermission(String permission, int pid, int uid) { 6208 if (permission == null) { 6209 return PackageManager.PERMISSION_DENIED; 6210 } 6211 return checkComponentPermission(permission, pid, UserHandle.getAppId(uid), -1, true); 6212 } 6213 6214 /** 6215 * Binder IPC calls go through the public entry point. 6216 * This can be called with or without the global lock held. 6217 */ 6218 int checkCallingPermission(String permission) { 6219 return checkPermission(permission, 6220 Binder.getCallingPid(), 6221 UserHandle.getAppId(Binder.getCallingUid())); 6222 } 6223 6224 /** 6225 * This can be called with or without the global lock held. 6226 */ 6227 void enforceCallingPermission(String permission, String func) { 6228 if (checkCallingPermission(permission) 6229 == PackageManager.PERMISSION_GRANTED) { 6230 return; 6231 } 6232 6233 String msg = "Permission Denial: " + func + " from pid=" 6234 + Binder.getCallingPid() 6235 + ", uid=" + Binder.getCallingUid() 6236 + " requires " + permission; 6237 Slog.w(TAG, msg); 6238 throw new SecurityException(msg); 6239 } 6240 6241 /** 6242 * Determine if UID is holding permissions required to access {@link Uri} in 6243 * the given {@link ProviderInfo}. Final permission checking is always done 6244 * in {@link ContentProvider}. 6245 */ 6246 private final boolean checkHoldingPermissionsLocked( 6247 IPackageManager pm, ProviderInfo pi, GrantUri grantUri, int uid, final int modeFlags) { 6248 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6249 "checkHoldingPermissionsLocked: uri=" + grantUri + " uid=" + uid); 6250 if (UserHandle.getUserId(uid) != grantUri.sourceUserId) { 6251 return false; 6252 } 6253 return checkHoldingPermissionsInternalLocked(pm, pi, grantUri, uid, modeFlags, true); 6254 } 6255 6256 private final boolean checkHoldingPermissionsInternalLocked(IPackageManager pm, ProviderInfo pi, 6257 GrantUri grantUri, int uid, final int modeFlags, boolean considerUidPermissions) { 6258 if (pi.applicationInfo.uid == uid) { 6259 return true; 6260 } else if (!pi.exported) { 6261 return false; 6262 } 6263 6264 boolean readMet = (modeFlags & Intent.FLAG_GRANT_READ_URI_PERMISSION) == 0; 6265 boolean writeMet = (modeFlags & Intent.FLAG_GRANT_WRITE_URI_PERMISSION) == 0; 6266 try { 6267 // check if target holds top-level <provider> permissions 6268 if (!readMet && pi.readPermission != null && considerUidPermissions 6269 && (pm.checkUidPermission(pi.readPermission, uid) == PERMISSION_GRANTED)) { 6270 readMet = true; 6271 } 6272 if (!writeMet && pi.writePermission != null && considerUidPermissions 6273 && (pm.checkUidPermission(pi.writePermission, uid) == PERMISSION_GRANTED)) { 6274 writeMet = true; 6275 } 6276 6277 // track if unprotected read/write is allowed; any denied 6278 // <path-permission> below removes this ability 6279 boolean allowDefaultRead = pi.readPermission == null; 6280 boolean allowDefaultWrite = pi.writePermission == null; 6281 6282 // check if target holds any <path-permission> that match uri 6283 final PathPermission[] pps = pi.pathPermissions; 6284 if (pps != null) { 6285 final String path = grantUri.uri.getPath(); 6286 int i = pps.length; 6287 while (i > 0 && (!readMet || !writeMet)) { 6288 i--; 6289 PathPermission pp = pps[i]; 6290 if (pp.match(path)) { 6291 if (!readMet) { 6292 final String pprperm = pp.getReadPermission(); 6293 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking read perm for " 6294 + pprperm + " for " + pp.getPath() 6295 + ": match=" + pp.match(path) 6296 + " check=" + pm.checkUidPermission(pprperm, uid)); 6297 if (pprperm != null) { 6298 if (considerUidPermissions && pm.checkUidPermission(pprperm, uid) 6299 == PERMISSION_GRANTED) { 6300 readMet = true; 6301 } else { 6302 allowDefaultRead = false; 6303 } 6304 } 6305 } 6306 if (!writeMet) { 6307 final String ppwperm = pp.getWritePermission(); 6308 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking write perm " 6309 + ppwperm + " for " + pp.getPath() 6310 + ": match=" + pp.match(path) 6311 + " check=" + pm.checkUidPermission(ppwperm, uid)); 6312 if (ppwperm != null) { 6313 if (considerUidPermissions && pm.checkUidPermission(ppwperm, uid) 6314 == PERMISSION_GRANTED) { 6315 writeMet = true; 6316 } else { 6317 allowDefaultWrite = false; 6318 } 6319 } 6320 } 6321 } 6322 } 6323 } 6324 6325 // grant unprotected <provider> read/write, if not blocked by 6326 // <path-permission> above 6327 if (allowDefaultRead) readMet = true; 6328 if (allowDefaultWrite) writeMet = true; 6329 6330 } catch (RemoteException e) { 6331 return false; 6332 } 6333 6334 return readMet && writeMet; 6335 } 6336 6337 private ProviderInfo getProviderInfoLocked(String authority, int userHandle) { 6338 ProviderInfo pi = null; 6339 ContentProviderRecord cpr = mProviderMap.getProviderByName(authority, userHandle); 6340 if (cpr != null) { 6341 pi = cpr.info; 6342 } else { 6343 try { 6344 pi = AppGlobals.getPackageManager().resolveContentProvider( 6345 authority, PackageManager.GET_URI_PERMISSION_PATTERNS, userHandle); 6346 } catch (RemoteException ex) { 6347 } 6348 } 6349 return pi; 6350 } 6351 6352 private UriPermission findUriPermissionLocked(int targetUid, GrantUri grantUri) { 6353 final ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6354 if (targetUris != null) { 6355 return targetUris.get(grantUri); 6356 } 6357 return null; 6358 } 6359 6360 private UriPermission findOrCreateUriPermissionLocked(String sourcePkg, 6361 String targetPkg, int targetUid, GrantUri grantUri) { 6362 ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6363 if (targetUris == null) { 6364 targetUris = Maps.newArrayMap(); 6365 mGrantedUriPermissions.put(targetUid, targetUris); 6366 } 6367 6368 UriPermission perm = targetUris.get(grantUri); 6369 if (perm == null) { 6370 perm = new UriPermission(sourcePkg, targetPkg, targetUid, grantUri); 6371 targetUris.put(grantUri, perm); 6372 } 6373 6374 return perm; 6375 } 6376 6377 private final boolean checkUriPermissionLocked(GrantUri grantUri, int uid, 6378 final int modeFlags) { 6379 final boolean persistable = (modeFlags & Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION) != 0; 6380 final int minStrength = persistable ? UriPermission.STRENGTH_PERSISTABLE 6381 : UriPermission.STRENGTH_OWNED; 6382 6383 // Root gets to do everything. 6384 if (uid == 0) { 6385 return true; 6386 } 6387 6388 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 6389 if (perms == null) return false; 6390 6391 // First look for exact match 6392 final UriPermission exactPerm = perms.get(grantUri); 6393 if (exactPerm != null && exactPerm.getStrength(modeFlags) >= minStrength) { 6394 return true; 6395 } 6396 6397 // No exact match, look for prefixes 6398 final int N = perms.size(); 6399 for (int i = 0; i < N; i++) { 6400 final UriPermission perm = perms.valueAt(i); 6401 if (perm.uri.prefix && grantUri.uri.isPathPrefixMatch(perm.uri.uri) 6402 && perm.getStrength(modeFlags) >= minStrength) { 6403 return true; 6404 } 6405 } 6406 6407 return false; 6408 } 6409 6410 @Override 6411 public int checkUriPermission(Uri uri, int pid, int uid, 6412 final int modeFlags, int userId) { 6413 enforceNotIsolatedCaller("checkUriPermission"); 6414 6415 // Another redirected-binder-call permissions check as in 6416 // {@link checkComponentPermission}. 6417 Identity tlsIdentity = sCallerIdentity.get(); 6418 if (tlsIdentity != null) { 6419 uid = tlsIdentity.uid; 6420 pid = tlsIdentity.pid; 6421 } 6422 6423 // Our own process gets to do everything. 6424 if (pid == MY_PID) { 6425 return PackageManager.PERMISSION_GRANTED; 6426 } 6427 synchronized (this) { 6428 return checkUriPermissionLocked(new GrantUri(userId, uri, false), uid, modeFlags) 6429 ? PackageManager.PERMISSION_GRANTED 6430 : PackageManager.PERMISSION_DENIED; 6431 } 6432 } 6433 6434 /** 6435 * Check if the targetPkg can be granted permission to access uri by 6436 * the callingUid using the given modeFlags. Throws a security exception 6437 * if callingUid is not allowed to do this. Returns the uid of the target 6438 * if the URI permission grant should be performed; returns -1 if it is not 6439 * needed (for example targetPkg already has permission to access the URI). 6440 * If you already know the uid of the target, you can supply it in 6441 * lastTargetUid else set that to -1. 6442 */ 6443 int checkGrantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 6444 final int modeFlags, int lastTargetUid) { 6445 if (!Intent.isAccessUriMode(modeFlags)) { 6446 return -1; 6447 } 6448 6449 if (targetPkg != null) { 6450 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6451 "Checking grant " + targetPkg + " permission to " + grantUri); 6452 } 6453 6454 final IPackageManager pm = AppGlobals.getPackageManager(); 6455 6456 // If this is not a content: uri, we can't do anything with it. 6457 if (!ContentResolver.SCHEME_CONTENT.equals(grantUri.uri.getScheme())) { 6458 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6459 "Can't grant URI permission for non-content URI: " + grantUri); 6460 return -1; 6461 } 6462 6463 final String authority = grantUri.uri.getAuthority(); 6464 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6465 if (pi == null) { 6466 Slog.w(TAG, "No content provider found for permission check: " + 6467 grantUri.uri.toSafeString()); 6468 return -1; 6469 } 6470 6471 int targetUid = lastTargetUid; 6472 if (targetUid < 0 && targetPkg != null) { 6473 try { 6474 targetUid = pm.getPackageUid(targetPkg, UserHandle.getUserId(callingUid)); 6475 if (targetUid < 0) { 6476 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6477 "Can't grant URI permission no uid for: " + targetPkg); 6478 return -1; 6479 } 6480 } catch (RemoteException ex) { 6481 return -1; 6482 } 6483 } 6484 6485 if (targetUid >= 0) { 6486 // First... does the target actually need this permission? 6487 if (checkHoldingPermissionsLocked(pm, pi, grantUri, targetUid, modeFlags)) { 6488 // No need to grant the target this permission. 6489 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6490 "Target " + targetPkg + " already has full permission to " + grantUri); 6491 return -1; 6492 } 6493 } else { 6494 // First... there is no target package, so can anyone access it? 6495 boolean allowed = pi.exported; 6496 if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) { 6497 if (pi.readPermission != null) { 6498 allowed = false; 6499 } 6500 } 6501 if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) { 6502 if (pi.writePermission != null) { 6503 allowed = false; 6504 } 6505 } 6506 if (allowed) { 6507 return -1; 6508 } 6509 } 6510 6511 /* There is a special cross user grant if: 6512 * - The target is on another user. 6513 * - Apps on the current user can access the uri without any uid permissions. 6514 * In this case, we grant a uri permission, even if the ContentProvider does not normally 6515 * grant uri permissions. 6516 */ 6517 boolean specialCrossUserGrant = UserHandle.getUserId(targetUid) != grantUri.sourceUserId 6518 && checkHoldingPermissionsInternalLocked(pm, pi, grantUri, callingUid, 6519 modeFlags, false /*without considering the uid permissions*/); 6520 6521 // Second... is the provider allowing granting of URI permissions? 6522 if (!specialCrossUserGrant) { 6523 if (!pi.grantUriPermissions) { 6524 throw new SecurityException("Provider " + pi.packageName 6525 + "/" + pi.name 6526 + " does not allow granting of Uri permissions (uri " 6527 + grantUri + ")"); 6528 } 6529 if (pi.uriPermissionPatterns != null) { 6530 final int N = pi.uriPermissionPatterns.length; 6531 boolean allowed = false; 6532 for (int i=0; i<N; i++) { 6533 if (pi.uriPermissionPatterns[i] != null 6534 && pi.uriPermissionPatterns[i].match(grantUri.uri.getPath())) { 6535 allowed = true; 6536 break; 6537 } 6538 } 6539 if (!allowed) { 6540 throw new SecurityException("Provider " + pi.packageName 6541 + "/" + pi.name 6542 + " does not allow granting of permission to path of Uri " 6543 + grantUri); 6544 } 6545 } 6546 } 6547 6548 // Third... does the caller itself have permission to access 6549 // this uri? 6550 if (UserHandle.getAppId(callingUid) != Process.SYSTEM_UID) { 6551 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 6552 // Require they hold a strong enough Uri permission 6553 if (!checkUriPermissionLocked(grantUri, callingUid, modeFlags)) { 6554 throw new SecurityException("Uid " + callingUid 6555 + " does not have permission to uri " + grantUri); 6556 } 6557 } 6558 } 6559 return targetUid; 6560 } 6561 6562 @Override 6563 public int checkGrantUriPermission(int callingUid, String targetPkg, Uri uri, 6564 final int modeFlags, int userId) { 6565 enforceNotIsolatedCaller("checkGrantUriPermission"); 6566 synchronized(this) { 6567 return checkGrantUriPermissionLocked(callingUid, targetPkg, 6568 new GrantUri(userId, uri, false), modeFlags, -1); 6569 } 6570 } 6571 6572 void grantUriPermissionUncheckedLocked(int targetUid, String targetPkg, GrantUri grantUri, 6573 final int modeFlags, UriPermissionOwner owner) { 6574 if (!Intent.isAccessUriMode(modeFlags)) { 6575 return; 6576 } 6577 6578 // So here we are: the caller has the assumed permission 6579 // to the uri, and the target doesn't. Let's now give this to 6580 // the target. 6581 6582 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6583 "Granting " + targetPkg + "/" + targetUid + " permission to " + grantUri); 6584 6585 final String authority = grantUri.uri.getAuthority(); 6586 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6587 if (pi == null) { 6588 Slog.w(TAG, "No content provider found for grant: " + grantUri.toSafeString()); 6589 return; 6590 } 6591 6592 if ((modeFlags & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0) { 6593 grantUri.prefix = true; 6594 } 6595 final UriPermission perm = findOrCreateUriPermissionLocked( 6596 pi.packageName, targetPkg, targetUid, grantUri); 6597 perm.grantModes(modeFlags, owner); 6598 } 6599 6600 void grantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 6601 final int modeFlags, UriPermissionOwner owner, int targetUserId) { 6602 if (targetPkg == null) { 6603 throw new NullPointerException("targetPkg"); 6604 } 6605 int targetUid; 6606 final IPackageManager pm = AppGlobals.getPackageManager(); 6607 try { 6608 targetUid = pm.getPackageUid(targetPkg, targetUserId); 6609 } catch (RemoteException ex) { 6610 return; 6611 } 6612 6613 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, modeFlags, 6614 targetUid); 6615 if (targetUid < 0) { 6616 return; 6617 } 6618 6619 grantUriPermissionUncheckedLocked(targetUid, targetPkg, grantUri, modeFlags, 6620 owner); 6621 } 6622 6623 static class NeededUriGrants extends ArrayList<GrantUri> { 6624 final String targetPkg; 6625 final int targetUid; 6626 final int flags; 6627 6628 NeededUriGrants(String targetPkg, int targetUid, int flags) { 6629 this.targetPkg = targetPkg; 6630 this.targetUid = targetUid; 6631 this.flags = flags; 6632 } 6633 } 6634 6635 /** 6636 * Like checkGrantUriPermissionLocked, but takes an Intent. 6637 */ 6638 NeededUriGrants checkGrantUriPermissionFromIntentLocked(int callingUid, 6639 String targetPkg, Intent intent, int mode, NeededUriGrants needed, int targetUserId) { 6640 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6641 "Checking URI perm to data=" + (intent != null ? intent.getData() : null) 6642 + " clip=" + (intent != null ? intent.getClipData() : null) 6643 + " from " + intent + "; flags=0x" 6644 + Integer.toHexString(intent != null ? intent.getFlags() : 0)); 6645 6646 if (targetPkg == null) { 6647 throw new NullPointerException("targetPkg"); 6648 } 6649 6650 if (intent == null) { 6651 return null; 6652 } 6653 Uri data = intent.getData(); 6654 ClipData clip = intent.getClipData(); 6655 if (data == null && clip == null) { 6656 return null; 6657 } 6658 // Default userId for uris in the intent (if they don't specify it themselves) 6659 int contentUserHint = intent.getContentUserHint(); 6660 if (contentUserHint == UserHandle.USER_CURRENT) { 6661 contentUserHint = UserHandle.getUserId(callingUid); 6662 } 6663 final IPackageManager pm = AppGlobals.getPackageManager(); 6664 int targetUid; 6665 if (needed != null) { 6666 targetUid = needed.targetUid; 6667 } else { 6668 try { 6669 targetUid = pm.getPackageUid(targetPkg, targetUserId); 6670 } catch (RemoteException ex) { 6671 return null; 6672 } 6673 if (targetUid < 0) { 6674 if (DEBUG_URI_PERMISSION) { 6675 Slog.v(TAG, "Can't grant URI permission no uid for: " + targetPkg 6676 + " on user " + targetUserId); 6677 } 6678 return null; 6679 } 6680 } 6681 if (data != null) { 6682 GrantUri grantUri = GrantUri.resolve(contentUserHint, data); 6683 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 6684 targetUid); 6685 if (targetUid > 0) { 6686 if (needed == null) { 6687 needed = new NeededUriGrants(targetPkg, targetUid, mode); 6688 } 6689 needed.add(grantUri); 6690 } 6691 } 6692 if (clip != null) { 6693 for (int i=0; i<clip.getItemCount(); i++) { 6694 Uri uri = clip.getItemAt(i).getUri(); 6695 if (uri != null) { 6696 GrantUri grantUri = GrantUri.resolve(contentUserHint, uri); 6697 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 6698 targetUid); 6699 if (targetUid > 0) { 6700 if (needed == null) { 6701 needed = new NeededUriGrants(targetPkg, targetUid, mode); 6702 } 6703 needed.add(grantUri); 6704 } 6705 } else { 6706 Intent clipIntent = clip.getItemAt(i).getIntent(); 6707 if (clipIntent != null) { 6708 NeededUriGrants newNeeded = checkGrantUriPermissionFromIntentLocked( 6709 callingUid, targetPkg, clipIntent, mode, needed, targetUserId); 6710 if (newNeeded != null) { 6711 needed = newNeeded; 6712 } 6713 } 6714 } 6715 } 6716 } 6717 6718 return needed; 6719 } 6720 6721 /** 6722 * Like grantUriPermissionUncheckedLocked, but takes an Intent. 6723 */ 6724 void grantUriPermissionUncheckedFromIntentLocked(NeededUriGrants needed, 6725 UriPermissionOwner owner) { 6726 if (needed != null) { 6727 for (int i=0; i<needed.size(); i++) { 6728 GrantUri grantUri = needed.get(i); 6729 grantUriPermissionUncheckedLocked(needed.targetUid, needed.targetPkg, 6730 grantUri, needed.flags, owner); 6731 } 6732 } 6733 } 6734 6735 void grantUriPermissionFromIntentLocked(int callingUid, 6736 String targetPkg, Intent intent, UriPermissionOwner owner, int targetUserId) { 6737 NeededUriGrants needed = checkGrantUriPermissionFromIntentLocked(callingUid, targetPkg, 6738 intent, intent != null ? intent.getFlags() : 0, null, targetUserId); 6739 if (needed == null) { 6740 return; 6741 } 6742 6743 grantUriPermissionUncheckedFromIntentLocked(needed, owner); 6744 } 6745 6746 @Override 6747 public void grantUriPermission(IApplicationThread caller, String targetPkg, Uri uri, 6748 final int modeFlags, int userId) { 6749 enforceNotIsolatedCaller("grantUriPermission"); 6750 GrantUri grantUri = new GrantUri(userId, uri, false); 6751 synchronized(this) { 6752 final ProcessRecord r = getRecordForAppLocked(caller); 6753 if (r == null) { 6754 throw new SecurityException("Unable to find app for caller " 6755 + caller 6756 + " when granting permission to uri " + grantUri); 6757 } 6758 if (targetPkg == null) { 6759 throw new IllegalArgumentException("null target"); 6760 } 6761 if (grantUri == null) { 6762 throw new IllegalArgumentException("null uri"); 6763 } 6764 6765 Preconditions.checkFlagsArgument(modeFlags, Intent.FLAG_GRANT_READ_URI_PERMISSION 6766 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION 6767 | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION 6768 | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION); 6769 6770 grantUriPermissionLocked(r.uid, targetPkg, grantUri, modeFlags, null, 6771 UserHandle.getUserId(r.uid)); 6772 } 6773 } 6774 6775 void removeUriPermissionIfNeededLocked(UriPermission perm) { 6776 if (perm.modeFlags == 0) { 6777 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 6778 perm.targetUid); 6779 if (perms != null) { 6780 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6781 "Removing " + perm.targetUid + " permission to " + perm.uri); 6782 6783 perms.remove(perm.uri); 6784 if (perms.isEmpty()) { 6785 mGrantedUriPermissions.remove(perm.targetUid); 6786 } 6787 } 6788 } 6789 } 6790 6791 private void revokeUriPermissionLocked(int callingUid, GrantUri grantUri, final int modeFlags) { 6792 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Revoking all granted permissions to " + grantUri); 6793 6794 final IPackageManager pm = AppGlobals.getPackageManager(); 6795 final String authority = grantUri.uri.getAuthority(); 6796 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6797 if (pi == null) { 6798 Slog.w(TAG, "No content provider found for permission revoke: " 6799 + grantUri.toSafeString()); 6800 return; 6801 } 6802 6803 // Does the caller have this permission on the URI? 6804 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 6805 // Right now, if you are not the original owner of the permission, 6806 // you are not allowed to revoke it. 6807 //if (!checkUriPermissionLocked(uri, callingUid, modeFlags)) { 6808 throw new SecurityException("Uid " + callingUid 6809 + " does not have permission to uri " + grantUri); 6810 //} 6811 } 6812 6813 boolean persistChanged = false; 6814 6815 // Go through all of the permissions and remove any that match. 6816 int N = mGrantedUriPermissions.size(); 6817 for (int i = 0; i < N; i++) { 6818 final int targetUid = mGrantedUriPermissions.keyAt(i); 6819 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6820 6821 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 6822 final UriPermission perm = it.next(); 6823 if (perm.uri.sourceUserId == grantUri.sourceUserId 6824 && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) { 6825 if (DEBUG_URI_PERMISSION) 6826 Slog.v(TAG, 6827 "Revoking " + perm.targetUid + " permission to " + perm.uri); 6828 persistChanged |= perm.revokeModes( 6829 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 6830 if (perm.modeFlags == 0) { 6831 it.remove(); 6832 } 6833 } 6834 } 6835 6836 if (perms.isEmpty()) { 6837 mGrantedUriPermissions.remove(targetUid); 6838 N--; 6839 i--; 6840 } 6841 } 6842 6843 if (persistChanged) { 6844 schedulePersistUriGrants(); 6845 } 6846 } 6847 6848 @Override 6849 public void revokeUriPermission(IApplicationThread caller, Uri uri, final int modeFlags, 6850 int userId) { 6851 enforceNotIsolatedCaller("revokeUriPermission"); 6852 synchronized(this) { 6853 final ProcessRecord r = getRecordForAppLocked(caller); 6854 if (r == null) { 6855 throw new SecurityException("Unable to find app for caller " 6856 + caller 6857 + " when revoking permission to uri " + uri); 6858 } 6859 if (uri == null) { 6860 Slog.w(TAG, "revokeUriPermission: null uri"); 6861 return; 6862 } 6863 6864 if (!Intent.isAccessUriMode(modeFlags)) { 6865 return; 6866 } 6867 6868 final IPackageManager pm = AppGlobals.getPackageManager(); 6869 final String authority = uri.getAuthority(); 6870 final ProviderInfo pi = getProviderInfoLocked(authority, userId); 6871 if (pi == null) { 6872 Slog.w(TAG, "No content provider found for permission revoke: " 6873 + uri.toSafeString()); 6874 return; 6875 } 6876 6877 revokeUriPermissionLocked(r.uid, new GrantUri(userId, uri, false), modeFlags); 6878 } 6879 } 6880 6881 /** 6882 * Remove any {@link UriPermission} granted <em>from</em> or <em>to</em> the 6883 * given package. 6884 * 6885 * @param packageName Package name to match, or {@code null} to apply to all 6886 * packages. 6887 * @param userHandle User to match, or {@link UserHandle#USER_ALL} to apply 6888 * to all users. 6889 * @param persistable If persistable grants should be removed. 6890 */ 6891 private void removeUriPermissionsForPackageLocked( 6892 String packageName, int userHandle, boolean persistable) { 6893 if (userHandle == UserHandle.USER_ALL && packageName == null) { 6894 throw new IllegalArgumentException("Must narrow by either package or user"); 6895 } 6896 6897 boolean persistChanged = false; 6898 6899 int N = mGrantedUriPermissions.size(); 6900 for (int i = 0; i < N; i++) { 6901 final int targetUid = mGrantedUriPermissions.keyAt(i); 6902 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6903 6904 // Only inspect grants matching user 6905 if (userHandle == UserHandle.USER_ALL 6906 || userHandle == UserHandle.getUserId(targetUid)) { 6907 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 6908 final UriPermission perm = it.next(); 6909 6910 // Only inspect grants matching package 6911 if (packageName == null || perm.sourcePkg.equals(packageName) 6912 || perm.targetPkg.equals(packageName)) { 6913 persistChanged |= perm.revokeModes( 6914 persistable ? ~0 : ~Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 6915 6916 // Only remove when no modes remain; any persisted grants 6917 // will keep this alive. 6918 if (perm.modeFlags == 0) { 6919 it.remove(); 6920 } 6921 } 6922 } 6923 6924 if (perms.isEmpty()) { 6925 mGrantedUriPermissions.remove(targetUid); 6926 N--; 6927 i--; 6928 } 6929 } 6930 } 6931 6932 if (persistChanged) { 6933 schedulePersistUriGrants(); 6934 } 6935 } 6936 6937 @Override 6938 public IBinder newUriPermissionOwner(String name) { 6939 enforceNotIsolatedCaller("newUriPermissionOwner"); 6940 synchronized(this) { 6941 UriPermissionOwner owner = new UriPermissionOwner(this, name); 6942 return owner.getExternalTokenLocked(); 6943 } 6944 } 6945 6946 @Override 6947 public void grantUriPermissionFromOwner(IBinder token, int fromUid, String targetPkg, Uri uri, 6948 final int modeFlags, int sourceUserId, int targetUserId) { 6949 synchronized(this) { 6950 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 6951 if (owner == null) { 6952 throw new IllegalArgumentException("Unknown owner: " + token); 6953 } 6954 if (fromUid != Binder.getCallingUid()) { 6955 if (Binder.getCallingUid() != Process.myUid()) { 6956 // Only system code can grant URI permissions on behalf 6957 // of other users. 6958 throw new SecurityException("nice try"); 6959 } 6960 } 6961 if (targetPkg == null) { 6962 throw new IllegalArgumentException("null target"); 6963 } 6964 if (uri == null) { 6965 throw new IllegalArgumentException("null uri"); 6966 } 6967 6968 grantUriPermissionLocked(fromUid, targetPkg, new GrantUri(sourceUserId, uri, false), 6969 modeFlags, owner, targetUserId); 6970 } 6971 } 6972 6973 @Override 6974 public void revokeUriPermissionFromOwner(IBinder token, Uri uri, int mode, int userId) { 6975 synchronized(this) { 6976 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 6977 if (owner == null) { 6978 throw new IllegalArgumentException("Unknown owner: " + token); 6979 } 6980 6981 if (uri == null) { 6982 owner.removeUriPermissionsLocked(mode); 6983 } else { 6984 owner.removeUriPermissionLocked(new GrantUri(userId, uri, false), mode); 6985 } 6986 } 6987 } 6988 6989 private void schedulePersistUriGrants() { 6990 if (!mHandler.hasMessages(PERSIST_URI_GRANTS_MSG)) { 6991 mHandler.sendMessageDelayed(mHandler.obtainMessage(PERSIST_URI_GRANTS_MSG), 6992 10 * DateUtils.SECOND_IN_MILLIS); 6993 } 6994 } 6995 6996 private void writeGrantedUriPermissions() { 6997 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "writeGrantedUriPermissions()"); 6998 6999 // Snapshot permissions so we can persist without lock 7000 ArrayList<UriPermission.Snapshot> persist = Lists.newArrayList(); 7001 synchronized (this) { 7002 final int size = mGrantedUriPermissions.size(); 7003 for (int i = 0; i < size; i++) { 7004 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 7005 for (UriPermission perm : perms.values()) { 7006 if (perm.persistedModeFlags != 0) { 7007 persist.add(perm.snapshot()); 7008 } 7009 } 7010 } 7011 } 7012 7013 FileOutputStream fos = null; 7014 try { 7015 fos = mGrantFile.startWrite(); 7016 7017 XmlSerializer out = new FastXmlSerializer(); 7018 out.setOutput(fos, "utf-8"); 7019 out.startDocument(null, true); 7020 out.startTag(null, TAG_URI_GRANTS); 7021 for (UriPermission.Snapshot perm : persist) { 7022 out.startTag(null, TAG_URI_GRANT); 7023 writeIntAttribute(out, ATTR_SOURCE_USER_ID, perm.uri.sourceUserId); 7024 writeIntAttribute(out, ATTR_TARGET_USER_ID, perm.targetUserId); 7025 out.attribute(null, ATTR_SOURCE_PKG, perm.sourcePkg); 7026 out.attribute(null, ATTR_TARGET_PKG, perm.targetPkg); 7027 out.attribute(null, ATTR_URI, String.valueOf(perm.uri.uri)); 7028 writeBooleanAttribute(out, ATTR_PREFIX, perm.uri.prefix); 7029 writeIntAttribute(out, ATTR_MODE_FLAGS, perm.persistedModeFlags); 7030 writeLongAttribute(out, ATTR_CREATED_TIME, perm.persistedCreateTime); 7031 out.endTag(null, TAG_URI_GRANT); 7032 } 7033 out.endTag(null, TAG_URI_GRANTS); 7034 out.endDocument(); 7035 7036 mGrantFile.finishWrite(fos); 7037 } catch (IOException e) { 7038 if (fos != null) { 7039 mGrantFile.failWrite(fos); 7040 } 7041 } 7042 } 7043 7044 private void readGrantedUriPermissionsLocked() { 7045 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "readGrantedUriPermissions()"); 7046 7047 final long now = System.currentTimeMillis(); 7048 7049 FileInputStream fis = null; 7050 try { 7051 fis = mGrantFile.openRead(); 7052 final XmlPullParser in = Xml.newPullParser(); 7053 in.setInput(fis, null); 7054 7055 int type; 7056 while ((type = in.next()) != END_DOCUMENT) { 7057 final String tag = in.getName(); 7058 if (type == START_TAG) { 7059 if (TAG_URI_GRANT.equals(tag)) { 7060 final int sourceUserId; 7061 final int targetUserId; 7062 final int userHandle = readIntAttribute(in, 7063 ATTR_USER_HANDLE, UserHandle.USER_NULL); 7064 if (userHandle != UserHandle.USER_NULL) { 7065 // For backwards compatibility. 7066 sourceUserId = userHandle; 7067 targetUserId = userHandle; 7068 } else { 7069 sourceUserId = readIntAttribute(in, ATTR_SOURCE_USER_ID); 7070 targetUserId = readIntAttribute(in, ATTR_TARGET_USER_ID); 7071 } 7072 final String sourcePkg = in.getAttributeValue(null, ATTR_SOURCE_PKG); 7073 final String targetPkg = in.getAttributeValue(null, ATTR_TARGET_PKG); 7074 final Uri uri = Uri.parse(in.getAttributeValue(null, ATTR_URI)); 7075 final boolean prefix = readBooleanAttribute(in, ATTR_PREFIX); 7076 final int modeFlags = readIntAttribute(in, ATTR_MODE_FLAGS); 7077 final long createdTime = readLongAttribute(in, ATTR_CREATED_TIME, now); 7078 7079 // Sanity check that provider still belongs to source package 7080 final ProviderInfo pi = getProviderInfoLocked( 7081 uri.getAuthority(), sourceUserId); 7082 if (pi != null && sourcePkg.equals(pi.packageName)) { 7083 int targetUid = -1; 7084 try { 7085 targetUid = AppGlobals.getPackageManager() 7086 .getPackageUid(targetPkg, targetUserId); 7087 } catch (RemoteException e) { 7088 } 7089 if (targetUid != -1) { 7090 final UriPermission perm = findOrCreateUriPermissionLocked( 7091 sourcePkg, targetPkg, targetUid, 7092 new GrantUri(sourceUserId, uri, prefix)); 7093 perm.initPersistedModes(modeFlags, createdTime); 7094 } 7095 } else { 7096 Slog.w(TAG, "Persisted grant for " + uri + " had source " + sourcePkg 7097 + " but instead found " + pi); 7098 } 7099 } 7100 } 7101 } 7102 } catch (FileNotFoundException e) { 7103 // Missing grants is okay 7104 } catch (IOException e) { 7105 Log.wtf(TAG, "Failed reading Uri grants", e); 7106 } catch (XmlPullParserException e) { 7107 Log.wtf(TAG, "Failed reading Uri grants", e); 7108 } finally { 7109 IoUtils.closeQuietly(fis); 7110 } 7111 } 7112 7113 @Override 7114 public void takePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 7115 enforceNotIsolatedCaller("takePersistableUriPermission"); 7116 7117 Preconditions.checkFlagsArgument(modeFlags, 7118 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 7119 7120 synchronized (this) { 7121 final int callingUid = Binder.getCallingUid(); 7122 boolean persistChanged = false; 7123 GrantUri grantUri = new GrantUri(userId, uri, false); 7124 7125 UriPermission exactPerm = findUriPermissionLocked(callingUid, 7126 new GrantUri(userId, uri, false)); 7127 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 7128 new GrantUri(userId, uri, true)); 7129 7130 final boolean exactValid = (exactPerm != null) 7131 && ((modeFlags & exactPerm.persistableModeFlags) == modeFlags); 7132 final boolean prefixValid = (prefixPerm != null) 7133 && ((modeFlags & prefixPerm.persistableModeFlags) == modeFlags); 7134 7135 if (!(exactValid || prefixValid)) { 7136 throw new SecurityException("No persistable permission grants found for UID " 7137 + callingUid + " and Uri " + grantUri.toSafeString()); 7138 } 7139 7140 if (exactValid) { 7141 persistChanged |= exactPerm.takePersistableModes(modeFlags); 7142 } 7143 if (prefixValid) { 7144 persistChanged |= prefixPerm.takePersistableModes(modeFlags); 7145 } 7146 7147 persistChanged |= maybePrunePersistedUriGrantsLocked(callingUid); 7148 7149 if (persistChanged) { 7150 schedulePersistUriGrants(); 7151 } 7152 } 7153 } 7154 7155 @Override 7156 public void releasePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 7157 enforceNotIsolatedCaller("releasePersistableUriPermission"); 7158 7159 Preconditions.checkFlagsArgument(modeFlags, 7160 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 7161 7162 synchronized (this) { 7163 final int callingUid = Binder.getCallingUid(); 7164 boolean persistChanged = false; 7165 7166 UriPermission exactPerm = findUriPermissionLocked(callingUid, 7167 new GrantUri(userId, uri, false)); 7168 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 7169 new GrantUri(userId, uri, true)); 7170 if (exactPerm == null && prefixPerm == null) { 7171 throw new SecurityException("No permission grants found for UID " + callingUid 7172 + " and Uri " + uri.toSafeString()); 7173 } 7174 7175 if (exactPerm != null) { 7176 persistChanged |= exactPerm.releasePersistableModes(modeFlags); 7177 removeUriPermissionIfNeededLocked(exactPerm); 7178 } 7179 if (prefixPerm != null) { 7180 persistChanged |= prefixPerm.releasePersistableModes(modeFlags); 7181 removeUriPermissionIfNeededLocked(prefixPerm); 7182 } 7183 7184 if (persistChanged) { 7185 schedulePersistUriGrants(); 7186 } 7187 } 7188 } 7189 7190 /** 7191 * Prune any older {@link UriPermission} for the given UID until outstanding 7192 * persisted grants are below {@link #MAX_PERSISTED_URI_GRANTS}. 7193 * 7194 * @return if any mutations occured that require persisting. 7195 */ 7196 private boolean maybePrunePersistedUriGrantsLocked(int uid) { 7197 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 7198 if (perms == null) return false; 7199 if (perms.size() < MAX_PERSISTED_URI_GRANTS) return false; 7200 7201 final ArrayList<UriPermission> persisted = Lists.newArrayList(); 7202 for (UriPermission perm : perms.values()) { 7203 if (perm.persistedModeFlags != 0) { 7204 persisted.add(perm); 7205 } 7206 } 7207 7208 final int trimCount = persisted.size() - MAX_PERSISTED_URI_GRANTS; 7209 if (trimCount <= 0) return false; 7210 7211 Collections.sort(persisted, new UriPermission.PersistedTimeComparator()); 7212 for (int i = 0; i < trimCount; i++) { 7213 final UriPermission perm = persisted.get(i); 7214 7215 if (DEBUG_URI_PERMISSION) { 7216 Slog.v(TAG, "Trimming grant created at " + perm.persistedCreateTime); 7217 } 7218 7219 perm.releasePersistableModes(~0); 7220 removeUriPermissionIfNeededLocked(perm); 7221 } 7222 7223 return true; 7224 } 7225 7226 @Override 7227 public ParceledListSlice<android.content.UriPermission> getPersistedUriPermissions( 7228 String packageName, boolean incoming) { 7229 enforceNotIsolatedCaller("getPersistedUriPermissions"); 7230 Preconditions.checkNotNull(packageName, "packageName"); 7231 7232 final int callingUid = Binder.getCallingUid(); 7233 final IPackageManager pm = AppGlobals.getPackageManager(); 7234 try { 7235 final int packageUid = pm.getPackageUid(packageName, UserHandle.getUserId(callingUid)); 7236 if (packageUid != callingUid) { 7237 throw new SecurityException( 7238 "Package " + packageName + " does not belong to calling UID " + callingUid); 7239 } 7240 } catch (RemoteException e) { 7241 throw new SecurityException("Failed to verify package name ownership"); 7242 } 7243 7244 final ArrayList<android.content.UriPermission> result = Lists.newArrayList(); 7245 synchronized (this) { 7246 if (incoming) { 7247 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 7248 callingUid); 7249 if (perms == null) { 7250 Slog.w(TAG, "No permission grants found for " + packageName); 7251 } else { 7252 for (UriPermission perm : perms.values()) { 7253 if (packageName.equals(perm.targetPkg) && perm.persistedModeFlags != 0) { 7254 result.add(perm.buildPersistedPublicApiObject()); 7255 } 7256 } 7257 } 7258 } else { 7259 final int size = mGrantedUriPermissions.size(); 7260 for (int i = 0; i < size; i++) { 7261 final ArrayMap<GrantUri, UriPermission> perms = 7262 mGrantedUriPermissions.valueAt(i); 7263 for (UriPermission perm : perms.values()) { 7264 if (packageName.equals(perm.sourcePkg) && perm.persistedModeFlags != 0) { 7265 result.add(perm.buildPersistedPublicApiObject()); 7266 } 7267 } 7268 } 7269 } 7270 } 7271 return new ParceledListSlice<android.content.UriPermission>(result); 7272 } 7273 7274 @Override 7275 public void showWaitingForDebugger(IApplicationThread who, boolean waiting) { 7276 synchronized (this) { 7277 ProcessRecord app = 7278 who != null ? getRecordForAppLocked(who) : null; 7279 if (app == null) return; 7280 7281 Message msg = Message.obtain(); 7282 msg.what = WAIT_FOR_DEBUGGER_MSG; 7283 msg.obj = app; 7284 msg.arg1 = waiting ? 1 : 0; 7285 mHandler.sendMessage(msg); 7286 } 7287 } 7288 7289 @Override 7290 public void getMemoryInfo(ActivityManager.MemoryInfo outInfo) { 7291 final long homeAppMem = mProcessList.getMemLevel(ProcessList.HOME_APP_ADJ); 7292 final long cachedAppMem = mProcessList.getMemLevel(ProcessList.CACHED_APP_MIN_ADJ); 7293 outInfo.availMem = Process.getFreeMemory(); 7294 outInfo.totalMem = Process.getTotalMemory(); 7295 outInfo.threshold = homeAppMem; 7296 outInfo.lowMemory = outInfo.availMem < (homeAppMem + ((cachedAppMem-homeAppMem)/2)); 7297 outInfo.hiddenAppThreshold = cachedAppMem; 7298 outInfo.secondaryServerThreshold = mProcessList.getMemLevel( 7299 ProcessList.SERVICE_ADJ); 7300 outInfo.visibleAppThreshold = mProcessList.getMemLevel( 7301 ProcessList.VISIBLE_APP_ADJ); 7302 outInfo.foregroundAppThreshold = mProcessList.getMemLevel( 7303 ProcessList.FOREGROUND_APP_ADJ); 7304 } 7305 7306 // ========================================================= 7307 // TASK MANAGEMENT 7308 // ========================================================= 7309 7310 @Override 7311 public List<IAppTask> getAppTasks() { 7312 final PackageManager pm = mContext.getPackageManager(); 7313 int callingUid = Binder.getCallingUid(); 7314 long ident = Binder.clearCallingIdentity(); 7315 7316 // Compose the list of packages for this id to test against 7317 HashSet<String> packages = new HashSet<String>(); 7318 String[] uidPackages = pm.getPackagesForUid(callingUid); 7319 for (int i = 0; i < uidPackages.length; i++) { 7320 packages.add(uidPackages[i]); 7321 } 7322 7323 synchronized(this) { 7324 ArrayList<IAppTask> list = new ArrayList<IAppTask>(); 7325 try { 7326 if (localLOGV) Slog.v(TAG, "getAppTasks"); 7327 7328 final int N = mRecentTasks.size(); 7329 for (int i = 0; i < N; i++) { 7330 TaskRecord tr = mRecentTasks.get(i); 7331 // Skip tasks that are not created by the caller 7332 if (packages.contains(tr.getBaseIntent().getComponent().getPackageName())) { 7333 ActivityManager.RecentTaskInfo taskInfo = 7334 createRecentTaskInfoFromTaskRecord(tr); 7335 AppTaskImpl taskImpl = new AppTaskImpl(taskInfo.persistentId, callingUid); 7336 list.add(taskImpl); 7337 } 7338 } 7339 } finally { 7340 Binder.restoreCallingIdentity(ident); 7341 } 7342 return list; 7343 } 7344 } 7345 7346 @Override 7347 public List<RunningTaskInfo> getTasks(int maxNum, int flags) { 7348 final int callingUid = Binder.getCallingUid(); 7349 ArrayList<RunningTaskInfo> list = new ArrayList<RunningTaskInfo>(); 7350 7351 synchronized(this) { 7352 if (localLOGV) Slog.v( 7353 TAG, "getTasks: max=" + maxNum + ", flags=" + flags); 7354 7355 final boolean allowed = checkCallingPermission( 7356 android.Manifest.permission.GET_TASKS) 7357 == PackageManager.PERMISSION_GRANTED; 7358 if (!allowed) { 7359 Slog.w(TAG, "getTasks: caller " + callingUid 7360 + " does not hold GET_TASKS; limiting output"); 7361 } 7362 7363 // TODO: Improve with MRU list from all ActivityStacks. 7364 mStackSupervisor.getTasksLocked(maxNum, list, callingUid, allowed); 7365 } 7366 7367 return list; 7368 } 7369 7370 TaskRecord getMostRecentTask() { 7371 return mRecentTasks.get(0); 7372 } 7373 7374 /** 7375 * Creates a new RecentTaskInfo from a TaskRecord. 7376 */ 7377 private ActivityManager.RecentTaskInfo createRecentTaskInfoFromTaskRecord(TaskRecord tr) { 7378 // Update the task description to reflect any changes in the task stack 7379 tr.updateTaskDescription(); 7380 7381 // Compose the recent task info 7382 ActivityManager.RecentTaskInfo rti = new ActivityManager.RecentTaskInfo(); 7383 rti.id = tr.getTopActivity() == null ? -1 : tr.taskId; 7384 rti.persistentId = tr.taskId; 7385 rti.baseIntent = new Intent(tr.getBaseIntent()); 7386 rti.origActivity = tr.origActivity; 7387 rti.description = tr.lastDescription; 7388 rti.stackId = tr.stack != null ? tr.stack.mStackId : -1; 7389 rti.userId = tr.userId; 7390 rti.taskDescription = new ActivityManager.TaskDescription(tr.lastTaskDescription); 7391 rti.firstActiveTime = tr.firstActiveTime; 7392 rti.lastActiveTime = tr.lastActiveTime; 7393 rti.affiliatedTaskId = tr.mAffiliatedTaskId; 7394 return rti; 7395 } 7396 7397 @Override 7398 public List<ActivityManager.RecentTaskInfo> getRecentTasks(int maxNum, int flags, int userId) { 7399 final int callingUid = Binder.getCallingUid(); 7400 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 7401 false, ALLOW_FULL_ONLY, "getRecentTasks", null); 7402 7403 final boolean includeProfiles = (flags & ActivityManager.RECENT_INCLUDE_PROFILES) != 0; 7404 final boolean withExcluded = (flags&ActivityManager.RECENT_WITH_EXCLUDED) != 0; 7405 synchronized (this) { 7406 final boolean allowed = checkCallingPermission(android.Manifest.permission.GET_TASKS) 7407 == PackageManager.PERMISSION_GRANTED; 7408 if (!allowed) { 7409 Slog.w(TAG, "getRecentTasks: caller " + callingUid 7410 + " does not hold GET_TASKS; limiting output"); 7411 } 7412 final boolean detailed = checkCallingPermission( 7413 android.Manifest.permission.GET_DETAILED_TASKS) 7414 == PackageManager.PERMISSION_GRANTED; 7415 7416 IPackageManager pm = AppGlobals.getPackageManager(); 7417 7418 final int N = mRecentTasks.size(); 7419 ArrayList<ActivityManager.RecentTaskInfo> res 7420 = new ArrayList<ActivityManager.RecentTaskInfo>( 7421 maxNum < N ? maxNum : N); 7422 7423 final Set<Integer> includedUsers; 7424 if (includeProfiles) { 7425 includedUsers = getProfileIdsLocked(userId); 7426 } else { 7427 includedUsers = new HashSet<Integer>(); 7428 } 7429 includedUsers.add(Integer.valueOf(userId)); 7430 7431 // Regroup affiliated tasks together. 7432 for (int i = 0; i < N; ) { 7433 TaskRecord task = mRecentTasks.remove(i); 7434 if (mTmpRecents.contains(task)) { 7435 continue; 7436 } 7437 int affiliatedTaskId = task.mAffiliatedTaskId; 7438 while (true) { 7439 TaskRecord next = task.mNextAffiliate; 7440 if (next == null) { 7441 break; 7442 } 7443 if (next.mAffiliatedTaskId != affiliatedTaskId) { 7444 Slog.e(TAG, "Error in Recents: next.affiliatedTaskId=" + 7445 next.mAffiliatedTaskId + " affiliatedTaskId=" + affiliatedTaskId); 7446 task.setNextAffiliate(null); 7447 if (next.mPrevAffiliate == task) { 7448 next.setPrevAffiliate(null); 7449 } 7450 break; 7451 } 7452 if (next.mPrevAffiliate != task) { 7453 Slog.e(TAG, "Error in Recents chain prev.mNextAffiliate=" + 7454 next.mPrevAffiliate + " task=" + task); 7455 next.setPrevAffiliate(null); 7456 break; 7457 } 7458 if (!mRecentTasks.contains(next)) { 7459 Slog.e(TAG, "Error in Recents: next=" + next + " not in mRecentTasks"); 7460 task.setNextAffiliate(null); 7461 if (next.mPrevAffiliate == task) { 7462 next.setPrevAffiliate(null); 7463 } 7464 break; 7465 } 7466 task = next; 7467 } 7468 // task is now the end of the list 7469 do { 7470 mRecentTasks.remove(task); 7471 mRecentTasks.add(i++, task); 7472 mTmpRecents.add(task); 7473 } while ((task = task.mPrevAffiliate) != null); 7474 } 7475 mTmpRecents.clear(); 7476 // mRecentTasks is now in sorted, affiliated order. 7477 7478 for (int i=0; i<N && maxNum > 0; i++) { 7479 TaskRecord tr = mRecentTasks.get(i); 7480 // Only add calling user or related users recent tasks 7481 if (!includedUsers.contains(Integer.valueOf(tr.userId))) continue; 7482 7483 // Return the entry if desired by the caller. We always return 7484 // the first entry, because callers always expect this to be the 7485 // foreground app. We may filter others if the caller has 7486 // not supplied RECENT_WITH_EXCLUDED and there is some reason 7487 // we should exclude the entry. 7488 7489 if (i == 0 7490 || withExcluded 7491 || (tr.intent == null) 7492 || ((tr.intent.getFlags() & Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS) 7493 == 0)) { 7494 if (!allowed) { 7495 // If the caller doesn't have the GET_TASKS permission, then only 7496 // allow them to see a small subset of tasks -- their own and home. 7497 if (!tr.isHomeTask() && tr.creatorUid != callingUid) { 7498 continue; 7499 } 7500 } 7501 if (tr.autoRemoveRecents && tr.getTopActivity() == null) { 7502 // Don't include auto remove tasks that are finished or finishing. 7503 continue; 7504 } 7505 7506 ActivityManager.RecentTaskInfo rti = createRecentTaskInfoFromTaskRecord(tr); 7507 if (!detailed) { 7508 rti.baseIntent.replaceExtras((Bundle)null); 7509 } 7510 7511 if ((flags&ActivityManager.RECENT_IGNORE_UNAVAILABLE) != 0) { 7512 // Check whether this activity is currently available. 7513 try { 7514 if (rti.origActivity != null) { 7515 if (pm.getActivityInfo(rti.origActivity, 0, userId) 7516 == null) { 7517 continue; 7518 } 7519 } else if (rti.baseIntent != null) { 7520 if (pm.queryIntentActivities(rti.baseIntent, 7521 null, 0, userId) == null) { 7522 continue; 7523 } 7524 } 7525 } catch (RemoteException e) { 7526 // Will never happen. 7527 } 7528 } 7529 7530 res.add(rti); 7531 maxNum--; 7532 } 7533 } 7534 return res; 7535 } 7536 } 7537 7538 private TaskRecord recentTaskForIdLocked(int id) { 7539 final int N = mRecentTasks.size(); 7540 for (int i=0; i<N; i++) { 7541 TaskRecord tr = mRecentTasks.get(i); 7542 if (tr.taskId == id) { 7543 return tr; 7544 } 7545 } 7546 return null; 7547 } 7548 7549 @Override 7550 public ActivityManager.TaskThumbnail getTaskThumbnail(int id) { 7551 synchronized (this) { 7552 enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER, 7553 "getTaskThumbnail()"); 7554 TaskRecord tr = recentTaskForIdLocked(id); 7555 if (tr != null) { 7556 return tr.getTaskThumbnailLocked(); 7557 } 7558 } 7559 return null; 7560 } 7561 7562 @Override 7563 public void setTaskDescription(IBinder token, ActivityManager.TaskDescription td) { 7564 synchronized (this) { 7565 ActivityRecord r = ActivityRecord.isInStackLocked(token); 7566 if (r != null) { 7567 r.taskDescription = td; 7568 r.task.updateTaskDescription(); 7569 } 7570 } 7571 } 7572 7573 private void killUnneededProcessLocked(ProcessRecord pr, String reason) { 7574 if (!pr.killedByAm) { 7575 Slog.i(TAG, "Killing " + pr.toShortString() + " (adj " + pr.setAdj + "): " + reason); 7576 EventLog.writeEvent(EventLogTags.AM_KILL, pr.userId, pr.pid, 7577 pr.processName, pr.setAdj, reason); 7578 pr.killedByAm = true; 7579 Process.killProcessQuiet(pr.pid); 7580 Process.killProcessGroup(pr.info.uid, pr.pid); 7581 } 7582 } 7583 7584 private void cleanUpRemovedTaskLocked(TaskRecord tr, int flags) { 7585 tr.disposeThumbnail(); 7586 mRecentTasks.remove(tr); 7587 tr.closeRecentsChain(); 7588 final boolean killProcesses = (flags&ActivityManager.REMOVE_TASK_KILL_PROCESS) != 0; 7589 Intent baseIntent = new Intent( 7590 tr.intent != null ? tr.intent : tr.affinityIntent); 7591 ComponentName component = baseIntent.getComponent(); 7592 if (component == null) { 7593 Slog.w(TAG, "Now component for base intent of task: " + tr); 7594 return; 7595 } 7596 7597 // Find any running services associated with this app. 7598 mServices.cleanUpRemovedTaskLocked(tr, component, baseIntent); 7599 7600 if (killProcesses) { 7601 // Find any running processes associated with this app. 7602 final String pkg = component.getPackageName(); 7603 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 7604 ArrayMap<String, SparseArray<ProcessRecord>> pmap = mProcessNames.getMap(); 7605 for (int i=0; i<pmap.size(); i++) { 7606 SparseArray<ProcessRecord> uids = pmap.valueAt(i); 7607 for (int j=0; j<uids.size(); j++) { 7608 ProcessRecord proc = uids.valueAt(j); 7609 if (proc.userId != tr.userId) { 7610 continue; 7611 } 7612 if (!proc.pkgList.containsKey(pkg)) { 7613 continue; 7614 } 7615 procs.add(proc); 7616 } 7617 } 7618 7619 // Kill the running processes. 7620 for (int i=0; i<procs.size(); i++) { 7621 ProcessRecord pr = procs.get(i); 7622 if (pr == mHomeProcess) { 7623 // Don't kill the home process along with tasks from the same package. 7624 continue; 7625 } 7626 if (pr.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 7627 killUnneededProcessLocked(pr, "remove task"); 7628 } else { 7629 pr.waitingToKill = "remove task"; 7630 } 7631 } 7632 } 7633 } 7634 7635 /** 7636 * Removes the task with the specified task id. 7637 * 7638 * @param taskId Identifier of the task to be removed. 7639 * @param flags Additional operational flags. May be 0 or 7640 * {@link ActivityManager#REMOVE_TASK_KILL_PROCESS}. 7641 * @return Returns true if the given task was found and removed. 7642 */ 7643 private boolean removeTaskByIdLocked(int taskId, int flags) { 7644 TaskRecord tr = recentTaskForIdLocked(taskId); 7645 if (tr != null) { 7646 tr.removeTaskActivitiesLocked(); 7647 cleanUpRemovedTaskLocked(tr, flags); 7648 if (tr.isPersistable) { 7649 notifyTaskPersisterLocked(null, true); 7650 } 7651 return true; 7652 } 7653 return false; 7654 } 7655 7656 @Override 7657 public boolean removeTask(int taskId, int flags) { 7658 synchronized (this) { 7659 enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, 7660 "removeTask()"); 7661 long ident = Binder.clearCallingIdentity(); 7662 try { 7663 return removeTaskByIdLocked(taskId, flags); 7664 } finally { 7665 Binder.restoreCallingIdentity(ident); 7666 } 7667 } 7668 } 7669 7670 /** 7671 * TODO: Add mController hook 7672 */ 7673 @Override 7674 public void moveTaskToFront(int taskId, int flags, Bundle options) { 7675 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7676 "moveTaskToFront()"); 7677 7678 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToFront: moving taskId=" + taskId); 7679 synchronized(this) { 7680 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7681 Binder.getCallingUid(), "Task to front")) { 7682 ActivityOptions.abort(options); 7683 return; 7684 } 7685 final long origId = Binder.clearCallingIdentity(); 7686 try { 7687 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 7688 if (task == null) { 7689 return; 7690 } 7691 if (mStackSupervisor.isLockTaskModeViolation(task)) { 7692 mStackSupervisor.showLockTaskToast(); 7693 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode"); 7694 return; 7695 } 7696 final ActivityRecord prev = mStackSupervisor.topRunningActivityLocked(); 7697 if (prev != null && prev.isRecentsActivity()) { 7698 task.setTaskToReturnTo(ActivityRecord.RECENTS_ACTIVITY_TYPE); 7699 } 7700 mStackSupervisor.findTaskToMoveToFrontLocked(task, flags, options); 7701 } finally { 7702 Binder.restoreCallingIdentity(origId); 7703 } 7704 ActivityOptions.abort(options); 7705 } 7706 } 7707 7708 @Override 7709 public void moveTaskToBack(int taskId) { 7710 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7711 "moveTaskToBack()"); 7712 7713 synchronized(this) { 7714 TaskRecord tr = recentTaskForIdLocked(taskId); 7715 if (tr != null) { 7716 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToBack: moving task=" + tr); 7717 ActivityStack stack = tr.stack; 7718 if (stack.mResumedActivity != null && stack.mResumedActivity.task == tr) { 7719 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7720 Binder.getCallingUid(), "Task to back")) { 7721 return; 7722 } 7723 } 7724 final long origId = Binder.clearCallingIdentity(); 7725 try { 7726 stack.moveTaskToBackLocked(taskId, null); 7727 } finally { 7728 Binder.restoreCallingIdentity(origId); 7729 } 7730 } 7731 } 7732 } 7733 7734 /** 7735 * Moves an activity, and all of the other activities within the same task, to the bottom 7736 * of the history stack. The activity's order within the task is unchanged. 7737 * 7738 * @param token A reference to the activity we wish to move 7739 * @param nonRoot If false then this only works if the activity is the root 7740 * of a task; if true it will work for any activity in a task. 7741 * @return Returns true if the move completed, false if not. 7742 */ 7743 @Override 7744 public boolean moveActivityTaskToBack(IBinder token, boolean nonRoot) { 7745 enforceNotIsolatedCaller("moveActivityTaskToBack"); 7746 synchronized(this) { 7747 final long origId = Binder.clearCallingIdentity(); 7748 int taskId = ActivityRecord.getTaskForActivityLocked(token, !nonRoot); 7749 if (taskId >= 0) { 7750 return ActivityRecord.getStackLocked(token).moveTaskToBackLocked(taskId, null); 7751 } 7752 Binder.restoreCallingIdentity(origId); 7753 } 7754 return false; 7755 } 7756 7757 @Override 7758 public void moveTaskBackwards(int task) { 7759 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7760 "moveTaskBackwards()"); 7761 7762 synchronized(this) { 7763 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7764 Binder.getCallingUid(), "Task backwards")) { 7765 return; 7766 } 7767 final long origId = Binder.clearCallingIdentity(); 7768 moveTaskBackwardsLocked(task); 7769 Binder.restoreCallingIdentity(origId); 7770 } 7771 } 7772 7773 private final void moveTaskBackwardsLocked(int task) { 7774 Slog.e(TAG, "moveTaskBackwards not yet implemented!"); 7775 } 7776 7777 @Override 7778 public IBinder getHomeActivityToken() throws RemoteException { 7779 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7780 "getHomeActivityToken()"); 7781 synchronized (this) { 7782 return mStackSupervisor.getHomeActivityToken(); 7783 } 7784 } 7785 7786 @Override 7787 public IActivityContainer createActivityContainer(IBinder parentActivityToken, 7788 IActivityContainerCallback callback) throws RemoteException { 7789 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7790 "createActivityContainer()"); 7791 synchronized (this) { 7792 if (parentActivityToken == null) { 7793 throw new IllegalArgumentException("parent token must not be null"); 7794 } 7795 ActivityRecord r = ActivityRecord.forToken(parentActivityToken); 7796 if (r == null) { 7797 return null; 7798 } 7799 if (callback == null) { 7800 throw new IllegalArgumentException("callback must not be null"); 7801 } 7802 return mStackSupervisor.createActivityContainer(r, callback); 7803 } 7804 } 7805 7806 @Override 7807 public void deleteActivityContainer(IActivityContainer container) throws RemoteException { 7808 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7809 "deleteActivityContainer()"); 7810 synchronized (this) { 7811 mStackSupervisor.deleteActivityContainer(container); 7812 } 7813 } 7814 7815 @Override 7816 public IActivityContainer getEnclosingActivityContainer(IBinder activityToken) 7817 throws RemoteException { 7818 synchronized (this) { 7819 ActivityStack stack = ActivityRecord.getStackLocked(activityToken); 7820 if (stack != null) { 7821 return stack.mActivityContainer; 7822 } 7823 return null; 7824 } 7825 } 7826 7827 @Override 7828 public void moveTaskToStack(int taskId, int stackId, boolean toTop) { 7829 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7830 "moveTaskToStack()"); 7831 if (stackId == HOME_STACK_ID) { 7832 Slog.e(TAG, "moveTaskToStack: Attempt to move task " + taskId + " to home stack", 7833 new RuntimeException("here").fillInStackTrace()); 7834 } 7835 synchronized (this) { 7836 long ident = Binder.clearCallingIdentity(); 7837 try { 7838 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToStack: moving task=" + taskId + " to stackId=" 7839 + stackId + " toTop=" + toTop); 7840 mStackSupervisor.moveTaskToStack(taskId, stackId, toTop); 7841 } finally { 7842 Binder.restoreCallingIdentity(ident); 7843 } 7844 } 7845 } 7846 7847 @Override 7848 public void resizeStack(int stackBoxId, Rect bounds) { 7849 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7850 "resizeStackBox()"); 7851 long ident = Binder.clearCallingIdentity(); 7852 try { 7853 mWindowManager.resizeStack(stackBoxId, bounds); 7854 } finally { 7855 Binder.restoreCallingIdentity(ident); 7856 } 7857 } 7858 7859 @Override 7860 public List<StackInfo> getAllStackInfos() { 7861 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7862 "getAllStackInfos()"); 7863 long ident = Binder.clearCallingIdentity(); 7864 try { 7865 synchronized (this) { 7866 return mStackSupervisor.getAllStackInfosLocked(); 7867 } 7868 } finally { 7869 Binder.restoreCallingIdentity(ident); 7870 } 7871 } 7872 7873 @Override 7874 public StackInfo getStackInfo(int stackId) { 7875 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7876 "getStackInfo()"); 7877 long ident = Binder.clearCallingIdentity(); 7878 try { 7879 synchronized (this) { 7880 return mStackSupervisor.getStackInfoLocked(stackId); 7881 } 7882 } finally { 7883 Binder.restoreCallingIdentity(ident); 7884 } 7885 } 7886 7887 @Override 7888 public boolean isInHomeStack(int taskId) { 7889 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7890 "getStackInfo()"); 7891 long ident = Binder.clearCallingIdentity(); 7892 try { 7893 synchronized (this) { 7894 TaskRecord tr = recentTaskForIdLocked(taskId); 7895 return tr != null && tr.stack != null && tr.stack.isHomeStack(); 7896 } 7897 } finally { 7898 Binder.restoreCallingIdentity(ident); 7899 } 7900 } 7901 7902 @Override 7903 public int getTaskForActivity(IBinder token, boolean onlyRoot) { 7904 synchronized(this) { 7905 return ActivityRecord.getTaskForActivityLocked(token, onlyRoot); 7906 } 7907 } 7908 7909 private boolean isLockTaskAuthorized(String pkg) { 7910 final DevicePolicyManager dpm = (DevicePolicyManager) 7911 mContext.getSystemService(Context.DEVICE_POLICY_SERVICE); 7912 try { 7913 int uid = mContext.getPackageManager().getPackageUid(pkg, 7914 Binder.getCallingUserHandle().getIdentifier()); 7915 return (uid == Binder.getCallingUid()) && dpm != null && dpm.isLockTaskPermitted(pkg); 7916 } catch (NameNotFoundException e) { 7917 return false; 7918 } 7919 } 7920 7921 void startLockTaskMode(TaskRecord task) { 7922 final String pkg; 7923 synchronized (this) { 7924 pkg = task.intent.getComponent().getPackageName(); 7925 } 7926 boolean isSystemInitiated = Binder.getCallingUid() == Process.SYSTEM_UID; 7927 if (!isSystemInitiated && !isLockTaskAuthorized(pkg)) { 7928 final TaskRecord taskRecord = task; 7929 mHandler.post(new Runnable() { 7930 @Override 7931 public void run() { 7932 mLockToAppRequest.showLockTaskPrompt(taskRecord); 7933 } 7934 }); 7935 return; 7936 } 7937 long ident = Binder.clearCallingIdentity(); 7938 try { 7939 synchronized (this) { 7940 // Since we lost lock on task, make sure it is still there. 7941 task = mStackSupervisor.anyTaskForIdLocked(task.taskId); 7942 if (task != null) { 7943 if (!isSystemInitiated 7944 && ((mFocusedActivity == null) || (task != mFocusedActivity.task))) { 7945 throw new IllegalArgumentException("Invalid task, not in foreground"); 7946 } 7947 mStackSupervisor.setLockTaskModeLocked(task, !isSystemInitiated); 7948 } 7949 } 7950 } finally { 7951 Binder.restoreCallingIdentity(ident); 7952 } 7953 } 7954 7955 @Override 7956 public void startLockTaskMode(int taskId) { 7957 final TaskRecord task; 7958 long ident = Binder.clearCallingIdentity(); 7959 try { 7960 synchronized (this) { 7961 task = mStackSupervisor.anyTaskForIdLocked(taskId); 7962 } 7963 } finally { 7964 Binder.restoreCallingIdentity(ident); 7965 } 7966 if (task != null) { 7967 startLockTaskMode(task); 7968 } 7969 } 7970 7971 @Override 7972 public void startLockTaskMode(IBinder token) { 7973 final TaskRecord task; 7974 long ident = Binder.clearCallingIdentity(); 7975 try { 7976 synchronized (this) { 7977 final ActivityRecord r = ActivityRecord.forToken(token); 7978 if (r == null) { 7979 return; 7980 } 7981 task = r.task; 7982 } 7983 } finally { 7984 Binder.restoreCallingIdentity(ident); 7985 } 7986 if (task != null) { 7987 startLockTaskMode(task); 7988 } 7989 } 7990 7991 @Override 7992 public void startLockTaskModeOnCurrent() throws RemoteException { 7993 checkCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS); 7994 ActivityRecord r = null; 7995 synchronized (this) { 7996 r = mStackSupervisor.topRunningActivityLocked(); 7997 } 7998 startLockTaskMode(r.task); 7999 } 8000 8001 @Override 8002 public void stopLockTaskMode() { 8003 // Verify that the user matches the package of the intent for the TaskRecord 8004 // we are locked to or systtem. This will ensure the same caller for startLockTaskMode 8005 // and stopLockTaskMode. 8006 final int callingUid = Binder.getCallingUid(); 8007 if (callingUid != Process.SYSTEM_UID) { 8008 try { 8009 String pkg = 8010 mStackSupervisor.mLockTaskModeTask.intent.getComponent().getPackageName(); 8011 int uid = mContext.getPackageManager().getPackageUid(pkg, 8012 Binder.getCallingUserHandle().getIdentifier()); 8013 if (uid != callingUid) { 8014 throw new SecurityException("Invalid uid, expected " + uid); 8015 } 8016 } catch (NameNotFoundException e) { 8017 Log.d(TAG, "stopLockTaskMode " + e); 8018 return; 8019 } 8020 } 8021 long ident = Binder.clearCallingIdentity(); 8022 try { 8023 Log.d(TAG, "stopLockTaskMode"); 8024 // Stop lock task 8025 synchronized (this) { 8026 mStackSupervisor.setLockTaskModeLocked(null, false); 8027 } 8028 } finally { 8029 Binder.restoreCallingIdentity(ident); 8030 } 8031 } 8032 8033 @Override 8034 public void stopLockTaskModeOnCurrent() throws RemoteException { 8035 checkCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS); 8036 long ident = Binder.clearCallingIdentity(); 8037 try { 8038 stopLockTaskMode(); 8039 } finally { 8040 Binder.restoreCallingIdentity(ident); 8041 } 8042 } 8043 8044 @Override 8045 public boolean isInLockTaskMode() { 8046 synchronized (this) { 8047 return mStackSupervisor.isInLockTaskMode(); 8048 } 8049 } 8050 8051 // ========================================================= 8052 // CONTENT PROVIDERS 8053 // ========================================================= 8054 8055 private final List<ProviderInfo> generateApplicationProvidersLocked(ProcessRecord app) { 8056 List<ProviderInfo> providers = null; 8057 try { 8058 providers = AppGlobals.getPackageManager(). 8059 queryContentProviders(app.processName, app.uid, 8060 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS); 8061 } catch (RemoteException ex) { 8062 } 8063 if (DEBUG_MU) 8064 Slog.v(TAG_MU, "generateApplicationProvidersLocked, app.info.uid = " + app.uid); 8065 int userId = app.userId; 8066 if (providers != null) { 8067 int N = providers.size(); 8068 app.pubProviders.ensureCapacity(N + app.pubProviders.size()); 8069 for (int i=0; i<N; i++) { 8070 ProviderInfo cpi = 8071 (ProviderInfo)providers.get(i); 8072 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo, 8073 cpi.name, cpi.flags); 8074 if (singleton && UserHandle.getUserId(app.uid) != 0) { 8075 // This is a singleton provider, but a user besides the 8076 // default user is asking to initialize a process it runs 8077 // in... well, no, it doesn't actually run in this process, 8078 // it runs in the process of the default user. Get rid of it. 8079 providers.remove(i); 8080 N--; 8081 i--; 8082 continue; 8083 } 8084 8085 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 8086 ContentProviderRecord cpr = mProviderMap.getProviderByClass(comp, userId); 8087 if (cpr == null) { 8088 cpr = new ContentProviderRecord(this, cpi, app.info, comp, singleton); 8089 mProviderMap.putProviderByClass(comp, cpr); 8090 } 8091 if (DEBUG_MU) 8092 Slog.v(TAG_MU, "generateApplicationProvidersLocked, cpi.uid = " + cpr.uid); 8093 app.pubProviders.put(cpi.name, cpr); 8094 if (!cpi.multiprocess || !"android".equals(cpi.packageName)) { 8095 // Don't add this if it is a platform component that is marked 8096 // to run in multiple processes, because this is actually 8097 // part of the framework so doesn't make sense to track as a 8098 // separate apk in the process. 8099 app.addPackage(cpi.applicationInfo.packageName, cpi.applicationInfo.versionCode, 8100 mProcessStats); 8101 } 8102 ensurePackageDexOpt(cpi.applicationInfo.packageName); 8103 } 8104 } 8105 return providers; 8106 } 8107 8108 /** 8109 * Check if {@link ProcessRecord} has a possible chance at accessing the 8110 * given {@link ProviderInfo}. Final permission checking is always done 8111 * in {@link ContentProvider}. 8112 */ 8113 private final String checkContentProviderPermissionLocked( 8114 ProviderInfo cpi, ProcessRecord r, int userId, boolean checkUser) { 8115 final int callingPid = (r != null) ? r.pid : Binder.getCallingPid(); 8116 final int callingUid = (r != null) ? r.uid : Binder.getCallingUid(); 8117 boolean checkedGrants = false; 8118 if (checkUser) { 8119 // Looking for cross-user grants before enforcing the typical cross-users permissions 8120 int tmpTargetUserId = unsafeConvertIncomingUser(userId); 8121 if (tmpTargetUserId != UserHandle.getUserId(callingUid)) { 8122 if (checkAuthorityGrants(callingUid, cpi, tmpTargetUserId, checkUser)) { 8123 return null; 8124 } 8125 checkedGrants = true; 8126 } 8127 userId = handleIncomingUser(callingPid, callingUid, userId, 8128 false, ALLOW_NON_FULL, 8129 "checkContentProviderPermissionLocked " + cpi.authority, null); 8130 if (userId != tmpTargetUserId) { 8131 // When we actually went to determine the final targer user ID, this ended 8132 // up different than our initial check for the authority. This is because 8133 // they had asked for USER_CURRENT_OR_SELF and we ended up switching to 8134 // SELF. So we need to re-check the grants again. 8135 checkedGrants = false; 8136 } 8137 } 8138 if (checkComponentPermission(cpi.readPermission, callingPid, callingUid, 8139 cpi.applicationInfo.uid, cpi.exported) 8140 == PackageManager.PERMISSION_GRANTED) { 8141 return null; 8142 } 8143 if (checkComponentPermission(cpi.writePermission, callingPid, callingUid, 8144 cpi.applicationInfo.uid, cpi.exported) 8145 == PackageManager.PERMISSION_GRANTED) { 8146 return null; 8147 } 8148 8149 PathPermission[] pps = cpi.pathPermissions; 8150 if (pps != null) { 8151 int i = pps.length; 8152 while (i > 0) { 8153 i--; 8154 PathPermission pp = pps[i]; 8155 String pprperm = pp.getReadPermission(); 8156 if (pprperm != null && checkComponentPermission(pprperm, callingPid, callingUid, 8157 cpi.applicationInfo.uid, cpi.exported) 8158 == PackageManager.PERMISSION_GRANTED) { 8159 return null; 8160 } 8161 String ppwperm = pp.getWritePermission(); 8162 if (ppwperm != null && checkComponentPermission(ppwperm, callingPid, callingUid, 8163 cpi.applicationInfo.uid, cpi.exported) 8164 == PackageManager.PERMISSION_GRANTED) { 8165 return null; 8166 } 8167 } 8168 } 8169 if (!checkedGrants && checkAuthorityGrants(callingUid, cpi, userId, checkUser)) { 8170 return null; 8171 } 8172 8173 String msg; 8174 if (!cpi.exported) { 8175 msg = "Permission Denial: opening provider " + cpi.name 8176 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 8177 + ", uid=" + callingUid + ") that is not exported from uid " 8178 + cpi.applicationInfo.uid; 8179 } else { 8180 msg = "Permission Denial: opening provider " + cpi.name 8181 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 8182 + ", uid=" + callingUid + ") requires " 8183 + cpi.readPermission + " or " + cpi.writePermission; 8184 } 8185 Slog.w(TAG, msg); 8186 return msg; 8187 } 8188 8189 /** 8190 * Returns if the ContentProvider has granted a uri to callingUid 8191 */ 8192 boolean checkAuthorityGrants(int callingUid, ProviderInfo cpi, int userId, boolean checkUser) { 8193 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 8194 if (perms != null) { 8195 for (int i=perms.size()-1; i>=0; i--) { 8196 GrantUri grantUri = perms.keyAt(i); 8197 if (grantUri.sourceUserId == userId || !checkUser) { 8198 if (matchesProvider(grantUri.uri, cpi)) { 8199 return true; 8200 } 8201 } 8202 } 8203 } 8204 return false; 8205 } 8206 8207 /** 8208 * Returns true if the uri authority is one of the authorities specified in the provider. 8209 */ 8210 boolean matchesProvider(Uri uri, ProviderInfo cpi) { 8211 String uriAuth = uri.getAuthority(); 8212 String cpiAuth = cpi.authority; 8213 if (cpiAuth.indexOf(';') == -1) { 8214 return cpiAuth.equals(uriAuth); 8215 } 8216 String[] cpiAuths = cpiAuth.split(";"); 8217 int length = cpiAuths.length; 8218 for (int i = 0; i < length; i++) { 8219 if (cpiAuths[i].equals(uriAuth)) return true; 8220 } 8221 return false; 8222 } 8223 8224 ContentProviderConnection incProviderCountLocked(ProcessRecord r, 8225 final ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 8226 if (r != null) { 8227 for (int i=0; i<r.conProviders.size(); i++) { 8228 ContentProviderConnection conn = r.conProviders.get(i); 8229 if (conn.provider == cpr) { 8230 if (DEBUG_PROVIDER) Slog.v(TAG, 8231 "Adding provider requested by " 8232 + r.processName + " from process " 8233 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 8234 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 8235 if (stable) { 8236 conn.stableCount++; 8237 conn.numStableIncs++; 8238 } else { 8239 conn.unstableCount++; 8240 conn.numUnstableIncs++; 8241 } 8242 return conn; 8243 } 8244 } 8245 ContentProviderConnection conn = new ContentProviderConnection(cpr, r); 8246 if (stable) { 8247 conn.stableCount = 1; 8248 conn.numStableIncs = 1; 8249 } else { 8250 conn.unstableCount = 1; 8251 conn.numUnstableIncs = 1; 8252 } 8253 cpr.connections.add(conn); 8254 r.conProviders.add(conn); 8255 return conn; 8256 } 8257 cpr.addExternalProcessHandleLocked(externalProcessToken); 8258 return null; 8259 } 8260 8261 boolean decProviderCountLocked(ContentProviderConnection conn, 8262 ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 8263 if (conn != null) { 8264 cpr = conn.provider; 8265 if (DEBUG_PROVIDER) Slog.v(TAG, 8266 "Removing provider requested by " 8267 + conn.client.processName + " from process " 8268 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 8269 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 8270 if (stable) { 8271 conn.stableCount--; 8272 } else { 8273 conn.unstableCount--; 8274 } 8275 if (conn.stableCount == 0 && conn.unstableCount == 0) { 8276 cpr.connections.remove(conn); 8277 conn.client.conProviders.remove(conn); 8278 return true; 8279 } 8280 return false; 8281 } 8282 cpr.removeExternalProcessHandleLocked(externalProcessToken); 8283 return false; 8284 } 8285 8286 private final ContentProviderHolder getContentProviderImpl(IApplicationThread caller, 8287 String name, IBinder token, boolean stable, int userId) { 8288 ContentProviderRecord cpr; 8289 ContentProviderConnection conn = null; 8290 ProviderInfo cpi = null; 8291 8292 synchronized(this) { 8293 ProcessRecord r = null; 8294 if (caller != null) { 8295 r = getRecordForAppLocked(caller); 8296 if (r == null) { 8297 throw new SecurityException( 8298 "Unable to find app for caller " + caller 8299 + " (pid=" + Binder.getCallingPid() 8300 + ") when getting content provider " + name); 8301 } 8302 } 8303 8304 boolean checkCrossUser = true; 8305 8306 // First check if this content provider has been published... 8307 cpr = mProviderMap.getProviderByName(name, userId); 8308 // If that didn't work, check if it exists for user 0 and then 8309 // verify that it's a singleton provider before using it. 8310 if (cpr == null && userId != UserHandle.USER_OWNER) { 8311 cpr = mProviderMap.getProviderByName(name, UserHandle.USER_OWNER); 8312 if (cpr != null) { 8313 cpi = cpr.info; 8314 if (isSingleton(cpi.processName, cpi.applicationInfo, 8315 cpi.name, cpi.flags) 8316 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid)) { 8317 userId = UserHandle.USER_OWNER; 8318 checkCrossUser = false; 8319 } else { 8320 cpr = null; 8321 cpi = null; 8322 } 8323 } 8324 } 8325 8326 boolean providerRunning = cpr != null; 8327 if (providerRunning) { 8328 cpi = cpr.info; 8329 String msg; 8330 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, checkCrossUser)) 8331 != null) { 8332 throw new SecurityException(msg); 8333 } 8334 8335 if (r != null && cpr.canRunHere(r)) { 8336 // This provider has been published or is in the process 8337 // of being published... but it is also allowed to run 8338 // in the caller's process, so don't make a connection 8339 // and just let the caller instantiate its own instance. 8340 ContentProviderHolder holder = cpr.newHolder(null); 8341 // don't give caller the provider object, it needs 8342 // to make its own. 8343 holder.provider = null; 8344 return holder; 8345 } 8346 8347 final long origId = Binder.clearCallingIdentity(); 8348 8349 // In this case the provider instance already exists, so we can 8350 // return it right away. 8351 conn = incProviderCountLocked(r, cpr, token, stable); 8352 if (conn != null && (conn.stableCount+conn.unstableCount) == 1) { 8353 if (cpr.proc != null && r.setAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 8354 // If this is a perceptible app accessing the provider, 8355 // make sure to count it as being accessed and thus 8356 // back up on the LRU list. This is good because 8357 // content providers are often expensive to start. 8358 updateLruProcessLocked(cpr.proc, false, null); 8359 } 8360 } 8361 8362 if (cpr.proc != null) { 8363 if (false) { 8364 if (cpr.name.flattenToShortString().equals( 8365 "com.android.providers.calendar/.CalendarProvider2")) { 8366 Slog.v(TAG, "****************** KILLING " 8367 + cpr.name.flattenToShortString()); 8368 Process.killProcess(cpr.proc.pid); 8369 } 8370 } 8371 boolean success = updateOomAdjLocked(cpr.proc); 8372 if (DEBUG_PROVIDER) Slog.i(TAG, "Adjust success: " + success); 8373 // NOTE: there is still a race here where a signal could be 8374 // pending on the process even though we managed to update its 8375 // adj level. Not sure what to do about this, but at least 8376 // the race is now smaller. 8377 if (!success) { 8378 // Uh oh... it looks like the provider's process 8379 // has been killed on us. We need to wait for a new 8380 // process to be started, and make sure its death 8381 // doesn't kill our process. 8382 Slog.i(TAG, 8383 "Existing provider " + cpr.name.flattenToShortString() 8384 + " is crashing; detaching " + r); 8385 boolean lastRef = decProviderCountLocked(conn, cpr, token, stable); 8386 appDiedLocked(cpr.proc, cpr.proc.pid, cpr.proc.thread); 8387 if (!lastRef) { 8388 // This wasn't the last ref our process had on 8389 // the provider... we have now been killed, bail. 8390 return null; 8391 } 8392 providerRunning = false; 8393 conn = null; 8394 } 8395 } 8396 8397 Binder.restoreCallingIdentity(origId); 8398 } 8399 8400 boolean singleton; 8401 if (!providerRunning) { 8402 try { 8403 cpi = AppGlobals.getPackageManager(). 8404 resolveContentProvider(name, 8405 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS, userId); 8406 } catch (RemoteException ex) { 8407 } 8408 if (cpi == null) { 8409 return null; 8410 } 8411 // If the provider is a singleton AND 8412 // (it's a call within the same user || the provider is a 8413 // privileged app) 8414 // Then allow connecting to the singleton provider 8415 singleton = isSingleton(cpi.processName, cpi.applicationInfo, 8416 cpi.name, cpi.flags) 8417 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid); 8418 if (singleton) { 8419 userId = UserHandle.USER_OWNER; 8420 } 8421 cpi.applicationInfo = getAppInfoForUser(cpi.applicationInfo, userId); 8422 8423 String msg; 8424 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, !singleton)) 8425 != null) { 8426 throw new SecurityException(msg); 8427 } 8428 8429 if (!mProcessesReady && !mDidUpdate && !mWaitingUpdate 8430 && !cpi.processName.equals("system")) { 8431 // If this content provider does not run in the system 8432 // process, and the system is not yet ready to run other 8433 // processes, then fail fast instead of hanging. 8434 throw new IllegalArgumentException( 8435 "Attempt to launch content provider before system ready"); 8436 } 8437 8438 // Make sure that the user who owns this provider is started. If not, 8439 // we don't want to allow it to run. 8440 if (mStartedUsers.get(userId) == null) { 8441 Slog.w(TAG, "Unable to launch app " 8442 + cpi.applicationInfo.packageName + "/" 8443 + cpi.applicationInfo.uid + " for provider " 8444 + name + ": user " + userId + " is stopped"); 8445 return null; 8446 } 8447 8448 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 8449 cpr = mProviderMap.getProviderByClass(comp, userId); 8450 final boolean firstClass = cpr == null; 8451 if (firstClass) { 8452 try { 8453 ApplicationInfo ai = 8454 AppGlobals.getPackageManager(). 8455 getApplicationInfo( 8456 cpi.applicationInfo.packageName, 8457 STOCK_PM_FLAGS, userId); 8458 if (ai == null) { 8459 Slog.w(TAG, "No package info for content provider " 8460 + cpi.name); 8461 return null; 8462 } 8463 ai = getAppInfoForUser(ai, userId); 8464 cpr = new ContentProviderRecord(this, cpi, ai, comp, singleton); 8465 } catch (RemoteException ex) { 8466 // pm is in same process, this will never happen. 8467 } 8468 } 8469 8470 if (r != null && cpr.canRunHere(r)) { 8471 // If this is a multiprocess provider, then just return its 8472 // info and allow the caller to instantiate it. Only do 8473 // this if the provider is the same user as the caller's 8474 // process, or can run as root (so can be in any process). 8475 return cpr.newHolder(null); 8476 } 8477 8478 if (DEBUG_PROVIDER) { 8479 RuntimeException e = new RuntimeException("here"); 8480 Slog.w(TAG, "LAUNCHING REMOTE PROVIDER (myuid " + (r != null ? r.uid : null) 8481 + " pruid " + cpr.appInfo.uid + "): " + cpr.info.name, e); 8482 } 8483 8484 // This is single process, and our app is now connecting to it. 8485 // See if we are already in the process of launching this 8486 // provider. 8487 final int N = mLaunchingProviders.size(); 8488 int i; 8489 for (i=0; i<N; i++) { 8490 if (mLaunchingProviders.get(i) == cpr) { 8491 break; 8492 } 8493 } 8494 8495 // If the provider is not already being launched, then get it 8496 // started. 8497 if (i >= N) { 8498 final long origId = Binder.clearCallingIdentity(); 8499 8500 try { 8501 // Content provider is now in use, its package can't be stopped. 8502 try { 8503 AppGlobals.getPackageManager().setPackageStoppedState( 8504 cpr.appInfo.packageName, false, userId); 8505 } catch (RemoteException e) { 8506 } catch (IllegalArgumentException e) { 8507 Slog.w(TAG, "Failed trying to unstop package " 8508 + cpr.appInfo.packageName + ": " + e); 8509 } 8510 8511 // Use existing process if already started 8512 ProcessRecord proc = getProcessRecordLocked( 8513 cpi.processName, cpr.appInfo.uid, false); 8514 if (proc != null && proc.thread != null) { 8515 if (DEBUG_PROVIDER) { 8516 Slog.d(TAG, "Installing in existing process " + proc); 8517 } 8518 proc.pubProviders.put(cpi.name, cpr); 8519 try { 8520 proc.thread.scheduleInstallProvider(cpi); 8521 } catch (RemoteException e) { 8522 } 8523 } else { 8524 proc = startProcessLocked(cpi.processName, 8525 cpr.appInfo, false, 0, "content provider", 8526 new ComponentName(cpi.applicationInfo.packageName, 8527 cpi.name), false, false, false); 8528 if (proc == null) { 8529 Slog.w(TAG, "Unable to launch app " 8530 + cpi.applicationInfo.packageName + "/" 8531 + cpi.applicationInfo.uid + " for provider " 8532 + name + ": process is bad"); 8533 return null; 8534 } 8535 } 8536 cpr.launchingApp = proc; 8537 mLaunchingProviders.add(cpr); 8538 } finally { 8539 Binder.restoreCallingIdentity(origId); 8540 } 8541 } 8542 8543 // Make sure the provider is published (the same provider class 8544 // may be published under multiple names). 8545 if (firstClass) { 8546 mProviderMap.putProviderByClass(comp, cpr); 8547 } 8548 8549 mProviderMap.putProviderByName(name, cpr); 8550 conn = incProviderCountLocked(r, cpr, token, stable); 8551 if (conn != null) { 8552 conn.waiting = true; 8553 } 8554 } 8555 } 8556 8557 // Wait for the provider to be published... 8558 synchronized (cpr) { 8559 while (cpr.provider == null) { 8560 if (cpr.launchingApp == null) { 8561 Slog.w(TAG, "Unable to launch app " 8562 + cpi.applicationInfo.packageName + "/" 8563 + cpi.applicationInfo.uid + " for provider " 8564 + name + ": launching app became null"); 8565 EventLog.writeEvent(EventLogTags.AM_PROVIDER_LOST_PROCESS, 8566 UserHandle.getUserId(cpi.applicationInfo.uid), 8567 cpi.applicationInfo.packageName, 8568 cpi.applicationInfo.uid, name); 8569 return null; 8570 } 8571 try { 8572 if (DEBUG_MU) { 8573 Slog.v(TAG_MU, "Waiting to start provider " + cpr + " launchingApp=" 8574 + cpr.launchingApp); 8575 } 8576 if (conn != null) { 8577 conn.waiting = true; 8578 } 8579 cpr.wait(); 8580 } catch (InterruptedException ex) { 8581 } finally { 8582 if (conn != null) { 8583 conn.waiting = false; 8584 } 8585 } 8586 } 8587 } 8588 return cpr != null ? cpr.newHolder(conn) : null; 8589 } 8590 8591 @Override 8592 public final ContentProviderHolder getContentProvider( 8593 IApplicationThread caller, String name, int userId, boolean stable) { 8594 enforceNotIsolatedCaller("getContentProvider"); 8595 if (caller == null) { 8596 String msg = "null IApplicationThread when getting content provider " 8597 + name; 8598 Slog.w(TAG, msg); 8599 throw new SecurityException(msg); 8600 } 8601 // The incoming user check is now handled in checkContentProviderPermissionLocked() to deal 8602 // with cross-user grant. 8603 return getContentProviderImpl(caller, name, null, stable, userId); 8604 } 8605 8606 public ContentProviderHolder getContentProviderExternal( 8607 String name, int userId, IBinder token) { 8608 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 8609 "Do not have permission in call getContentProviderExternal()"); 8610 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 8611 false, ALLOW_FULL_ONLY, "getContentProvider", null); 8612 return getContentProviderExternalUnchecked(name, token, userId); 8613 } 8614 8615 private ContentProviderHolder getContentProviderExternalUnchecked(String name, 8616 IBinder token, int userId) { 8617 return getContentProviderImpl(null, name, token, true, userId); 8618 } 8619 8620 /** 8621 * Drop a content provider from a ProcessRecord's bookkeeping 8622 */ 8623 public void removeContentProvider(IBinder connection, boolean stable) { 8624 enforceNotIsolatedCaller("removeContentProvider"); 8625 long ident = Binder.clearCallingIdentity(); 8626 try { 8627 synchronized (this) { 8628 ContentProviderConnection conn; 8629 try { 8630 conn = (ContentProviderConnection)connection; 8631 } catch (ClassCastException e) { 8632 String msg ="removeContentProvider: " + connection 8633 + " not a ContentProviderConnection"; 8634 Slog.w(TAG, msg); 8635 throw new IllegalArgumentException(msg); 8636 } 8637 if (conn == null) { 8638 throw new NullPointerException("connection is null"); 8639 } 8640 if (decProviderCountLocked(conn, null, null, stable)) { 8641 updateOomAdjLocked(); 8642 } 8643 } 8644 } finally { 8645 Binder.restoreCallingIdentity(ident); 8646 } 8647 } 8648 8649 public void removeContentProviderExternal(String name, IBinder token) { 8650 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 8651 "Do not have permission in call removeContentProviderExternal()"); 8652 removeContentProviderExternalUnchecked(name, token, UserHandle.getCallingUserId()); 8653 } 8654 8655 private void removeContentProviderExternalUnchecked(String name, IBinder token, int userId) { 8656 synchronized (this) { 8657 ContentProviderRecord cpr = mProviderMap.getProviderByName(name, userId); 8658 if(cpr == null) { 8659 //remove from mProvidersByClass 8660 if(localLOGV) Slog.v(TAG, name+" content provider not found in providers list"); 8661 return; 8662 } 8663 8664 //update content provider record entry info 8665 ComponentName comp = new ComponentName(cpr.info.packageName, cpr.info.name); 8666 ContentProviderRecord localCpr = mProviderMap.getProviderByClass(comp, userId); 8667 if (localCpr.hasExternalProcessHandles()) { 8668 if (localCpr.removeExternalProcessHandleLocked(token)) { 8669 updateOomAdjLocked(); 8670 } else { 8671 Slog.e(TAG, "Attmpt to remove content provider " + localCpr 8672 + " with no external reference for token: " 8673 + token + "."); 8674 } 8675 } else { 8676 Slog.e(TAG, "Attmpt to remove content provider: " + localCpr 8677 + " with no external references."); 8678 } 8679 } 8680 } 8681 8682 public final void publishContentProviders(IApplicationThread caller, 8683 List<ContentProviderHolder> providers) { 8684 if (providers == null) { 8685 return; 8686 } 8687 8688 enforceNotIsolatedCaller("publishContentProviders"); 8689 synchronized (this) { 8690 final ProcessRecord r = getRecordForAppLocked(caller); 8691 if (DEBUG_MU) 8692 Slog.v(TAG_MU, "ProcessRecord uid = " + r.uid); 8693 if (r == null) { 8694 throw new SecurityException( 8695 "Unable to find app for caller " + caller 8696 + " (pid=" + Binder.getCallingPid() 8697 + ") when publishing content providers"); 8698 } 8699 8700 final long origId = Binder.clearCallingIdentity(); 8701 8702 final int N = providers.size(); 8703 for (int i=0; i<N; i++) { 8704 ContentProviderHolder src = providers.get(i); 8705 if (src == null || src.info == null || src.provider == null) { 8706 continue; 8707 } 8708 ContentProviderRecord dst = r.pubProviders.get(src.info.name); 8709 if (DEBUG_MU) 8710 Slog.v(TAG_MU, "ContentProviderRecord uid = " + dst.uid); 8711 if (dst != null) { 8712 ComponentName comp = new ComponentName(dst.info.packageName, dst.info.name); 8713 mProviderMap.putProviderByClass(comp, dst); 8714 String names[] = dst.info.authority.split(";"); 8715 for (int j = 0; j < names.length; j++) { 8716 mProviderMap.putProviderByName(names[j], dst); 8717 } 8718 8719 int NL = mLaunchingProviders.size(); 8720 int j; 8721 for (j=0; j<NL; j++) { 8722 if (mLaunchingProviders.get(j) == dst) { 8723 mLaunchingProviders.remove(j); 8724 j--; 8725 NL--; 8726 } 8727 } 8728 synchronized (dst) { 8729 dst.provider = src.provider; 8730 dst.proc = r; 8731 dst.notifyAll(); 8732 } 8733 updateOomAdjLocked(r); 8734 } 8735 } 8736 8737 Binder.restoreCallingIdentity(origId); 8738 } 8739 } 8740 8741 public boolean refContentProvider(IBinder connection, int stable, int unstable) { 8742 ContentProviderConnection conn; 8743 try { 8744 conn = (ContentProviderConnection)connection; 8745 } catch (ClassCastException e) { 8746 String msg ="refContentProvider: " + connection 8747 + " not a ContentProviderConnection"; 8748 Slog.w(TAG, msg); 8749 throw new IllegalArgumentException(msg); 8750 } 8751 if (conn == null) { 8752 throw new NullPointerException("connection is null"); 8753 } 8754 8755 synchronized (this) { 8756 if (stable > 0) { 8757 conn.numStableIncs += stable; 8758 } 8759 stable = conn.stableCount + stable; 8760 if (stable < 0) { 8761 throw new IllegalStateException("stableCount < 0: " + stable); 8762 } 8763 8764 if (unstable > 0) { 8765 conn.numUnstableIncs += unstable; 8766 } 8767 unstable = conn.unstableCount + unstable; 8768 if (unstable < 0) { 8769 throw new IllegalStateException("unstableCount < 0: " + unstable); 8770 } 8771 8772 if ((stable+unstable) <= 0) { 8773 throw new IllegalStateException("ref counts can't go to zero here: stable=" 8774 + stable + " unstable=" + unstable); 8775 } 8776 conn.stableCount = stable; 8777 conn.unstableCount = unstable; 8778 return !conn.dead; 8779 } 8780 } 8781 8782 public void unstableProviderDied(IBinder connection) { 8783 ContentProviderConnection conn; 8784 try { 8785 conn = (ContentProviderConnection)connection; 8786 } catch (ClassCastException e) { 8787 String msg ="refContentProvider: " + connection 8788 + " not a ContentProviderConnection"; 8789 Slog.w(TAG, msg); 8790 throw new IllegalArgumentException(msg); 8791 } 8792 if (conn == null) { 8793 throw new NullPointerException("connection is null"); 8794 } 8795 8796 // Safely retrieve the content provider associated with the connection. 8797 IContentProvider provider; 8798 synchronized (this) { 8799 provider = conn.provider.provider; 8800 } 8801 8802 if (provider == null) { 8803 // Um, yeah, we're way ahead of you. 8804 return; 8805 } 8806 8807 // Make sure the caller is being honest with us. 8808 if (provider.asBinder().pingBinder()) { 8809 // Er, no, still looks good to us. 8810 synchronized (this) { 8811 Slog.w(TAG, "unstableProviderDied: caller " + Binder.getCallingUid() 8812 + " says " + conn + " died, but we don't agree"); 8813 return; 8814 } 8815 } 8816 8817 // Well look at that! It's dead! 8818 synchronized (this) { 8819 if (conn.provider.provider != provider) { 8820 // But something changed... good enough. 8821 return; 8822 } 8823 8824 ProcessRecord proc = conn.provider.proc; 8825 if (proc == null || proc.thread == null) { 8826 // Seems like the process is already cleaned up. 8827 return; 8828 } 8829 8830 // As far as we're concerned, this is just like receiving a 8831 // death notification... just a bit prematurely. 8832 Slog.i(TAG, "Process " + proc.processName + " (pid " + proc.pid 8833 + ") early provider death"); 8834 final long ident = Binder.clearCallingIdentity(); 8835 try { 8836 appDiedLocked(proc, proc.pid, proc.thread); 8837 } finally { 8838 Binder.restoreCallingIdentity(ident); 8839 } 8840 } 8841 } 8842 8843 @Override 8844 public void appNotRespondingViaProvider(IBinder connection) { 8845 enforceCallingPermission( 8846 android.Manifest.permission.REMOVE_TASKS, "appNotRespondingViaProvider()"); 8847 8848 final ContentProviderConnection conn = (ContentProviderConnection) connection; 8849 if (conn == null) { 8850 Slog.w(TAG, "ContentProviderConnection is null"); 8851 return; 8852 } 8853 8854 final ProcessRecord host = conn.provider.proc; 8855 if (host == null) { 8856 Slog.w(TAG, "Failed to find hosting ProcessRecord"); 8857 return; 8858 } 8859 8860 final long token = Binder.clearCallingIdentity(); 8861 try { 8862 appNotResponding(host, null, null, false, "ContentProvider not responding"); 8863 } finally { 8864 Binder.restoreCallingIdentity(token); 8865 } 8866 } 8867 8868 public final void installSystemProviders() { 8869 List<ProviderInfo> providers; 8870 synchronized (this) { 8871 ProcessRecord app = mProcessNames.get("system", Process.SYSTEM_UID); 8872 providers = generateApplicationProvidersLocked(app); 8873 if (providers != null) { 8874 for (int i=providers.size()-1; i>=0; i--) { 8875 ProviderInfo pi = (ProviderInfo)providers.get(i); 8876 if ((pi.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) == 0) { 8877 Slog.w(TAG, "Not installing system proc provider " + pi.name 8878 + ": not system .apk"); 8879 providers.remove(i); 8880 } 8881 } 8882 } 8883 } 8884 if (providers != null) { 8885 mSystemThread.installSystemProviders(providers); 8886 } 8887 8888 mCoreSettingsObserver = new CoreSettingsObserver(this); 8889 8890 //mUsageStatsService.monitorPackages(); 8891 } 8892 8893 /** 8894 * Allows app to retrieve the MIME type of a URI without having permission 8895 * to access its content provider. 8896 * 8897 * CTS tests for this functionality can be run with "runtest cts-appsecurity". 8898 * 8899 * Test cases are at cts/tests/appsecurity-tests/test-apps/UsePermissionDiffCert/ 8900 * src/com/android/cts/usespermissiondiffcertapp/AccessPermissionWithDiffSigTest.java 8901 */ 8902 public String getProviderMimeType(Uri uri, int userId) { 8903 enforceNotIsolatedCaller("getProviderMimeType"); 8904 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 8905 userId, false, ALLOW_NON_FULL_IN_PROFILE, "getProviderMimeType", null); 8906 final String name = uri.getAuthority(); 8907 final long ident = Binder.clearCallingIdentity(); 8908 ContentProviderHolder holder = null; 8909 8910 try { 8911 holder = getContentProviderExternalUnchecked(name, null, userId); 8912 if (holder != null) { 8913 return holder.provider.getType(uri); 8914 } 8915 } catch (RemoteException e) { 8916 Log.w(TAG, "Content provider dead retrieving " + uri, e); 8917 return null; 8918 } finally { 8919 if (holder != null) { 8920 removeContentProviderExternalUnchecked(name, null, userId); 8921 } 8922 Binder.restoreCallingIdentity(ident); 8923 } 8924 8925 return null; 8926 } 8927 8928 // ========================================================= 8929 // GLOBAL MANAGEMENT 8930 // ========================================================= 8931 8932 final ProcessRecord newProcessRecordLocked(ApplicationInfo info, String customProcess, 8933 boolean isolated) { 8934 String proc = customProcess != null ? customProcess : info.processName; 8935 BatteryStatsImpl.Uid.Proc ps = null; 8936 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 8937 int uid = info.uid; 8938 if (isolated) { 8939 int userId = UserHandle.getUserId(uid); 8940 int stepsLeft = Process.LAST_ISOLATED_UID - Process.FIRST_ISOLATED_UID + 1; 8941 while (true) { 8942 if (mNextIsolatedProcessUid < Process.FIRST_ISOLATED_UID 8943 || mNextIsolatedProcessUid > Process.LAST_ISOLATED_UID) { 8944 mNextIsolatedProcessUid = Process.FIRST_ISOLATED_UID; 8945 } 8946 uid = UserHandle.getUid(userId, mNextIsolatedProcessUid); 8947 mNextIsolatedProcessUid++; 8948 if (mIsolatedProcesses.indexOfKey(uid) < 0) { 8949 // No process for this uid, use it. 8950 break; 8951 } 8952 stepsLeft--; 8953 if (stepsLeft <= 0) { 8954 return null; 8955 } 8956 } 8957 } 8958 return new ProcessRecord(stats, info, proc, uid); 8959 } 8960 8961 final ProcessRecord addAppLocked(ApplicationInfo info, boolean isolated, 8962 String abiOverride) { 8963 ProcessRecord app; 8964 if (!isolated) { 8965 app = getProcessRecordLocked(info.processName, info.uid, true); 8966 } else { 8967 app = null; 8968 } 8969 8970 if (app == null) { 8971 app = newProcessRecordLocked(info, null, isolated); 8972 mProcessNames.put(info.processName, app.uid, app); 8973 if (isolated) { 8974 mIsolatedProcesses.put(app.uid, app); 8975 } 8976 updateLruProcessLocked(app, false, null); 8977 updateOomAdjLocked(); 8978 } 8979 8980 // This package really, really can not be stopped. 8981 try { 8982 AppGlobals.getPackageManager().setPackageStoppedState( 8983 info.packageName, false, UserHandle.getUserId(app.uid)); 8984 } catch (RemoteException e) { 8985 } catch (IllegalArgumentException e) { 8986 Slog.w(TAG, "Failed trying to unstop package " 8987 + info.packageName + ": " + e); 8988 } 8989 8990 if ((info.flags&(ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) 8991 == (ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) { 8992 app.persistent = true; 8993 app.maxAdj = ProcessList.PERSISTENT_PROC_ADJ; 8994 } 8995 if (app.thread == null && mPersistentStartingProcesses.indexOf(app) < 0) { 8996 mPersistentStartingProcesses.add(app); 8997 startProcessLocked(app, "added application", app.processName, 8998 abiOverride); 8999 } 9000 9001 return app; 9002 } 9003 9004 public void unhandledBack() { 9005 enforceCallingPermission(android.Manifest.permission.FORCE_BACK, 9006 "unhandledBack()"); 9007 9008 synchronized(this) { 9009 final long origId = Binder.clearCallingIdentity(); 9010 try { 9011 getFocusedStack().unhandledBackLocked(); 9012 } finally { 9013 Binder.restoreCallingIdentity(origId); 9014 } 9015 } 9016 } 9017 9018 public ParcelFileDescriptor openContentUri(Uri uri) throws RemoteException { 9019 enforceNotIsolatedCaller("openContentUri"); 9020 final int userId = UserHandle.getCallingUserId(); 9021 String name = uri.getAuthority(); 9022 ContentProviderHolder cph = getContentProviderExternalUnchecked(name, null, userId); 9023 ParcelFileDescriptor pfd = null; 9024 if (cph != null) { 9025 // We record the binder invoker's uid in thread-local storage before 9026 // going to the content provider to open the file. Later, in the code 9027 // that handles all permissions checks, we look for this uid and use 9028 // that rather than the Activity Manager's own uid. The effect is that 9029 // we do the check against the caller's permissions even though it looks 9030 // to the content provider like the Activity Manager itself is making 9031 // the request. 9032 sCallerIdentity.set(new Identity( 9033 Binder.getCallingPid(), Binder.getCallingUid())); 9034 try { 9035 pfd = cph.provider.openFile(null, uri, "r", null); 9036 } catch (FileNotFoundException e) { 9037 // do nothing; pfd will be returned null 9038 } finally { 9039 // Ensure that whatever happens, we clean up the identity state 9040 sCallerIdentity.remove(); 9041 } 9042 9043 // We've got the fd now, so we're done with the provider. 9044 removeContentProviderExternalUnchecked(name, null, userId); 9045 } else { 9046 Slog.d(TAG, "Failed to get provider for authority '" + name + "'"); 9047 } 9048 return pfd; 9049 } 9050 9051 // Actually is sleeping or shutting down or whatever else in the future 9052 // is an inactive state. 9053 public boolean isSleepingOrShuttingDown() { 9054 return mSleeping || mShuttingDown; 9055 } 9056 9057 public boolean isSleeping() { 9058 return mSleeping; 9059 } 9060 9061 void goingToSleep() { 9062 synchronized(this) { 9063 mWentToSleep = true; 9064 updateEventDispatchingLocked(); 9065 goToSleepIfNeededLocked(); 9066 } 9067 } 9068 9069 void finishRunningVoiceLocked() { 9070 if (mRunningVoice) { 9071 mRunningVoice = false; 9072 goToSleepIfNeededLocked(); 9073 } 9074 } 9075 9076 void goToSleepIfNeededLocked() { 9077 if (mWentToSleep && !mRunningVoice) { 9078 if (!mSleeping) { 9079 mSleeping = true; 9080 mStackSupervisor.goingToSleepLocked(); 9081 9082 // Initialize the wake times of all processes. 9083 checkExcessivePowerUsageLocked(false); 9084 mHandler.removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 9085 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 9086 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 9087 } 9088 } 9089 } 9090 9091 void notifyTaskPersisterLocked(TaskRecord task, boolean flush) { 9092 if (task != null && task.stack != null && task.stack.isHomeStack()) { 9093 // Never persist the home stack. 9094 return; 9095 } 9096 mTaskPersister.wakeup(task, flush); 9097 } 9098 9099 @Override 9100 public boolean shutdown(int timeout) { 9101 if (checkCallingPermission(android.Manifest.permission.SHUTDOWN) 9102 != PackageManager.PERMISSION_GRANTED) { 9103 throw new SecurityException("Requires permission " 9104 + android.Manifest.permission.SHUTDOWN); 9105 } 9106 9107 boolean timedout = false; 9108 9109 synchronized(this) { 9110 mShuttingDown = true; 9111 updateEventDispatchingLocked(); 9112 timedout = mStackSupervisor.shutdownLocked(timeout); 9113 } 9114 9115 mAppOpsService.shutdown(); 9116 if (mUsageStatsService != null) { 9117 mUsageStatsService.prepareShutdown(); 9118 } 9119 mBatteryStatsService.shutdown(); 9120 synchronized (this) { 9121 mProcessStats.shutdownLocked(); 9122 } 9123 notifyTaskPersisterLocked(null, true); 9124 9125 return timedout; 9126 } 9127 9128 public final void activitySlept(IBinder token) { 9129 if (localLOGV) Slog.v(TAG, "Activity slept: token=" + token); 9130 9131 final long origId = Binder.clearCallingIdentity(); 9132 9133 synchronized (this) { 9134 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9135 if (r != null) { 9136 mStackSupervisor.activitySleptLocked(r); 9137 } 9138 } 9139 9140 Binder.restoreCallingIdentity(origId); 9141 } 9142 9143 void logLockScreen(String msg) { 9144 if (DEBUG_LOCKSCREEN) Slog.d(TAG, Debug.getCallers(2) + ":" + msg + 9145 " mLockScreenShown=" + mLockScreenShown + " mWentToSleep=" + 9146 mWentToSleep + " mSleeping=" + mSleeping + " mDismissKeyguardOnNextActivity=" + 9147 mStackSupervisor.mDismissKeyguardOnNextActivity); 9148 } 9149 9150 private void comeOutOfSleepIfNeededLocked() { 9151 if ((!mWentToSleep && !mLockScreenShown) || mRunningVoice) { 9152 if (mSleeping) { 9153 mSleeping = false; 9154 mStackSupervisor.comeOutOfSleepIfNeededLocked(); 9155 } 9156 } 9157 } 9158 9159 void wakingUp() { 9160 synchronized(this) { 9161 mWentToSleep = false; 9162 updateEventDispatchingLocked(); 9163 comeOutOfSleepIfNeededLocked(); 9164 } 9165 } 9166 9167 void startRunningVoiceLocked() { 9168 if (!mRunningVoice) { 9169 mRunningVoice = true; 9170 comeOutOfSleepIfNeededLocked(); 9171 } 9172 } 9173 9174 private void updateEventDispatchingLocked() { 9175 mWindowManager.setEventDispatching(mBooted && !mWentToSleep && !mShuttingDown); 9176 } 9177 9178 public void setLockScreenShown(boolean shown) { 9179 if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER) 9180 != PackageManager.PERMISSION_GRANTED) { 9181 throw new SecurityException("Requires permission " 9182 + android.Manifest.permission.DEVICE_POWER); 9183 } 9184 9185 synchronized(this) { 9186 long ident = Binder.clearCallingIdentity(); 9187 try { 9188 if (DEBUG_LOCKSCREEN) logLockScreen(" shown=" + shown); 9189 mLockScreenShown = shown; 9190 comeOutOfSleepIfNeededLocked(); 9191 } finally { 9192 Binder.restoreCallingIdentity(ident); 9193 } 9194 } 9195 } 9196 9197 @Override 9198 public void stopAppSwitches() { 9199 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 9200 != PackageManager.PERMISSION_GRANTED) { 9201 throw new SecurityException("Requires permission " 9202 + android.Manifest.permission.STOP_APP_SWITCHES); 9203 } 9204 9205 synchronized(this) { 9206 mAppSwitchesAllowedTime = SystemClock.uptimeMillis() 9207 + APP_SWITCH_DELAY_TIME; 9208 mDidAppSwitch = false; 9209 mHandler.removeMessages(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 9210 Message msg = mHandler.obtainMessage(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 9211 mHandler.sendMessageDelayed(msg, APP_SWITCH_DELAY_TIME); 9212 } 9213 } 9214 9215 public void resumeAppSwitches() { 9216 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 9217 != PackageManager.PERMISSION_GRANTED) { 9218 throw new SecurityException("Requires permission " 9219 + android.Manifest.permission.STOP_APP_SWITCHES); 9220 } 9221 9222 synchronized(this) { 9223 // Note that we don't execute any pending app switches... we will 9224 // let those wait until either the timeout, or the next start 9225 // activity request. 9226 mAppSwitchesAllowedTime = 0; 9227 } 9228 } 9229 9230 boolean checkAppSwitchAllowedLocked(int callingPid, int callingUid, 9231 String name) { 9232 if (mAppSwitchesAllowedTime < SystemClock.uptimeMillis()) { 9233 return true; 9234 } 9235 9236 final int perm = checkComponentPermission( 9237 android.Manifest.permission.STOP_APP_SWITCHES, callingPid, 9238 callingUid, -1, true); 9239 if (perm == PackageManager.PERMISSION_GRANTED) { 9240 return true; 9241 } 9242 9243 Slog.w(TAG, name + " request from " + callingUid + " stopped"); 9244 return false; 9245 } 9246 9247 public void setDebugApp(String packageName, boolean waitForDebugger, 9248 boolean persistent) { 9249 enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP, 9250 "setDebugApp()"); 9251 9252 long ident = Binder.clearCallingIdentity(); 9253 try { 9254 // Note that this is not really thread safe if there are multiple 9255 // callers into it at the same time, but that's not a situation we 9256 // care about. 9257 if (persistent) { 9258 final ContentResolver resolver = mContext.getContentResolver(); 9259 Settings.Global.putString( 9260 resolver, Settings.Global.DEBUG_APP, 9261 packageName); 9262 Settings.Global.putInt( 9263 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 9264 waitForDebugger ? 1 : 0); 9265 } 9266 9267 synchronized (this) { 9268 if (!persistent) { 9269 mOrigDebugApp = mDebugApp; 9270 mOrigWaitForDebugger = mWaitForDebugger; 9271 } 9272 mDebugApp = packageName; 9273 mWaitForDebugger = waitForDebugger; 9274 mDebugTransient = !persistent; 9275 if (packageName != null) { 9276 forceStopPackageLocked(packageName, -1, false, false, true, true, 9277 false, UserHandle.USER_ALL, "set debug app"); 9278 } 9279 } 9280 } finally { 9281 Binder.restoreCallingIdentity(ident); 9282 } 9283 } 9284 9285 void setOpenGlTraceApp(ApplicationInfo app, String processName) { 9286 synchronized (this) { 9287 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 9288 if (!isDebuggable) { 9289 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 9290 throw new SecurityException("Process not debuggable: " + app.packageName); 9291 } 9292 } 9293 9294 mOpenGlTraceApp = processName; 9295 } 9296 } 9297 9298 void setProfileApp(ApplicationInfo app, String processName, String profileFile, 9299 ParcelFileDescriptor profileFd, boolean autoStopProfiler) { 9300 synchronized (this) { 9301 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 9302 if (!isDebuggable) { 9303 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 9304 throw new SecurityException("Process not debuggable: " + app.packageName); 9305 } 9306 } 9307 mProfileApp = processName; 9308 mProfileFile = profileFile; 9309 if (mProfileFd != null) { 9310 try { 9311 mProfileFd.close(); 9312 } catch (IOException e) { 9313 } 9314 mProfileFd = null; 9315 } 9316 mProfileFd = profileFd; 9317 mProfileType = 0; 9318 mAutoStopProfiler = autoStopProfiler; 9319 } 9320 } 9321 9322 @Override 9323 public void setAlwaysFinish(boolean enabled) { 9324 enforceCallingPermission(android.Manifest.permission.SET_ALWAYS_FINISH, 9325 "setAlwaysFinish()"); 9326 9327 Settings.Global.putInt( 9328 mContext.getContentResolver(), 9329 Settings.Global.ALWAYS_FINISH_ACTIVITIES, enabled ? 1 : 0); 9330 9331 synchronized (this) { 9332 mAlwaysFinishActivities = enabled; 9333 } 9334 } 9335 9336 @Override 9337 public void setActivityController(IActivityController controller) { 9338 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 9339 "setActivityController()"); 9340 synchronized (this) { 9341 mController = controller; 9342 Watchdog.getInstance().setActivityController(controller); 9343 } 9344 } 9345 9346 @Override 9347 public void setUserIsMonkey(boolean userIsMonkey) { 9348 synchronized (this) { 9349 synchronized (mPidsSelfLocked) { 9350 final int callingPid = Binder.getCallingPid(); 9351 ProcessRecord precessRecord = mPidsSelfLocked.get(callingPid); 9352 if (precessRecord == null) { 9353 throw new SecurityException("Unknown process: " + callingPid); 9354 } 9355 if (precessRecord.instrumentationUiAutomationConnection == null) { 9356 throw new SecurityException("Only an instrumentation process " 9357 + "with a UiAutomation can call setUserIsMonkey"); 9358 } 9359 } 9360 mUserIsMonkey = userIsMonkey; 9361 } 9362 } 9363 9364 @Override 9365 public boolean isUserAMonkey() { 9366 synchronized (this) { 9367 // If there is a controller also implies the user is a monkey. 9368 return (mUserIsMonkey || mController != null); 9369 } 9370 } 9371 9372 public void requestBugReport() { 9373 enforceCallingPermission(android.Manifest.permission.DUMP, "requestBugReport"); 9374 SystemProperties.set("ctl.start", "bugreport"); 9375 } 9376 9377 public static long getInputDispatchingTimeoutLocked(ActivityRecord r) { 9378 return r != null ? getInputDispatchingTimeoutLocked(r.app) : KEY_DISPATCHING_TIMEOUT; 9379 } 9380 9381 public static long getInputDispatchingTimeoutLocked(ProcessRecord r) { 9382 if (r != null && (r.instrumentationClass != null || r.usingWrapper)) { 9383 return INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT; 9384 } 9385 return KEY_DISPATCHING_TIMEOUT; 9386 } 9387 9388 @Override 9389 public long inputDispatchingTimedOut(int pid, final boolean aboveSystem, String reason) { 9390 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 9391 != PackageManager.PERMISSION_GRANTED) { 9392 throw new SecurityException("Requires permission " 9393 + android.Manifest.permission.FILTER_EVENTS); 9394 } 9395 ProcessRecord proc; 9396 long timeout; 9397 synchronized (this) { 9398 synchronized (mPidsSelfLocked) { 9399 proc = mPidsSelfLocked.get(pid); 9400 } 9401 timeout = getInputDispatchingTimeoutLocked(proc); 9402 } 9403 9404 if (!inputDispatchingTimedOut(proc, null, null, aboveSystem, reason)) { 9405 return -1; 9406 } 9407 9408 return timeout; 9409 } 9410 9411 /** 9412 * Handle input dispatching timeouts. 9413 * Returns whether input dispatching should be aborted or not. 9414 */ 9415 public boolean inputDispatchingTimedOut(final ProcessRecord proc, 9416 final ActivityRecord activity, final ActivityRecord parent, 9417 final boolean aboveSystem, String reason) { 9418 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 9419 != PackageManager.PERMISSION_GRANTED) { 9420 throw new SecurityException("Requires permission " 9421 + android.Manifest.permission.FILTER_EVENTS); 9422 } 9423 9424 final String annotation; 9425 if (reason == null) { 9426 annotation = "Input dispatching timed out"; 9427 } else { 9428 annotation = "Input dispatching timed out (" + reason + ")"; 9429 } 9430 9431 if (proc != null) { 9432 synchronized (this) { 9433 if (proc.debugging) { 9434 return false; 9435 } 9436 9437 if (mDidDexOpt) { 9438 // Give more time since we were dexopting. 9439 mDidDexOpt = false; 9440 return false; 9441 } 9442 9443 if (proc.instrumentationClass != null) { 9444 Bundle info = new Bundle(); 9445 info.putString("shortMsg", "keyDispatchingTimedOut"); 9446 info.putString("longMsg", annotation); 9447 finishInstrumentationLocked(proc, Activity.RESULT_CANCELED, info); 9448 return true; 9449 } 9450 } 9451 mHandler.post(new Runnable() { 9452 @Override 9453 public void run() { 9454 appNotResponding(proc, activity, parent, aboveSystem, annotation); 9455 } 9456 }); 9457 } 9458 9459 return true; 9460 } 9461 9462 public Bundle getAssistContextExtras(int requestType) { 9463 enforceCallingPermission(android.Manifest.permission.GET_TOP_ACTIVITY_INFO, 9464 "getAssistContextExtras()"); 9465 PendingAssistExtras pae; 9466 Bundle extras = new Bundle(); 9467 synchronized (this) { 9468 ActivityRecord activity = getFocusedStack().mResumedActivity; 9469 if (activity == null) { 9470 Slog.w(TAG, "getAssistContextExtras failed: no resumed activity"); 9471 return null; 9472 } 9473 extras.putString(Intent.EXTRA_ASSIST_PACKAGE, activity.packageName); 9474 if (activity.app == null || activity.app.thread == null) { 9475 Slog.w(TAG, "getAssistContextExtras failed: no process for " + activity); 9476 return extras; 9477 } 9478 if (activity.app.pid == Binder.getCallingPid()) { 9479 Slog.w(TAG, "getAssistContextExtras failed: request process same as " + activity); 9480 return extras; 9481 } 9482 pae = new PendingAssistExtras(activity); 9483 try { 9484 activity.app.thread.requestAssistContextExtras(activity.appToken, pae, 9485 requestType); 9486 mPendingAssistExtras.add(pae); 9487 mHandler.postDelayed(pae, PENDING_ASSIST_EXTRAS_TIMEOUT); 9488 } catch (RemoteException e) { 9489 Slog.w(TAG, "getAssistContextExtras failed: crash calling " + activity); 9490 return extras; 9491 } 9492 } 9493 synchronized (pae) { 9494 while (!pae.haveResult) { 9495 try { 9496 pae.wait(); 9497 } catch (InterruptedException e) { 9498 } 9499 } 9500 if (pae.result != null) { 9501 extras.putBundle(Intent.EXTRA_ASSIST_CONTEXT, pae.result); 9502 } 9503 } 9504 synchronized (this) { 9505 mPendingAssistExtras.remove(pae); 9506 mHandler.removeCallbacks(pae); 9507 } 9508 return extras; 9509 } 9510 9511 public void reportAssistContextExtras(IBinder token, Bundle extras) { 9512 PendingAssistExtras pae = (PendingAssistExtras)token; 9513 synchronized (pae) { 9514 pae.result = extras; 9515 pae.haveResult = true; 9516 pae.notifyAll(); 9517 } 9518 } 9519 9520 public void registerProcessObserver(IProcessObserver observer) { 9521 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 9522 "registerProcessObserver()"); 9523 synchronized (this) { 9524 mProcessObservers.register(observer); 9525 } 9526 } 9527 9528 @Override 9529 public void unregisterProcessObserver(IProcessObserver observer) { 9530 synchronized (this) { 9531 mProcessObservers.unregister(observer); 9532 } 9533 } 9534 9535 @Override 9536 public boolean convertFromTranslucent(IBinder token) { 9537 final long origId = Binder.clearCallingIdentity(); 9538 try { 9539 synchronized (this) { 9540 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9541 if (r == null) { 9542 return false; 9543 } 9544 if (r.changeWindowTranslucency(true)) { 9545 mWindowManager.setAppFullscreen(token, true); 9546 r.task.stack.releaseMediaResources(); 9547 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9548 return true; 9549 } 9550 return false; 9551 } 9552 } finally { 9553 Binder.restoreCallingIdentity(origId); 9554 } 9555 } 9556 9557 @Override 9558 public boolean convertToTranslucent(IBinder token, ActivityOptions options) { 9559 final long origId = Binder.clearCallingIdentity(); 9560 try { 9561 synchronized (this) { 9562 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9563 if (r == null) { 9564 return false; 9565 } 9566 int index = r.task.mActivities.lastIndexOf(r); 9567 if (index > 0) { 9568 ActivityRecord under = r.task.mActivities.get(index - 1); 9569 under.returningOptions = options; 9570 } 9571 if (r.changeWindowTranslucency(false)) { 9572 r.task.stack.convertToTranslucent(r); 9573 mWindowManager.setAppFullscreen(token, false); 9574 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9575 return true; 9576 } else { 9577 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9578 return false; 9579 } 9580 } 9581 } finally { 9582 Binder.restoreCallingIdentity(origId); 9583 } 9584 } 9585 9586 @Override 9587 public boolean setMediaPlaying(IBinder token, boolean playing) { 9588 final long origId = Binder.clearCallingIdentity(); 9589 try { 9590 synchronized (this) { 9591 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9592 if (r != null) { 9593 return mStackSupervisor.setMediaPlayingLocked(r, playing); 9594 } 9595 } 9596 return false; 9597 } finally { 9598 Binder.restoreCallingIdentity(origId); 9599 } 9600 } 9601 9602 @Override 9603 public boolean isBackgroundMediaPlaying(IBinder token) { 9604 final long origId = Binder.clearCallingIdentity(); 9605 try { 9606 synchronized (this) { 9607 final ActivityStack stack = ActivityRecord.getStackLocked(token); 9608 final boolean playing = stack == null ? false : stack.isMediaPlaying(); 9609 if (ActivityStackSupervisor.DEBUG_MEDIA_VISIBILITY) Slog.d(TAG, 9610 "isBackgroundMediaPlaying: stack=" + stack + " playing=" + playing); 9611 return playing; 9612 } 9613 } finally { 9614 Binder.restoreCallingIdentity(origId); 9615 } 9616 } 9617 9618 @Override 9619 public ActivityOptions getActivityOptions(IBinder token) { 9620 final long origId = Binder.clearCallingIdentity(); 9621 try { 9622 synchronized (this) { 9623 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9624 if (r != null) { 9625 final ActivityOptions activityOptions = r.pendingOptions; 9626 r.pendingOptions = null; 9627 return activityOptions; 9628 } 9629 return null; 9630 } 9631 } finally { 9632 Binder.restoreCallingIdentity(origId); 9633 } 9634 } 9635 9636 @Override 9637 public void setImmersive(IBinder token, boolean immersive) { 9638 synchronized(this) { 9639 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9640 if (r == null) { 9641 throw new IllegalArgumentException(); 9642 } 9643 r.immersive = immersive; 9644 9645 // update associated state if we're frontmost 9646 if (r == mFocusedActivity) { 9647 if (DEBUG_IMMERSIVE) { 9648 Slog.d(TAG, "Frontmost changed immersion: "+ r); 9649 } 9650 applyUpdateLockStateLocked(r); 9651 } 9652 } 9653 } 9654 9655 @Override 9656 public boolean isImmersive(IBinder token) { 9657 synchronized (this) { 9658 ActivityRecord r = ActivityRecord.isInStackLocked(token); 9659 if (r == null) { 9660 throw new IllegalArgumentException(); 9661 } 9662 return r.immersive; 9663 } 9664 } 9665 9666 public boolean isTopActivityImmersive() { 9667 enforceNotIsolatedCaller("startActivity"); 9668 synchronized (this) { 9669 ActivityRecord r = getFocusedStack().topRunningActivityLocked(null); 9670 return (r != null) ? r.immersive : false; 9671 } 9672 } 9673 9674 @Override 9675 public boolean isTopOfTask(IBinder token) { 9676 synchronized (this) { 9677 ActivityRecord r = ActivityRecord.isInStackLocked(token); 9678 if (r == null) { 9679 throw new IllegalArgumentException(); 9680 } 9681 return r.task.getTopActivity() == r; 9682 } 9683 } 9684 9685 public final void enterSafeMode() { 9686 synchronized(this) { 9687 // It only makes sense to do this before the system is ready 9688 // and started launching other packages. 9689 if (!mSystemReady) { 9690 try { 9691 AppGlobals.getPackageManager().enterSafeMode(); 9692 } catch (RemoteException e) { 9693 } 9694 } 9695 9696 mSafeMode = true; 9697 } 9698 } 9699 9700 public final void showSafeModeOverlay() { 9701 View v = LayoutInflater.from(mContext).inflate( 9702 com.android.internal.R.layout.safe_mode, null); 9703 WindowManager.LayoutParams lp = new WindowManager.LayoutParams(); 9704 lp.type = WindowManager.LayoutParams.TYPE_SECURE_SYSTEM_OVERLAY; 9705 lp.width = WindowManager.LayoutParams.WRAP_CONTENT; 9706 lp.height = WindowManager.LayoutParams.WRAP_CONTENT; 9707 lp.gravity = Gravity.BOTTOM | Gravity.START; 9708 lp.format = v.getBackground().getOpacity(); 9709 lp.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE 9710 | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE; 9711 lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; 9712 ((WindowManager)mContext.getSystemService( 9713 Context.WINDOW_SERVICE)).addView(v, lp); 9714 } 9715 9716 public void noteWakeupAlarm(IIntentSender sender, int sourceUid, String sourcePkg) { 9717 if (!(sender instanceof PendingIntentRecord)) { 9718 return; 9719 } 9720 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 9721 synchronized (stats) { 9722 if (mBatteryStatsService.isOnBattery()) { 9723 mBatteryStatsService.enforceCallingPermission(); 9724 PendingIntentRecord rec = (PendingIntentRecord)sender; 9725 int MY_UID = Binder.getCallingUid(); 9726 int uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid; 9727 BatteryStatsImpl.Uid.Pkg pkg = 9728 stats.getPackageStatsLocked(sourceUid >= 0 ? sourceUid : uid, 9729 sourcePkg != null ? sourcePkg : rec.key.packageName); 9730 pkg.incWakeupsLocked(); 9731 } 9732 } 9733 } 9734 9735 public boolean killPids(int[] pids, String pReason, boolean secure) { 9736 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9737 throw new SecurityException("killPids only available to the system"); 9738 } 9739 String reason = (pReason == null) ? "Unknown" : pReason; 9740 // XXX Note: don't acquire main activity lock here, because the window 9741 // manager calls in with its locks held. 9742 9743 boolean killed = false; 9744 synchronized (mPidsSelfLocked) { 9745 int[] types = new int[pids.length]; 9746 int worstType = 0; 9747 for (int i=0; i<pids.length; i++) { 9748 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 9749 if (proc != null) { 9750 int type = proc.setAdj; 9751 types[i] = type; 9752 if (type > worstType) { 9753 worstType = type; 9754 } 9755 } 9756 } 9757 9758 // If the worst oom_adj is somewhere in the cached proc LRU range, 9759 // then constrain it so we will kill all cached procs. 9760 if (worstType < ProcessList.CACHED_APP_MAX_ADJ 9761 && worstType > ProcessList.CACHED_APP_MIN_ADJ) { 9762 worstType = ProcessList.CACHED_APP_MIN_ADJ; 9763 } 9764 9765 // If this is not a secure call, don't let it kill processes that 9766 // are important. 9767 if (!secure && worstType < ProcessList.SERVICE_ADJ) { 9768 worstType = ProcessList.SERVICE_ADJ; 9769 } 9770 9771 Slog.w(TAG, "Killing processes " + reason + " at adjustment " + worstType); 9772 for (int i=0; i<pids.length; i++) { 9773 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 9774 if (proc == null) { 9775 continue; 9776 } 9777 int adj = proc.setAdj; 9778 if (adj >= worstType && !proc.killedByAm) { 9779 killUnneededProcessLocked(proc, reason); 9780 killed = true; 9781 } 9782 } 9783 } 9784 return killed; 9785 } 9786 9787 @Override 9788 public void killUid(int uid, String reason) { 9789 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9790 throw new SecurityException("killUid only available to the system"); 9791 } 9792 synchronized (this) { 9793 killPackageProcessesLocked(null, UserHandle.getAppId(uid), UserHandle.getUserId(uid), 9794 ProcessList.FOREGROUND_APP_ADJ-1, false, true, true, false, 9795 reason != null ? reason : "kill uid"); 9796 } 9797 } 9798 9799 @Override 9800 public boolean killProcessesBelowForeground(String reason) { 9801 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9802 throw new SecurityException("killProcessesBelowForeground() only available to system"); 9803 } 9804 9805 return killProcessesBelowAdj(ProcessList.FOREGROUND_APP_ADJ, reason); 9806 } 9807 9808 private boolean killProcessesBelowAdj(int belowAdj, String reason) { 9809 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9810 throw new SecurityException("killProcessesBelowAdj() only available to system"); 9811 } 9812 9813 boolean killed = false; 9814 synchronized (mPidsSelfLocked) { 9815 final int size = mPidsSelfLocked.size(); 9816 for (int i = 0; i < size; i++) { 9817 final int pid = mPidsSelfLocked.keyAt(i); 9818 final ProcessRecord proc = mPidsSelfLocked.valueAt(i); 9819 if (proc == null) continue; 9820 9821 final int adj = proc.setAdj; 9822 if (adj > belowAdj && !proc.killedByAm) { 9823 killUnneededProcessLocked(proc, reason); 9824 killed = true; 9825 } 9826 } 9827 } 9828 return killed; 9829 } 9830 9831 @Override 9832 public void hang(final IBinder who, boolean allowRestart) { 9833 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9834 != PackageManager.PERMISSION_GRANTED) { 9835 throw new SecurityException("Requires permission " 9836 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9837 } 9838 9839 final IBinder.DeathRecipient death = new DeathRecipient() { 9840 @Override 9841 public void binderDied() { 9842 synchronized (this) { 9843 notifyAll(); 9844 } 9845 } 9846 }; 9847 9848 try { 9849 who.linkToDeath(death, 0); 9850 } catch (RemoteException e) { 9851 Slog.w(TAG, "hang: given caller IBinder is already dead."); 9852 return; 9853 } 9854 9855 synchronized (this) { 9856 Watchdog.getInstance().setAllowRestart(allowRestart); 9857 Slog.i(TAG, "Hanging system process at request of pid " + Binder.getCallingPid()); 9858 synchronized (death) { 9859 while (who.isBinderAlive()) { 9860 try { 9861 death.wait(); 9862 } catch (InterruptedException e) { 9863 } 9864 } 9865 } 9866 Watchdog.getInstance().setAllowRestart(true); 9867 } 9868 } 9869 9870 @Override 9871 public void restart() { 9872 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9873 != PackageManager.PERMISSION_GRANTED) { 9874 throw new SecurityException("Requires permission " 9875 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9876 } 9877 9878 Log.i(TAG, "Sending shutdown broadcast..."); 9879 9880 BroadcastReceiver br = new BroadcastReceiver() { 9881 @Override public void onReceive(Context context, Intent intent) { 9882 // Now the broadcast is done, finish up the low-level shutdown. 9883 Log.i(TAG, "Shutting down activity manager..."); 9884 shutdown(10000); 9885 Log.i(TAG, "Shutdown complete, restarting!"); 9886 Process.killProcess(Process.myPid()); 9887 System.exit(10); 9888 } 9889 }; 9890 9891 // First send the high-level shut down broadcast. 9892 Intent intent = new Intent(Intent.ACTION_SHUTDOWN); 9893 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 9894 intent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 9895 /* For now we are not doing a clean shutdown, because things seem to get unhappy. 9896 mContext.sendOrderedBroadcastAsUser(intent, 9897 UserHandle.ALL, null, br, mHandler, 0, null, null); 9898 */ 9899 br.onReceive(mContext, intent); 9900 } 9901 9902 private long getLowRamTimeSinceIdle(long now) { 9903 return mLowRamTimeSinceLastIdle + (mLowRamStartTime > 0 ? (now-mLowRamStartTime) : 0); 9904 } 9905 9906 @Override 9907 public void performIdleMaintenance() { 9908 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9909 != PackageManager.PERMISSION_GRANTED) { 9910 throw new SecurityException("Requires permission " 9911 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9912 } 9913 9914 synchronized (this) { 9915 final long now = SystemClock.uptimeMillis(); 9916 final long timeSinceLastIdle = now - mLastIdleTime; 9917 final long lowRamSinceLastIdle = getLowRamTimeSinceIdle(now); 9918 mLastIdleTime = now; 9919 mLowRamTimeSinceLastIdle = 0; 9920 if (mLowRamStartTime != 0) { 9921 mLowRamStartTime = now; 9922 } 9923 9924 StringBuilder sb = new StringBuilder(128); 9925 sb.append("Idle maintenance over "); 9926 TimeUtils.formatDuration(timeSinceLastIdle, sb); 9927 sb.append(" low RAM for "); 9928 TimeUtils.formatDuration(lowRamSinceLastIdle, sb); 9929 Slog.i(TAG, sb.toString()); 9930 9931 // If at least 1/3 of our time since the last idle period has been spent 9932 // with RAM low, then we want to kill processes. 9933 boolean doKilling = lowRamSinceLastIdle > (timeSinceLastIdle/3); 9934 9935 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 9936 ProcessRecord proc = mLruProcesses.get(i); 9937 if (proc.notCachedSinceIdle) { 9938 if (proc.setProcState > ActivityManager.PROCESS_STATE_TOP 9939 && proc.setProcState <= ActivityManager.PROCESS_STATE_SERVICE) { 9940 if (doKilling && proc.initialIdlePss != 0 9941 && proc.lastPss > ((proc.initialIdlePss*3)/2)) { 9942 killUnneededProcessLocked(proc, "idle maint (pss " + proc.lastPss 9943 + " from " + proc.initialIdlePss + ")"); 9944 } 9945 } 9946 } else if (proc.setProcState < ActivityManager.PROCESS_STATE_HOME) { 9947 proc.notCachedSinceIdle = true; 9948 proc.initialIdlePss = 0; 9949 proc.nextPssTime = ProcessList.computeNextPssTime(proc.curProcState, true, 9950 isSleeping(), now); 9951 } 9952 } 9953 9954 mHandler.removeMessages(REQUEST_ALL_PSS_MSG); 9955 mHandler.sendEmptyMessageDelayed(REQUEST_ALL_PSS_MSG, 2*60*1000); 9956 } 9957 } 9958 9959 private void retrieveSettings() { 9960 final ContentResolver resolver = mContext.getContentResolver(); 9961 String debugApp = Settings.Global.getString( 9962 resolver, Settings.Global.DEBUG_APP); 9963 boolean waitForDebugger = Settings.Global.getInt( 9964 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 0) != 0; 9965 boolean alwaysFinishActivities = Settings.Global.getInt( 9966 resolver, Settings.Global.ALWAYS_FINISH_ACTIVITIES, 0) != 0; 9967 boolean forceRtl = Settings.Global.getInt( 9968 resolver, Settings.Global.DEVELOPMENT_FORCE_RTL, 0) != 0; 9969 // Transfer any global setting for forcing RTL layout, into a System Property 9970 SystemProperties.set(Settings.Global.DEVELOPMENT_FORCE_RTL, forceRtl ? "1":"0"); 9971 9972 Configuration configuration = new Configuration(); 9973 Settings.System.getConfiguration(resolver, configuration); 9974 if (forceRtl) { 9975 // This will take care of setting the correct layout direction flags 9976 configuration.setLayoutDirection(configuration.locale); 9977 } 9978 9979 synchronized (this) { 9980 mDebugApp = mOrigDebugApp = debugApp; 9981 mWaitForDebugger = mOrigWaitForDebugger = waitForDebugger; 9982 mAlwaysFinishActivities = alwaysFinishActivities; 9983 // This happens before any activities are started, so we can 9984 // change mConfiguration in-place. 9985 updateConfigurationLocked(configuration, null, false, true); 9986 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Initial config: " + mConfiguration); 9987 } 9988 } 9989 9990 public boolean testIsSystemReady() { 9991 // no need to synchronize(this) just to read & return the value 9992 return mSystemReady; 9993 } 9994 9995 private static File getCalledPreBootReceiversFile() { 9996 File dataDir = Environment.getDataDirectory(); 9997 File systemDir = new File(dataDir, "system"); 9998 File fname = new File(systemDir, CALLED_PRE_BOOTS_FILENAME); 9999 return fname; 10000 } 10001 10002 private static ArrayList<ComponentName> readLastDonePreBootReceivers() { 10003 ArrayList<ComponentName> lastDoneReceivers = new ArrayList<ComponentName>(); 10004 File file = getCalledPreBootReceiversFile(); 10005 FileInputStream fis = null; 10006 try { 10007 fis = new FileInputStream(file); 10008 DataInputStream dis = new DataInputStream(new BufferedInputStream(fis, 2048)); 10009 int fvers = dis.readInt(); 10010 if (fvers == LAST_PREBOOT_DELIVERED_FILE_VERSION) { 10011 String vers = dis.readUTF(); 10012 String codename = dis.readUTF(); 10013 String build = dis.readUTF(); 10014 if (android.os.Build.VERSION.RELEASE.equals(vers) 10015 && android.os.Build.VERSION.CODENAME.equals(codename) 10016 && android.os.Build.VERSION.INCREMENTAL.equals(build)) { 10017 int num = dis.readInt(); 10018 while (num > 0) { 10019 num--; 10020 String pkg = dis.readUTF(); 10021 String cls = dis.readUTF(); 10022 lastDoneReceivers.add(new ComponentName(pkg, cls)); 10023 } 10024 } 10025 } 10026 } catch (FileNotFoundException e) { 10027 } catch (IOException e) { 10028 Slog.w(TAG, "Failure reading last done pre-boot receivers", e); 10029 } finally { 10030 if (fis != null) { 10031 try { 10032 fis.close(); 10033 } catch (IOException e) { 10034 } 10035 } 10036 } 10037 return lastDoneReceivers; 10038 } 10039 10040 private static void writeLastDonePreBootReceivers(ArrayList<ComponentName> list) { 10041 File file = getCalledPreBootReceiversFile(); 10042 FileOutputStream fos = null; 10043 DataOutputStream dos = null; 10044 try { 10045 fos = new FileOutputStream(file); 10046 dos = new DataOutputStream(new BufferedOutputStream(fos, 2048)); 10047 dos.writeInt(LAST_PREBOOT_DELIVERED_FILE_VERSION); 10048 dos.writeUTF(android.os.Build.VERSION.RELEASE); 10049 dos.writeUTF(android.os.Build.VERSION.CODENAME); 10050 dos.writeUTF(android.os.Build.VERSION.INCREMENTAL); 10051 dos.writeInt(list.size()); 10052 for (int i=0; i<list.size(); i++) { 10053 dos.writeUTF(list.get(i).getPackageName()); 10054 dos.writeUTF(list.get(i).getClassName()); 10055 } 10056 } catch (IOException e) { 10057 Slog.w(TAG, "Failure writing last done pre-boot receivers", e); 10058 file.delete(); 10059 } finally { 10060 FileUtils.sync(fos); 10061 if (dos != null) { 10062 try { 10063 dos.close(); 10064 } catch (IOException e) { 10065 // TODO Auto-generated catch block 10066 e.printStackTrace(); 10067 } 10068 } 10069 } 10070 } 10071 10072 private boolean deliverPreBootCompleted(final Runnable onFinishCallback, 10073 ArrayList<ComponentName> doneReceivers, int userId) { 10074 boolean waitingUpdate = false; 10075 Intent intent = new Intent(Intent.ACTION_PRE_BOOT_COMPLETED); 10076 List<ResolveInfo> ris = null; 10077 try { 10078 ris = AppGlobals.getPackageManager().queryIntentReceivers( 10079 intent, null, 0, userId); 10080 } catch (RemoteException e) { 10081 } 10082 if (ris != null) { 10083 for (int i=ris.size()-1; i>=0; i--) { 10084 if ((ris.get(i).activityInfo.applicationInfo.flags 10085 &ApplicationInfo.FLAG_SYSTEM) == 0) { 10086 ris.remove(i); 10087 } 10088 } 10089 intent.addFlags(Intent.FLAG_RECEIVER_BOOT_UPGRADE); 10090 10091 // For User 0, load the version number. When delivering to a new user, deliver 10092 // to all receivers. 10093 if (userId == UserHandle.USER_OWNER) { 10094 ArrayList<ComponentName> lastDoneReceivers = readLastDonePreBootReceivers(); 10095 for (int i=0; i<ris.size(); i++) { 10096 ActivityInfo ai = ris.get(i).activityInfo; 10097 ComponentName comp = new ComponentName(ai.packageName, ai.name); 10098 if (lastDoneReceivers.contains(comp)) { 10099 // We already did the pre boot receiver for this app with the current 10100 // platform version, so don't do it again... 10101 ris.remove(i); 10102 i--; 10103 // ...however, do keep it as one that has been done, so we don't 10104 // forget about it when rewriting the file of last done receivers. 10105 doneReceivers.add(comp); 10106 } 10107 } 10108 } 10109 10110 // If primary user, send broadcast to all available users, else just to userId 10111 final int[] users = userId == UserHandle.USER_OWNER ? getUsersLocked() 10112 : new int[] { userId }; 10113 for (int i = 0; i < ris.size(); i++) { 10114 ActivityInfo ai = ris.get(i).activityInfo; 10115 ComponentName comp = new ComponentName(ai.packageName, ai.name); 10116 doneReceivers.add(comp); 10117 intent.setComponent(comp); 10118 for (int j=0; j<users.length; j++) { 10119 IIntentReceiver finisher = null; 10120 // On last receiver and user, set up a completion callback 10121 if (i == ris.size() - 1 && j == users.length - 1 && onFinishCallback != null) { 10122 finisher = new IIntentReceiver.Stub() { 10123 public void performReceive(Intent intent, int resultCode, 10124 String data, Bundle extras, boolean ordered, 10125 boolean sticky, int sendingUser) { 10126 // The raw IIntentReceiver interface is called 10127 // with the AM lock held, so redispatch to 10128 // execute our code without the lock. 10129 mHandler.post(onFinishCallback); 10130 } 10131 }; 10132 } 10133 Slog.i(TAG, "Sending system update to " + intent.getComponent() 10134 + " for user " + users[j]); 10135 broadcastIntentLocked(null, null, intent, null, finisher, 10136 0, null, null, null, AppOpsManager.OP_NONE, 10137 true, false, MY_PID, Process.SYSTEM_UID, 10138 users[j]); 10139 if (finisher != null) { 10140 waitingUpdate = true; 10141 } 10142 } 10143 } 10144 } 10145 10146 return waitingUpdate; 10147 } 10148 10149 public void systemReady(final Runnable goingCallback) { 10150 synchronized(this) { 10151 if (mSystemReady) { 10152 // If we're done calling all the receivers, run the next "boot phase" passed in 10153 // by the SystemServer 10154 if (goingCallback != null) { 10155 goingCallback.run(); 10156 } 10157 return; 10158 } 10159 10160 // Make sure we have the current profile info, since it is needed for 10161 // security checks. 10162 updateCurrentProfileIdsLocked(); 10163 10164 if (mRecentTasks == null) { 10165 mRecentTasks = mTaskPersister.restoreTasksLocked(); 10166 if (!mRecentTasks.isEmpty()) { 10167 mStackSupervisor.createStackForRestoredTaskHistory(mRecentTasks); 10168 } 10169 mTaskPersister.startPersisting(); 10170 } 10171 10172 // Check to see if there are any update receivers to run. 10173 if (!mDidUpdate) { 10174 if (mWaitingUpdate) { 10175 return; 10176 } 10177 final ArrayList<ComponentName> doneReceivers = new ArrayList<ComponentName>(); 10178 mWaitingUpdate = deliverPreBootCompleted(new Runnable() { 10179 public void run() { 10180 synchronized (ActivityManagerService.this) { 10181 mDidUpdate = true; 10182 } 10183 writeLastDonePreBootReceivers(doneReceivers); 10184 showBootMessage(mContext.getText( 10185 R.string.android_upgrading_complete), 10186 false); 10187 systemReady(goingCallback); 10188 } 10189 }, doneReceivers, UserHandle.USER_OWNER); 10190 10191 if (mWaitingUpdate) { 10192 return; 10193 } 10194 mDidUpdate = true; 10195 } 10196 10197 mAppOpsService.systemReady(); 10198 mSystemReady = true; 10199 } 10200 10201 ArrayList<ProcessRecord> procsToKill = null; 10202 synchronized(mPidsSelfLocked) { 10203 for (int i=mPidsSelfLocked.size()-1; i>=0; i--) { 10204 ProcessRecord proc = mPidsSelfLocked.valueAt(i); 10205 if (!isAllowedWhileBooting(proc.info)){ 10206 if (procsToKill == null) { 10207 procsToKill = new ArrayList<ProcessRecord>(); 10208 } 10209 procsToKill.add(proc); 10210 } 10211 } 10212 } 10213 10214 synchronized(this) { 10215 if (procsToKill != null) { 10216 for (int i=procsToKill.size()-1; i>=0; i--) { 10217 ProcessRecord proc = procsToKill.get(i); 10218 Slog.i(TAG, "Removing system update proc: " + proc); 10219 removeProcessLocked(proc, true, false, "system update done"); 10220 } 10221 } 10222 10223 // Now that we have cleaned up any update processes, we 10224 // are ready to start launching real processes and know that 10225 // we won't trample on them any more. 10226 mProcessesReady = true; 10227 } 10228 10229 Slog.i(TAG, "System now ready"); 10230 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_AMS_READY, 10231 SystemClock.uptimeMillis()); 10232 10233 synchronized(this) { 10234 // Make sure we have no pre-ready processes sitting around. 10235 10236 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) { 10237 ResolveInfo ri = mContext.getPackageManager() 10238 .resolveActivity(new Intent(Intent.ACTION_FACTORY_TEST), 10239 STOCK_PM_FLAGS); 10240 CharSequence errorMsg = null; 10241 if (ri != null) { 10242 ActivityInfo ai = ri.activityInfo; 10243 ApplicationInfo app = ai.applicationInfo; 10244 if ((app.flags&ApplicationInfo.FLAG_SYSTEM) != 0) { 10245 mTopAction = Intent.ACTION_FACTORY_TEST; 10246 mTopData = null; 10247 mTopComponent = new ComponentName(app.packageName, 10248 ai.name); 10249 } else { 10250 errorMsg = mContext.getResources().getText( 10251 com.android.internal.R.string.factorytest_not_system); 10252 } 10253 } else { 10254 errorMsg = mContext.getResources().getText( 10255 com.android.internal.R.string.factorytest_no_action); 10256 } 10257 if (errorMsg != null) { 10258 mTopAction = null; 10259 mTopData = null; 10260 mTopComponent = null; 10261 Message msg = Message.obtain(); 10262 msg.what = SHOW_FACTORY_ERROR_MSG; 10263 msg.getData().putCharSequence("msg", errorMsg); 10264 mHandler.sendMessage(msg); 10265 } 10266 } 10267 } 10268 10269 retrieveSettings(); 10270 10271 synchronized (this) { 10272 readGrantedUriPermissionsLocked(); 10273 } 10274 10275 if (goingCallback != null) goingCallback.run(); 10276 10277 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 10278 Integer.toString(mCurrentUserId), mCurrentUserId); 10279 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 10280 Integer.toString(mCurrentUserId), mCurrentUserId); 10281 mSystemServiceManager.startUser(mCurrentUserId); 10282 10283 synchronized (this) { 10284 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 10285 try { 10286 List apps = AppGlobals.getPackageManager(). 10287 getPersistentApplications(STOCK_PM_FLAGS); 10288 if (apps != null) { 10289 int N = apps.size(); 10290 int i; 10291 for (i=0; i<N; i++) { 10292 ApplicationInfo info 10293 = (ApplicationInfo)apps.get(i); 10294 if (info != null && 10295 !info.packageName.equals("android")) { 10296 addAppLocked(info, false, null /* ABI override */); 10297 } 10298 } 10299 } 10300 } catch (RemoteException ex) { 10301 // pm is in same process, this will never happen. 10302 } 10303 } 10304 10305 // Start up initial activity. 10306 mBooting = true; 10307 10308 try { 10309 if (AppGlobals.getPackageManager().hasSystemUidErrors()) { 10310 Message msg = Message.obtain(); 10311 msg.what = SHOW_UID_ERROR_MSG; 10312 mHandler.sendMessage(msg); 10313 } 10314 } catch (RemoteException e) { 10315 } 10316 10317 long ident = Binder.clearCallingIdentity(); 10318 try { 10319 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 10320 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 10321 | Intent.FLAG_RECEIVER_FOREGROUND); 10322 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 10323 broadcastIntentLocked(null, null, intent, 10324 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 10325 false, false, MY_PID, Process.SYSTEM_UID, mCurrentUserId); 10326 intent = new Intent(Intent.ACTION_USER_STARTING); 10327 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 10328 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 10329 broadcastIntentLocked(null, null, intent, 10330 null, new IIntentReceiver.Stub() { 10331 @Override 10332 public void performReceive(Intent intent, int resultCode, String data, 10333 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 10334 throws RemoteException { 10335 } 10336 }, 0, null, null, 10337 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 10338 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 10339 } catch (Throwable t) { 10340 Slog.wtf(TAG, "Failed sending first user broadcasts", t); 10341 } finally { 10342 Binder.restoreCallingIdentity(ident); 10343 } 10344 mStackSupervisor.resumeTopActivitiesLocked(); 10345 sendUserSwitchBroadcastsLocked(-1, mCurrentUserId); 10346 } 10347 } 10348 10349 private boolean makeAppCrashingLocked(ProcessRecord app, 10350 String shortMsg, String longMsg, String stackTrace) { 10351 app.crashing = true; 10352 app.crashingReport = generateProcessError(app, 10353 ActivityManager.ProcessErrorStateInfo.CRASHED, null, shortMsg, longMsg, stackTrace); 10354 startAppProblemLocked(app); 10355 app.stopFreezingAllLocked(); 10356 return handleAppCrashLocked(app, shortMsg, longMsg, stackTrace); 10357 } 10358 10359 private void makeAppNotRespondingLocked(ProcessRecord app, 10360 String activity, String shortMsg, String longMsg) { 10361 app.notResponding = true; 10362 app.notRespondingReport = generateProcessError(app, 10363 ActivityManager.ProcessErrorStateInfo.NOT_RESPONDING, 10364 activity, shortMsg, longMsg, null); 10365 startAppProblemLocked(app); 10366 app.stopFreezingAllLocked(); 10367 } 10368 10369 /** 10370 * Generate a process error record, suitable for attachment to a ProcessRecord. 10371 * 10372 * @param app The ProcessRecord in which the error occurred. 10373 * @param condition Crashing, Application Not Responding, etc. Values are defined in 10374 * ActivityManager.AppErrorStateInfo 10375 * @param activity The activity associated with the crash, if known. 10376 * @param shortMsg Short message describing the crash. 10377 * @param longMsg Long message describing the crash. 10378 * @param stackTrace Full crash stack trace, may be null. 10379 * 10380 * @return Returns a fully-formed AppErrorStateInfo record. 10381 */ 10382 private ActivityManager.ProcessErrorStateInfo generateProcessError(ProcessRecord app, 10383 int condition, String activity, String shortMsg, String longMsg, String stackTrace) { 10384 ActivityManager.ProcessErrorStateInfo report = new ActivityManager.ProcessErrorStateInfo(); 10385 10386 report.condition = condition; 10387 report.processName = app.processName; 10388 report.pid = app.pid; 10389 report.uid = app.info.uid; 10390 report.tag = activity; 10391 report.shortMsg = shortMsg; 10392 report.longMsg = longMsg; 10393 report.stackTrace = stackTrace; 10394 10395 return report; 10396 } 10397 10398 void killAppAtUsersRequest(ProcessRecord app, Dialog fromDialog) { 10399 synchronized (this) { 10400 app.crashing = false; 10401 app.crashingReport = null; 10402 app.notResponding = false; 10403 app.notRespondingReport = null; 10404 if (app.anrDialog == fromDialog) { 10405 app.anrDialog = null; 10406 } 10407 if (app.waitDialog == fromDialog) { 10408 app.waitDialog = null; 10409 } 10410 if (app.pid > 0 && app.pid != MY_PID) { 10411 handleAppCrashLocked(app, null, null, null); 10412 killUnneededProcessLocked(app, "user request after error"); 10413 } 10414 } 10415 } 10416 10417 private boolean handleAppCrashLocked(ProcessRecord app, String shortMsg, String longMsg, 10418 String stackTrace) { 10419 long now = SystemClock.uptimeMillis(); 10420 10421 Long crashTime; 10422 if (!app.isolated) { 10423 crashTime = mProcessCrashTimes.get(app.info.processName, app.uid); 10424 } else { 10425 crashTime = null; 10426 } 10427 if (crashTime != null && now < crashTime+ProcessList.MIN_CRASH_INTERVAL) { 10428 // This process loses! 10429 Slog.w(TAG, "Process " + app.info.processName 10430 + " has crashed too many times: killing!"); 10431 EventLog.writeEvent(EventLogTags.AM_PROCESS_CRASHED_TOO_MUCH, 10432 app.userId, app.info.processName, app.uid); 10433 mStackSupervisor.handleAppCrashLocked(app); 10434 if (!app.persistent) { 10435 // We don't want to start this process again until the user 10436 // explicitly does so... but for persistent process, we really 10437 // need to keep it running. If a persistent process is actually 10438 // repeatedly crashing, then badness for everyone. 10439 EventLog.writeEvent(EventLogTags.AM_PROC_BAD, app.userId, app.uid, 10440 app.info.processName); 10441 if (!app.isolated) { 10442 // XXX We don't have a way to mark isolated processes 10443 // as bad, since they don't have a peristent identity. 10444 mBadProcesses.put(app.info.processName, app.uid, 10445 new BadProcessInfo(now, shortMsg, longMsg, stackTrace)); 10446 mProcessCrashTimes.remove(app.info.processName, app.uid); 10447 } 10448 app.bad = true; 10449 app.removed = true; 10450 // Don't let services in this process be restarted and potentially 10451 // annoy the user repeatedly. Unless it is persistent, since those 10452 // processes run critical code. 10453 removeProcessLocked(app, false, false, "crash"); 10454 mStackSupervisor.resumeTopActivitiesLocked(); 10455 return false; 10456 } 10457 mStackSupervisor.resumeTopActivitiesLocked(); 10458 } else { 10459 mStackSupervisor.finishTopRunningActivityLocked(app); 10460 } 10461 10462 // Bump up the crash count of any services currently running in the proc. 10463 for (int i=app.services.size()-1; i>=0; i--) { 10464 // Any services running in the application need to be placed 10465 // back in the pending list. 10466 ServiceRecord sr = app.services.valueAt(i); 10467 sr.crashCount++; 10468 } 10469 10470 // If the crashing process is what we consider to be the "home process" and it has been 10471 // replaced by a third-party app, clear the package preferred activities from packages 10472 // with a home activity running in the process to prevent a repeatedly crashing app 10473 // from blocking the user to manually clear the list. 10474 final ArrayList<ActivityRecord> activities = app.activities; 10475 if (app == mHomeProcess && activities.size() > 0 10476 && (mHomeProcess.info.flags & ApplicationInfo.FLAG_SYSTEM) == 0) { 10477 for (int activityNdx = activities.size() - 1; activityNdx >= 0; --activityNdx) { 10478 final ActivityRecord r = activities.get(activityNdx); 10479 if (r.isHomeActivity()) { 10480 Log.i(TAG, "Clearing package preferred activities from " + r.packageName); 10481 try { 10482 ActivityThread.getPackageManager() 10483 .clearPackagePreferredActivities(r.packageName); 10484 } catch (RemoteException c) { 10485 // pm is in same process, this will never happen. 10486 } 10487 } 10488 } 10489 } 10490 10491 if (!app.isolated) { 10492 // XXX Can't keep track of crash times for isolated processes, 10493 // because they don't have a perisistent identity. 10494 mProcessCrashTimes.put(app.info.processName, app.uid, now); 10495 } 10496 10497 return true; 10498 } 10499 10500 void startAppProblemLocked(ProcessRecord app) { 10501 if (app.userId == mCurrentUserId) { 10502 app.errorReportReceiver = ApplicationErrorReport.getErrorReportReceiver( 10503 mContext, app.info.packageName, app.info.flags); 10504 } else { 10505 // If this app is not running under the current user, then we 10506 // can't give it a report button because that would require 10507 // launching the report UI under a different user. 10508 app.errorReportReceiver = null; 10509 } 10510 skipCurrentReceiverLocked(app); 10511 } 10512 10513 void skipCurrentReceiverLocked(ProcessRecord app) { 10514 for (BroadcastQueue queue : mBroadcastQueues) { 10515 queue.skipCurrentReceiverLocked(app); 10516 } 10517 } 10518 10519 /** 10520 * Used by {@link com.android.internal.os.RuntimeInit} to report when an application crashes. 10521 * The application process will exit immediately after this call returns. 10522 * @param app object of the crashing app, null for the system server 10523 * @param crashInfo describing the exception 10524 */ 10525 public void handleApplicationCrash(IBinder app, ApplicationErrorReport.CrashInfo crashInfo) { 10526 ProcessRecord r = findAppProcess(app, "Crash"); 10527 final String processName = app == null ? "system_server" 10528 : (r == null ? "unknown" : r.processName); 10529 10530 handleApplicationCrashInner("crash", r, processName, crashInfo); 10531 } 10532 10533 /* Native crash reporting uses this inner version because it needs to be somewhat 10534 * decoupled from the AM-managed cleanup lifecycle 10535 */ 10536 void handleApplicationCrashInner(String eventType, ProcessRecord r, String processName, 10537 ApplicationErrorReport.CrashInfo crashInfo) { 10538 EventLog.writeEvent(EventLogTags.AM_CRASH, Binder.getCallingPid(), 10539 UserHandle.getUserId(Binder.getCallingUid()), processName, 10540 r == null ? -1 : r.info.flags, 10541 crashInfo.exceptionClassName, 10542 crashInfo.exceptionMessage, 10543 crashInfo.throwFileName, 10544 crashInfo.throwLineNumber); 10545 10546 addErrorToDropBox(eventType, r, processName, null, null, null, null, null, crashInfo); 10547 10548 crashApplication(r, crashInfo); 10549 } 10550 10551 public void handleApplicationStrictModeViolation( 10552 IBinder app, 10553 int violationMask, 10554 StrictMode.ViolationInfo info) { 10555 ProcessRecord r = findAppProcess(app, "StrictMode"); 10556 if (r == null) { 10557 return; 10558 } 10559 10560 if ((violationMask & StrictMode.PENALTY_DROPBOX) != 0) { 10561 Integer stackFingerprint = info.hashCode(); 10562 boolean logIt = true; 10563 synchronized (mAlreadyLoggedViolatedStacks) { 10564 if (mAlreadyLoggedViolatedStacks.contains(stackFingerprint)) { 10565 logIt = false; 10566 // TODO: sub-sample into EventLog for these, with 10567 // the info.durationMillis? Then we'd get 10568 // the relative pain numbers, without logging all 10569 // the stack traces repeatedly. We'd want to do 10570 // likewise in the client code, which also does 10571 // dup suppression, before the Binder call. 10572 } else { 10573 if (mAlreadyLoggedViolatedStacks.size() >= MAX_DUP_SUPPRESSED_STACKS) { 10574 mAlreadyLoggedViolatedStacks.clear(); 10575 } 10576 mAlreadyLoggedViolatedStacks.add(stackFingerprint); 10577 } 10578 } 10579 if (logIt) { 10580 logStrictModeViolationToDropBox(r, info); 10581 } 10582 } 10583 10584 if ((violationMask & StrictMode.PENALTY_DIALOG) != 0) { 10585 AppErrorResult result = new AppErrorResult(); 10586 synchronized (this) { 10587 final long origId = Binder.clearCallingIdentity(); 10588 10589 Message msg = Message.obtain(); 10590 msg.what = SHOW_STRICT_MODE_VIOLATION_MSG; 10591 HashMap<String, Object> data = new HashMap<String, Object>(); 10592 data.put("result", result); 10593 data.put("app", r); 10594 data.put("violationMask", violationMask); 10595 data.put("info", info); 10596 msg.obj = data; 10597 mHandler.sendMessage(msg); 10598 10599 Binder.restoreCallingIdentity(origId); 10600 } 10601 int res = result.get(); 10602 Slog.w(TAG, "handleApplicationStrictModeViolation; res=" + res); 10603 } 10604 } 10605 10606 // Depending on the policy in effect, there could be a bunch of 10607 // these in quick succession so we try to batch these together to 10608 // minimize disk writes, number of dropbox entries, and maximize 10609 // compression, by having more fewer, larger records. 10610 private void logStrictModeViolationToDropBox( 10611 ProcessRecord process, 10612 StrictMode.ViolationInfo info) { 10613 if (info == null) { 10614 return; 10615 } 10616 final boolean isSystemApp = process == null || 10617 (process.info.flags & (ApplicationInfo.FLAG_SYSTEM | 10618 ApplicationInfo.FLAG_UPDATED_SYSTEM_APP)) != 0; 10619 final String processName = process == null ? "unknown" : process.processName; 10620 final String dropboxTag = isSystemApp ? "system_app_strictmode" : "data_app_strictmode"; 10621 final DropBoxManager dbox = (DropBoxManager) 10622 mContext.getSystemService(Context.DROPBOX_SERVICE); 10623 10624 // Exit early if the dropbox isn't configured to accept this report type. 10625 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 10626 10627 boolean bufferWasEmpty; 10628 boolean needsFlush; 10629 final StringBuilder sb = isSystemApp ? mStrictModeBuffer : new StringBuilder(1024); 10630 synchronized (sb) { 10631 bufferWasEmpty = sb.length() == 0; 10632 appendDropBoxProcessHeaders(process, processName, sb); 10633 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 10634 sb.append("System-App: ").append(isSystemApp).append("\n"); 10635 sb.append("Uptime-Millis: ").append(info.violationUptimeMillis).append("\n"); 10636 if (info.violationNumThisLoop != 0) { 10637 sb.append("Loop-Violation-Number: ").append(info.violationNumThisLoop).append("\n"); 10638 } 10639 if (info.numAnimationsRunning != 0) { 10640 sb.append("Animations-Running: ").append(info.numAnimationsRunning).append("\n"); 10641 } 10642 if (info.broadcastIntentAction != null) { 10643 sb.append("Broadcast-Intent-Action: ").append(info.broadcastIntentAction).append("\n"); 10644 } 10645 if (info.durationMillis != -1) { 10646 sb.append("Duration-Millis: ").append(info.durationMillis).append("\n"); 10647 } 10648 if (info.numInstances != -1) { 10649 sb.append("Instance-Count: ").append(info.numInstances).append("\n"); 10650 } 10651 if (info.tags != null) { 10652 for (String tag : info.tags) { 10653 sb.append("Span-Tag: ").append(tag).append("\n"); 10654 } 10655 } 10656 sb.append("\n"); 10657 if (info.crashInfo != null && info.crashInfo.stackTrace != null) { 10658 sb.append(info.crashInfo.stackTrace); 10659 } 10660 sb.append("\n"); 10661 10662 // Only buffer up to ~64k. Various logging bits truncate 10663 // things at 128k. 10664 needsFlush = (sb.length() > 64 * 1024); 10665 } 10666 10667 // Flush immediately if the buffer's grown too large, or this 10668 // is a non-system app. Non-system apps are isolated with a 10669 // different tag & policy and not batched. 10670 // 10671 // Batching is useful during internal testing with 10672 // StrictMode settings turned up high. Without batching, 10673 // thousands of separate files could be created on boot. 10674 if (!isSystemApp || needsFlush) { 10675 new Thread("Error dump: " + dropboxTag) { 10676 @Override 10677 public void run() { 10678 String report; 10679 synchronized (sb) { 10680 report = sb.toString(); 10681 sb.delete(0, sb.length()); 10682 sb.trimToSize(); 10683 } 10684 if (report.length() != 0) { 10685 dbox.addText(dropboxTag, report); 10686 } 10687 } 10688 }.start(); 10689 return; 10690 } 10691 10692 // System app batching: 10693 if (!bufferWasEmpty) { 10694 // An existing dropbox-writing thread is outstanding, so 10695 // we don't need to start it up. The existing thread will 10696 // catch the buffer appends we just did. 10697 return; 10698 } 10699 10700 // Worker thread to both batch writes and to avoid blocking the caller on I/O. 10701 // (After this point, we shouldn't access AMS internal data structures.) 10702 new Thread("Error dump: " + dropboxTag) { 10703 @Override 10704 public void run() { 10705 // 5 second sleep to let stacks arrive and be batched together 10706 try { 10707 Thread.sleep(5000); // 5 seconds 10708 } catch (InterruptedException e) {} 10709 10710 String errorReport; 10711 synchronized (mStrictModeBuffer) { 10712 errorReport = mStrictModeBuffer.toString(); 10713 if (errorReport.length() == 0) { 10714 return; 10715 } 10716 mStrictModeBuffer.delete(0, mStrictModeBuffer.length()); 10717 mStrictModeBuffer.trimToSize(); 10718 } 10719 dbox.addText(dropboxTag, errorReport); 10720 } 10721 }.start(); 10722 } 10723 10724 /** 10725 * Used by {@link Log} via {@link com.android.internal.os.RuntimeInit} to report serious errors. 10726 * @param app object of the crashing app, null for the system server 10727 * @param tag reported by the caller 10728 * @param crashInfo describing the context of the error 10729 * @return true if the process should exit immediately (WTF is fatal) 10730 */ 10731 public boolean handleApplicationWtf(IBinder app, String tag, 10732 ApplicationErrorReport.CrashInfo crashInfo) { 10733 ProcessRecord r = findAppProcess(app, "WTF"); 10734 final String processName = app == null ? "system_server" 10735 : (r == null ? "unknown" : r.processName); 10736 10737 EventLog.writeEvent(EventLogTags.AM_WTF, 10738 UserHandle.getUserId(Binder.getCallingUid()), Binder.getCallingPid(), 10739 processName, 10740 r == null ? -1 : r.info.flags, 10741 tag, crashInfo.exceptionMessage); 10742 10743 addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, crashInfo); 10744 10745 if (r != null && r.pid != Process.myPid() && 10746 Settings.Global.getInt(mContext.getContentResolver(), 10747 Settings.Global.WTF_IS_FATAL, 0) != 0) { 10748 crashApplication(r, crashInfo); 10749 return true; 10750 } else { 10751 return false; 10752 } 10753 } 10754 10755 /** 10756 * @param app object of some object (as stored in {@link com.android.internal.os.RuntimeInit}) 10757 * @return the corresponding {@link ProcessRecord} object, or null if none could be found 10758 */ 10759 private ProcessRecord findAppProcess(IBinder app, String reason) { 10760 if (app == null) { 10761 return null; 10762 } 10763 10764 synchronized (this) { 10765 final int NP = mProcessNames.getMap().size(); 10766 for (int ip=0; ip<NP; ip++) { 10767 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 10768 final int NA = apps.size(); 10769 for (int ia=0; ia<NA; ia++) { 10770 ProcessRecord p = apps.valueAt(ia); 10771 if (p.thread != null && p.thread.asBinder() == app) { 10772 return p; 10773 } 10774 } 10775 } 10776 10777 Slog.w(TAG, "Can't find mystery application for " + reason 10778 + " from pid=" + Binder.getCallingPid() 10779 + " uid=" + Binder.getCallingUid() + ": " + app); 10780 return null; 10781 } 10782 } 10783 10784 /** 10785 * Utility function for addErrorToDropBox and handleStrictModeViolation's logging 10786 * to append various headers to the dropbox log text. 10787 */ 10788 private void appendDropBoxProcessHeaders(ProcessRecord process, String processName, 10789 StringBuilder sb) { 10790 // Watchdog thread ends up invoking this function (with 10791 // a null ProcessRecord) to add the stack file to dropbox. 10792 // Do not acquire a lock on this (am) in such cases, as it 10793 // could cause a potential deadlock, if and when watchdog 10794 // is invoked due to unavailability of lock on am and it 10795 // would prevent watchdog from killing system_server. 10796 if (process == null) { 10797 sb.append("Process: ").append(processName).append("\n"); 10798 return; 10799 } 10800 // Note: ProcessRecord 'process' is guarded by the service 10801 // instance. (notably process.pkgList, which could otherwise change 10802 // concurrently during execution of this method) 10803 synchronized (this) { 10804 sb.append("Process: ").append(processName).append("\n"); 10805 int flags = process.info.flags; 10806 IPackageManager pm = AppGlobals.getPackageManager(); 10807 sb.append("Flags: 0x").append(Integer.toString(flags, 16)).append("\n"); 10808 for (int ip=0; ip<process.pkgList.size(); ip++) { 10809 String pkg = process.pkgList.keyAt(ip); 10810 sb.append("Package: ").append(pkg); 10811 try { 10812 PackageInfo pi = pm.getPackageInfo(pkg, 0, UserHandle.getCallingUserId()); 10813 if (pi != null) { 10814 sb.append(" v").append(pi.versionCode); 10815 if (pi.versionName != null) { 10816 sb.append(" (").append(pi.versionName).append(")"); 10817 } 10818 } 10819 } catch (RemoteException e) { 10820 Slog.e(TAG, "Error getting package info: " + pkg, e); 10821 } 10822 sb.append("\n"); 10823 } 10824 } 10825 } 10826 10827 private static String processClass(ProcessRecord process) { 10828 if (process == null || process.pid == MY_PID) { 10829 return "system_server"; 10830 } else if ((process.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 10831 return "system_app"; 10832 } else { 10833 return "data_app"; 10834 } 10835 } 10836 10837 /** 10838 * Write a description of an error (crash, WTF, ANR) to the drop box. 10839 * @param eventType to include in the drop box tag ("crash", "wtf", etc.) 10840 * @param process which caused the error, null means the system server 10841 * @param activity which triggered the error, null if unknown 10842 * @param parent activity related to the error, null if unknown 10843 * @param subject line related to the error, null if absent 10844 * @param report in long form describing the error, null if absent 10845 * @param logFile to include in the report, null if none 10846 * @param crashInfo giving an application stack trace, null if absent 10847 */ 10848 public void addErrorToDropBox(String eventType, 10849 ProcessRecord process, String processName, ActivityRecord activity, 10850 ActivityRecord parent, String subject, 10851 final String report, final File logFile, 10852 final ApplicationErrorReport.CrashInfo crashInfo) { 10853 // NOTE -- this must never acquire the ActivityManagerService lock, 10854 // otherwise the watchdog may be prevented from resetting the system. 10855 10856 final String dropboxTag = processClass(process) + "_" + eventType; 10857 final DropBoxManager dbox = (DropBoxManager) 10858 mContext.getSystemService(Context.DROPBOX_SERVICE); 10859 10860 // Exit early if the dropbox isn't configured to accept this report type. 10861 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 10862 10863 final StringBuilder sb = new StringBuilder(1024); 10864 appendDropBoxProcessHeaders(process, processName, sb); 10865 if (activity != null) { 10866 sb.append("Activity: ").append(activity.shortComponentName).append("\n"); 10867 } 10868 if (parent != null && parent.app != null && parent.app.pid != process.pid) { 10869 sb.append("Parent-Process: ").append(parent.app.processName).append("\n"); 10870 } 10871 if (parent != null && parent != activity) { 10872 sb.append("Parent-Activity: ").append(parent.shortComponentName).append("\n"); 10873 } 10874 if (subject != null) { 10875 sb.append("Subject: ").append(subject).append("\n"); 10876 } 10877 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 10878 if (Debug.isDebuggerConnected()) { 10879 sb.append("Debugger: Connected\n"); 10880 } 10881 sb.append("\n"); 10882 10883 // Do the rest in a worker thread to avoid blocking the caller on I/O 10884 // (After this point, we shouldn't access AMS internal data structures.) 10885 Thread worker = new Thread("Error dump: " + dropboxTag) { 10886 @Override 10887 public void run() { 10888 if (report != null) { 10889 sb.append(report); 10890 } 10891 if (logFile != null) { 10892 try { 10893 sb.append(FileUtils.readTextFile(logFile, DROPBOX_MAX_SIZE, 10894 "\n\n[[TRUNCATED]]")); 10895 } catch (IOException e) { 10896 Slog.e(TAG, "Error reading " + logFile, e); 10897 } 10898 } 10899 if (crashInfo != null && crashInfo.stackTrace != null) { 10900 sb.append(crashInfo.stackTrace); 10901 } 10902 10903 String setting = Settings.Global.ERROR_LOGCAT_PREFIX + dropboxTag; 10904 int lines = Settings.Global.getInt(mContext.getContentResolver(), setting, 0); 10905 if (lines > 0) { 10906 sb.append("\n"); 10907 10908 // Merge several logcat streams, and take the last N lines 10909 InputStreamReader input = null; 10910 try { 10911 java.lang.Process logcat = new ProcessBuilder("/system/bin/logcat", 10912 "-v", "time", "-b", "events", "-b", "system", "-b", "main", 10913 "-t", String.valueOf(lines)).redirectErrorStream(true).start(); 10914 10915 try { logcat.getOutputStream().close(); } catch (IOException e) {} 10916 try { logcat.getErrorStream().close(); } catch (IOException e) {} 10917 input = new InputStreamReader(logcat.getInputStream()); 10918 10919 int num; 10920 char[] buf = new char[8192]; 10921 while ((num = input.read(buf)) > 0) sb.append(buf, 0, num); 10922 } catch (IOException e) { 10923 Slog.e(TAG, "Error running logcat", e); 10924 } finally { 10925 if (input != null) try { input.close(); } catch (IOException e) {} 10926 } 10927 } 10928 10929 dbox.addText(dropboxTag, sb.toString()); 10930 } 10931 }; 10932 10933 if (process == null) { 10934 // If process is null, we are being called from some internal code 10935 // and may be about to die -- run this synchronously. 10936 worker.run(); 10937 } else { 10938 worker.start(); 10939 } 10940 } 10941 10942 /** 10943 * Bring up the "unexpected error" dialog box for a crashing app. 10944 * Deal with edge cases (intercepts from instrumented applications, 10945 * ActivityController, error intent receivers, that sort of thing). 10946 * @param r the application crashing 10947 * @param crashInfo describing the failure 10948 */ 10949 private void crashApplication(ProcessRecord r, ApplicationErrorReport.CrashInfo crashInfo) { 10950 long timeMillis = System.currentTimeMillis(); 10951 String shortMsg = crashInfo.exceptionClassName; 10952 String longMsg = crashInfo.exceptionMessage; 10953 String stackTrace = crashInfo.stackTrace; 10954 if (shortMsg != null && longMsg != null) { 10955 longMsg = shortMsg + ": " + longMsg; 10956 } else if (shortMsg != null) { 10957 longMsg = shortMsg; 10958 } 10959 10960 AppErrorResult result = new AppErrorResult(); 10961 synchronized (this) { 10962 if (mController != null) { 10963 try { 10964 String name = r != null ? r.processName : null; 10965 int pid = r != null ? r.pid : Binder.getCallingPid(); 10966 int uid = r != null ? r.info.uid : Binder.getCallingUid(); 10967 if (!mController.appCrashed(name, pid, 10968 shortMsg, longMsg, timeMillis, crashInfo.stackTrace)) { 10969 Slog.w(TAG, "Force-killing crashed app " + name 10970 + " at watcher's request"); 10971 Process.killProcess(pid); 10972 if (r != null) { 10973 Process.killProcessGroup(uid, pid); 10974 } 10975 return; 10976 } 10977 } catch (RemoteException e) { 10978 mController = null; 10979 Watchdog.getInstance().setActivityController(null); 10980 } 10981 } 10982 10983 final long origId = Binder.clearCallingIdentity(); 10984 10985 // If this process is running instrumentation, finish it. 10986 if (r != null && r.instrumentationClass != null) { 10987 Slog.w(TAG, "Error in app " + r.processName 10988 + " running instrumentation " + r.instrumentationClass + ":"); 10989 if (shortMsg != null) Slog.w(TAG, " " + shortMsg); 10990 if (longMsg != null) Slog.w(TAG, " " + longMsg); 10991 Bundle info = new Bundle(); 10992 info.putString("shortMsg", shortMsg); 10993 info.putString("longMsg", longMsg); 10994 finishInstrumentationLocked(r, Activity.RESULT_CANCELED, info); 10995 Binder.restoreCallingIdentity(origId); 10996 return; 10997 } 10998 10999 // If we can't identify the process or it's already exceeded its crash quota, 11000 // quit right away without showing a crash dialog. 11001 if (r == null || !makeAppCrashingLocked(r, shortMsg, longMsg, stackTrace)) { 11002 Binder.restoreCallingIdentity(origId); 11003 return; 11004 } 11005 11006 Message msg = Message.obtain(); 11007 msg.what = SHOW_ERROR_MSG; 11008 HashMap data = new HashMap(); 11009 data.put("result", result); 11010 data.put("app", r); 11011 msg.obj = data; 11012 mHandler.sendMessage(msg); 11013 11014 Binder.restoreCallingIdentity(origId); 11015 } 11016 11017 int res = result.get(); 11018 11019 Intent appErrorIntent = null; 11020 synchronized (this) { 11021 if (r != null && !r.isolated) { 11022 // XXX Can't keep track of crash time for isolated processes, 11023 // since they don't have a persistent identity. 11024 mProcessCrashTimes.put(r.info.processName, r.uid, 11025 SystemClock.uptimeMillis()); 11026 } 11027 if (res == AppErrorDialog.FORCE_QUIT_AND_REPORT) { 11028 appErrorIntent = createAppErrorIntentLocked(r, timeMillis, crashInfo); 11029 } 11030 } 11031 11032 if (appErrorIntent != null) { 11033 try { 11034 mContext.startActivityAsUser(appErrorIntent, new UserHandle(r.userId)); 11035 } catch (ActivityNotFoundException e) { 11036 Slog.w(TAG, "bug report receiver dissappeared", e); 11037 } 11038 } 11039 } 11040 11041 Intent createAppErrorIntentLocked(ProcessRecord r, 11042 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 11043 ApplicationErrorReport report = createAppErrorReportLocked(r, timeMillis, crashInfo); 11044 if (report == null) { 11045 return null; 11046 } 11047 Intent result = new Intent(Intent.ACTION_APP_ERROR); 11048 result.setComponent(r.errorReportReceiver); 11049 result.putExtra(Intent.EXTRA_BUG_REPORT, report); 11050 result.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 11051 return result; 11052 } 11053 11054 private ApplicationErrorReport createAppErrorReportLocked(ProcessRecord r, 11055 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 11056 if (r.errorReportReceiver == null) { 11057 return null; 11058 } 11059 11060 if (!r.crashing && !r.notResponding && !r.forceCrashReport) { 11061 return null; 11062 } 11063 11064 ApplicationErrorReport report = new ApplicationErrorReport(); 11065 report.packageName = r.info.packageName; 11066 report.installerPackageName = r.errorReportReceiver.getPackageName(); 11067 report.processName = r.processName; 11068 report.time = timeMillis; 11069 report.systemApp = (r.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0; 11070 11071 if (r.crashing || r.forceCrashReport) { 11072 report.type = ApplicationErrorReport.TYPE_CRASH; 11073 report.crashInfo = crashInfo; 11074 } else if (r.notResponding) { 11075 report.type = ApplicationErrorReport.TYPE_ANR; 11076 report.anrInfo = new ApplicationErrorReport.AnrInfo(); 11077 11078 report.anrInfo.activity = r.notRespondingReport.tag; 11079 report.anrInfo.cause = r.notRespondingReport.shortMsg; 11080 report.anrInfo.info = r.notRespondingReport.longMsg; 11081 } 11082 11083 return report; 11084 } 11085 11086 public List<ActivityManager.ProcessErrorStateInfo> getProcessesInErrorState() { 11087 enforceNotIsolatedCaller("getProcessesInErrorState"); 11088 // assume our apps are happy - lazy create the list 11089 List<ActivityManager.ProcessErrorStateInfo> errList = null; 11090 11091 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 11092 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 11093 int userId = UserHandle.getUserId(Binder.getCallingUid()); 11094 11095 synchronized (this) { 11096 11097 // iterate across all processes 11098 for (int i=mLruProcesses.size()-1; i>=0; i--) { 11099 ProcessRecord app = mLruProcesses.get(i); 11100 if (!allUsers && app.userId != userId) { 11101 continue; 11102 } 11103 if ((app.thread != null) && (app.crashing || app.notResponding)) { 11104 // This one's in trouble, so we'll generate a report for it 11105 // crashes are higher priority (in case there's a crash *and* an anr) 11106 ActivityManager.ProcessErrorStateInfo report = null; 11107 if (app.crashing) { 11108 report = app.crashingReport; 11109 } else if (app.notResponding) { 11110 report = app.notRespondingReport; 11111 } 11112 11113 if (report != null) { 11114 if (errList == null) { 11115 errList = new ArrayList<ActivityManager.ProcessErrorStateInfo>(1); 11116 } 11117 errList.add(report); 11118 } else { 11119 Slog.w(TAG, "Missing app error report, app = " + app.processName + 11120 " crashing = " + app.crashing + 11121 " notResponding = " + app.notResponding); 11122 } 11123 } 11124 } 11125 } 11126 11127 return errList; 11128 } 11129 11130 static int procStateToImportance(int procState, int memAdj, 11131 ActivityManager.RunningAppProcessInfo currApp) { 11132 int imp = ActivityManager.RunningAppProcessInfo.procStateToImportance(procState); 11133 if (imp == ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND) { 11134 currApp.lru = memAdj; 11135 } else { 11136 currApp.lru = 0; 11137 } 11138 return imp; 11139 } 11140 11141 private void fillInProcMemInfo(ProcessRecord app, 11142 ActivityManager.RunningAppProcessInfo outInfo) { 11143 outInfo.pid = app.pid; 11144 outInfo.uid = app.info.uid; 11145 if (mHeavyWeightProcess == app) { 11146 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_CANT_SAVE_STATE; 11147 } 11148 if (app.persistent) { 11149 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_PERSISTENT; 11150 } 11151 if (app.activities.size() > 0) { 11152 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_HAS_ACTIVITIES; 11153 } 11154 outInfo.lastTrimLevel = app.trimMemoryLevel; 11155 int adj = app.curAdj; 11156 int procState = app.curProcState; 11157 outInfo.importance = procStateToImportance(procState, adj, outInfo); 11158 outInfo.importanceReasonCode = app.adjTypeCode; 11159 outInfo.processState = app.curProcState; 11160 } 11161 11162 public List<ActivityManager.RunningAppProcessInfo> getRunningAppProcesses() { 11163 enforceNotIsolatedCaller("getRunningAppProcesses"); 11164 // Lazy instantiation of list 11165 List<ActivityManager.RunningAppProcessInfo> runList = null; 11166 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 11167 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 11168 int userId = UserHandle.getUserId(Binder.getCallingUid()); 11169 synchronized (this) { 11170 // Iterate across all processes 11171 for (int i=mLruProcesses.size()-1; i>=0; i--) { 11172 ProcessRecord app = mLruProcesses.get(i); 11173 if (!allUsers && app.userId != userId) { 11174 continue; 11175 } 11176 if ((app.thread != null) && (!app.crashing && !app.notResponding)) { 11177 // Generate process state info for running application 11178 ActivityManager.RunningAppProcessInfo currApp = 11179 new ActivityManager.RunningAppProcessInfo(app.processName, 11180 app.pid, app.getPackageList()); 11181 fillInProcMemInfo(app, currApp); 11182 if (app.adjSource instanceof ProcessRecord) { 11183 currApp.importanceReasonPid = ((ProcessRecord)app.adjSource).pid; 11184 currApp.importanceReasonImportance = 11185 ActivityManager.RunningAppProcessInfo.procStateToImportance( 11186 app.adjSourceProcState); 11187 } else if (app.adjSource instanceof ActivityRecord) { 11188 ActivityRecord r = (ActivityRecord)app.adjSource; 11189 if (r.app != null) currApp.importanceReasonPid = r.app.pid; 11190 } 11191 if (app.adjTarget instanceof ComponentName) { 11192 currApp.importanceReasonComponent = (ComponentName)app.adjTarget; 11193 } 11194 //Slog.v(TAG, "Proc " + app.processName + ": imp=" + currApp.importance 11195 // + " lru=" + currApp.lru); 11196 if (runList == null) { 11197 runList = new ArrayList<ActivityManager.RunningAppProcessInfo>(); 11198 } 11199 runList.add(currApp); 11200 } 11201 } 11202 } 11203 return runList; 11204 } 11205 11206 public List<ApplicationInfo> getRunningExternalApplications() { 11207 enforceNotIsolatedCaller("getRunningExternalApplications"); 11208 List<ActivityManager.RunningAppProcessInfo> runningApps = getRunningAppProcesses(); 11209 List<ApplicationInfo> retList = new ArrayList<ApplicationInfo>(); 11210 if (runningApps != null && runningApps.size() > 0) { 11211 Set<String> extList = new HashSet<String>(); 11212 for (ActivityManager.RunningAppProcessInfo app : runningApps) { 11213 if (app.pkgList != null) { 11214 for (String pkg : app.pkgList) { 11215 extList.add(pkg); 11216 } 11217 } 11218 } 11219 IPackageManager pm = AppGlobals.getPackageManager(); 11220 for (String pkg : extList) { 11221 try { 11222 ApplicationInfo info = pm.getApplicationInfo(pkg, 0, UserHandle.getCallingUserId()); 11223 if ((info.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0) { 11224 retList.add(info); 11225 } 11226 } catch (RemoteException e) { 11227 } 11228 } 11229 } 11230 return retList; 11231 } 11232 11233 @Override 11234 public void getMyMemoryState(ActivityManager.RunningAppProcessInfo outInfo) { 11235 enforceNotIsolatedCaller("getMyMemoryState"); 11236 synchronized (this) { 11237 ProcessRecord proc; 11238 synchronized (mPidsSelfLocked) { 11239 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 11240 } 11241 fillInProcMemInfo(proc, outInfo); 11242 } 11243 } 11244 11245 @Override 11246 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 11247 if (checkCallingPermission(android.Manifest.permission.DUMP) 11248 != PackageManager.PERMISSION_GRANTED) { 11249 pw.println("Permission Denial: can't dump ActivityManager from from pid=" 11250 + Binder.getCallingPid() 11251 + ", uid=" + Binder.getCallingUid() 11252 + " without permission " 11253 + android.Manifest.permission.DUMP); 11254 return; 11255 } 11256 11257 boolean dumpAll = false; 11258 boolean dumpClient = false; 11259 String dumpPackage = null; 11260 11261 int opti = 0; 11262 while (opti < args.length) { 11263 String opt = args[opti]; 11264 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 11265 break; 11266 } 11267 opti++; 11268 if ("-a".equals(opt)) { 11269 dumpAll = true; 11270 } else if ("-c".equals(opt)) { 11271 dumpClient = true; 11272 } else if ("-h".equals(opt)) { 11273 pw.println("Activity manager dump options:"); 11274 pw.println(" [-a] [-c] [-h] [cmd] ..."); 11275 pw.println(" cmd may be one of:"); 11276 pw.println(" a[ctivities]: activity stack state"); 11277 pw.println(" b[roadcasts] [PACKAGE_NAME] [history [-s]]: broadcast state"); 11278 pw.println(" i[ntents] [PACKAGE_NAME]: pending intent state"); 11279 pw.println(" p[rocesses] [PACKAGE_NAME]: process state"); 11280 pw.println(" o[om]: out of memory management"); 11281 pw.println(" prov[iders] [COMP_SPEC ...]: content provider state"); 11282 pw.println(" provider [COMP_SPEC]: provider client-side state"); 11283 pw.println(" s[ervices] [COMP_SPEC ...]: service state"); 11284 pw.println(" service [COMP_SPEC]: service client-side state"); 11285 pw.println(" package [PACKAGE_NAME]: all state related to given package"); 11286 pw.println(" all: dump all activities"); 11287 pw.println(" top: dump the top activity"); 11288 pw.println(" cmd may also be a COMP_SPEC to dump activities."); 11289 pw.println(" COMP_SPEC may be a component name (com.foo/.myApp),"); 11290 pw.println(" a partial substring in a component name, a"); 11291 pw.println(" hex object identifier."); 11292 pw.println(" -a: include all available server state."); 11293 pw.println(" -c: include client state."); 11294 return; 11295 } else { 11296 pw.println("Unknown argument: " + opt + "; use -h for help"); 11297 } 11298 } 11299 11300 long origId = Binder.clearCallingIdentity(); 11301 boolean more = false; 11302 // Is the caller requesting to dump a particular piece of data? 11303 if (opti < args.length) { 11304 String cmd = args[opti]; 11305 opti++; 11306 if ("activities".equals(cmd) || "a".equals(cmd)) { 11307 synchronized (this) { 11308 dumpActivitiesLocked(fd, pw, args, opti, true, dumpClient, null); 11309 } 11310 } else if ("broadcasts".equals(cmd) || "b".equals(cmd)) { 11311 String[] newArgs; 11312 String name; 11313 if (opti >= args.length) { 11314 name = null; 11315 newArgs = EMPTY_STRING_ARRAY; 11316 } else { 11317 name = args[opti]; 11318 opti++; 11319 newArgs = new String[args.length - opti]; 11320 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11321 args.length - opti); 11322 } 11323 synchronized (this) { 11324 dumpBroadcastsLocked(fd, pw, args, opti, true, name); 11325 } 11326 } else if ("intents".equals(cmd) || "i".equals(cmd)) { 11327 String[] newArgs; 11328 String name; 11329 if (opti >= args.length) { 11330 name = null; 11331 newArgs = EMPTY_STRING_ARRAY; 11332 } else { 11333 name = args[opti]; 11334 opti++; 11335 newArgs = new String[args.length - opti]; 11336 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11337 args.length - opti); 11338 } 11339 synchronized (this) { 11340 dumpPendingIntentsLocked(fd, pw, args, opti, true, name); 11341 } 11342 } else if ("processes".equals(cmd) || "p".equals(cmd)) { 11343 String[] newArgs; 11344 String name; 11345 if (opti >= args.length) { 11346 name = null; 11347 newArgs = EMPTY_STRING_ARRAY; 11348 } else { 11349 name = args[opti]; 11350 opti++; 11351 newArgs = new String[args.length - opti]; 11352 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11353 args.length - opti); 11354 } 11355 synchronized (this) { 11356 dumpProcessesLocked(fd, pw, args, opti, true, name); 11357 } 11358 } else if ("oom".equals(cmd) || "o".equals(cmd)) { 11359 synchronized (this) { 11360 dumpOomLocked(fd, pw, args, opti, true); 11361 } 11362 } else if ("provider".equals(cmd)) { 11363 String[] newArgs; 11364 String name; 11365 if (opti >= args.length) { 11366 name = null; 11367 newArgs = EMPTY_STRING_ARRAY; 11368 } else { 11369 name = args[opti]; 11370 opti++; 11371 newArgs = new String[args.length - opti]; 11372 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, args.length - opti); 11373 } 11374 if (!dumpProvider(fd, pw, name, newArgs, 0, dumpAll)) { 11375 pw.println("No providers match: " + name); 11376 pw.println("Use -h for help."); 11377 } 11378 } else if ("providers".equals(cmd) || "prov".equals(cmd)) { 11379 synchronized (this) { 11380 dumpProvidersLocked(fd, pw, args, opti, true, null); 11381 } 11382 } else if ("service".equals(cmd)) { 11383 String[] newArgs; 11384 String name; 11385 if (opti >= args.length) { 11386 name = null; 11387 newArgs = EMPTY_STRING_ARRAY; 11388 } else { 11389 name = args[opti]; 11390 opti++; 11391 newArgs = new String[args.length - opti]; 11392 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11393 args.length - opti); 11394 } 11395 if (!mServices.dumpService(fd, pw, name, newArgs, 0, dumpAll)) { 11396 pw.println("No services match: " + name); 11397 pw.println("Use -h for help."); 11398 } 11399 } else if ("package".equals(cmd)) { 11400 String[] newArgs; 11401 if (opti >= args.length) { 11402 pw.println("package: no package name specified"); 11403 pw.println("Use -h for help."); 11404 } else { 11405 dumpPackage = args[opti]; 11406 opti++; 11407 newArgs = new String[args.length - opti]; 11408 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11409 args.length - opti); 11410 args = newArgs; 11411 opti = 0; 11412 more = true; 11413 } 11414 } else if ("services".equals(cmd) || "s".equals(cmd)) { 11415 synchronized (this) { 11416 mServices.dumpServicesLocked(fd, pw, args, opti, true, dumpClient, null); 11417 } 11418 } else { 11419 // Dumping a single activity? 11420 if (!dumpActivity(fd, pw, cmd, args, opti, dumpAll)) { 11421 pw.println("Bad activity command, or no activities match: " + cmd); 11422 pw.println("Use -h for help."); 11423 } 11424 } 11425 if (!more) { 11426 Binder.restoreCallingIdentity(origId); 11427 return; 11428 } 11429 } 11430 11431 // No piece of data specified, dump everything. 11432 synchronized (this) { 11433 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11434 pw.println(); 11435 if (dumpAll) { 11436 pw.println("-------------------------------------------------------------------------------"); 11437 } 11438 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11439 pw.println(); 11440 if (dumpAll) { 11441 pw.println("-------------------------------------------------------------------------------"); 11442 } 11443 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11444 pw.println(); 11445 if (dumpAll) { 11446 pw.println("-------------------------------------------------------------------------------"); 11447 } 11448 mServices.dumpServicesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 11449 pw.println(); 11450 if (dumpAll) { 11451 pw.println("-------------------------------------------------------------------------------"); 11452 } 11453 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 11454 pw.println(); 11455 if (dumpAll) { 11456 pw.println("-------------------------------------------------------------------------------"); 11457 } 11458 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11459 } 11460 Binder.restoreCallingIdentity(origId); 11461 } 11462 11463 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11464 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) { 11465 pw.println("ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)"); 11466 11467 boolean printedAnything = mStackSupervisor.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient, 11468 dumpPackage); 11469 boolean needSep = printedAnything; 11470 11471 boolean printed = ActivityStackSupervisor.printThisActivity(pw, mFocusedActivity, 11472 dumpPackage, needSep, " mFocusedActivity: "); 11473 if (printed) { 11474 printedAnything = true; 11475 needSep = false; 11476 } 11477 11478 if (dumpPackage == null) { 11479 if (needSep) { 11480 pw.println(); 11481 } 11482 needSep = true; 11483 printedAnything = true; 11484 mStackSupervisor.dump(pw, " "); 11485 } 11486 11487 if (mRecentTasks.size() > 0) { 11488 boolean printedHeader = false; 11489 11490 final int N = mRecentTasks.size(); 11491 for (int i=0; i<N; i++) { 11492 TaskRecord tr = mRecentTasks.get(i); 11493 if (dumpPackage != null) { 11494 if (tr.realActivity == null || 11495 !dumpPackage.equals(tr.realActivity)) { 11496 continue; 11497 } 11498 } 11499 if (!printedHeader) { 11500 if (needSep) { 11501 pw.println(); 11502 } 11503 pw.println(" Recent tasks:"); 11504 printedHeader = true; 11505 printedAnything = true; 11506 } 11507 pw.print(" * Recent #"); pw.print(i); pw.print(": "); 11508 pw.println(tr); 11509 if (dumpAll) { 11510 mRecentTasks.get(i).dump(pw, " "); 11511 } 11512 } 11513 } 11514 11515 if (!printedAnything) { 11516 pw.println(" (nothing)"); 11517 } 11518 } 11519 11520 void dumpProcessesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11521 int opti, boolean dumpAll, String dumpPackage) { 11522 boolean needSep = false; 11523 boolean printedAnything = false; 11524 int numPers = 0; 11525 11526 pw.println("ACTIVITY MANAGER RUNNING PROCESSES (dumpsys activity processes)"); 11527 11528 if (dumpAll) { 11529 final int NP = mProcessNames.getMap().size(); 11530 for (int ip=0; ip<NP; ip++) { 11531 SparseArray<ProcessRecord> procs = mProcessNames.getMap().valueAt(ip); 11532 final int NA = procs.size(); 11533 for (int ia=0; ia<NA; ia++) { 11534 ProcessRecord r = procs.valueAt(ia); 11535 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11536 continue; 11537 } 11538 if (!needSep) { 11539 pw.println(" All known processes:"); 11540 needSep = true; 11541 printedAnything = true; 11542 } 11543 pw.print(r.persistent ? " *PERS*" : " *APP*"); 11544 pw.print(" UID "); pw.print(procs.keyAt(ia)); 11545 pw.print(" "); pw.println(r); 11546 r.dump(pw, " "); 11547 if (r.persistent) { 11548 numPers++; 11549 } 11550 } 11551 } 11552 } 11553 11554 if (mIsolatedProcesses.size() > 0) { 11555 boolean printed = false; 11556 for (int i=0; i<mIsolatedProcesses.size(); i++) { 11557 ProcessRecord r = mIsolatedProcesses.valueAt(i); 11558 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11559 continue; 11560 } 11561 if (!printed) { 11562 if (needSep) { 11563 pw.println(); 11564 } 11565 pw.println(" Isolated process list (sorted by uid):"); 11566 printedAnything = true; 11567 printed = true; 11568 needSep = true; 11569 } 11570 pw.println(String.format("%sIsolated #%2d: %s", 11571 " ", i, r.toString())); 11572 } 11573 } 11574 11575 if (mLruProcesses.size() > 0) { 11576 if (needSep) { 11577 pw.println(); 11578 } 11579 pw.print(" Process LRU list (sorted by oom_adj, "); pw.print(mLruProcesses.size()); 11580 pw.print(" total, non-act at "); 11581 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 11582 pw.print(", non-svc at "); 11583 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 11584 pw.println("):"); 11585 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", false, dumpPackage); 11586 needSep = true; 11587 printedAnything = true; 11588 } 11589 11590 if (dumpAll || dumpPackage != null) { 11591 synchronized (mPidsSelfLocked) { 11592 boolean printed = false; 11593 for (int i=0; i<mPidsSelfLocked.size(); i++) { 11594 ProcessRecord r = mPidsSelfLocked.valueAt(i); 11595 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11596 continue; 11597 } 11598 if (!printed) { 11599 if (needSep) pw.println(); 11600 needSep = true; 11601 pw.println(" PID mappings:"); 11602 printed = true; 11603 printedAnything = true; 11604 } 11605 pw.print(" PID #"); pw.print(mPidsSelfLocked.keyAt(i)); 11606 pw.print(": "); pw.println(mPidsSelfLocked.valueAt(i)); 11607 } 11608 } 11609 } 11610 11611 if (mForegroundProcesses.size() > 0) { 11612 synchronized (mPidsSelfLocked) { 11613 boolean printed = false; 11614 for (int i=0; i<mForegroundProcesses.size(); i++) { 11615 ProcessRecord r = mPidsSelfLocked.get( 11616 mForegroundProcesses.valueAt(i).pid); 11617 if (dumpPackage != null && (r == null 11618 || !r.pkgList.containsKey(dumpPackage))) { 11619 continue; 11620 } 11621 if (!printed) { 11622 if (needSep) pw.println(); 11623 needSep = true; 11624 pw.println(" Foreground Processes:"); 11625 printed = true; 11626 printedAnything = true; 11627 } 11628 pw.print(" PID #"); pw.print(mForegroundProcesses.keyAt(i)); 11629 pw.print(": "); pw.println(mForegroundProcesses.valueAt(i)); 11630 } 11631 } 11632 } 11633 11634 if (mPersistentStartingProcesses.size() > 0) { 11635 if (needSep) pw.println(); 11636 needSep = true; 11637 printedAnything = true; 11638 pw.println(" Persisent processes that are starting:"); 11639 dumpProcessList(pw, this, mPersistentStartingProcesses, " ", 11640 "Starting Norm", "Restarting PERS", dumpPackage); 11641 } 11642 11643 if (mRemovedProcesses.size() > 0) { 11644 if (needSep) pw.println(); 11645 needSep = true; 11646 printedAnything = true; 11647 pw.println(" Processes that are being removed:"); 11648 dumpProcessList(pw, this, mRemovedProcesses, " ", 11649 "Removed Norm", "Removed PERS", dumpPackage); 11650 } 11651 11652 if (mProcessesOnHold.size() > 0) { 11653 if (needSep) pw.println(); 11654 needSep = true; 11655 printedAnything = true; 11656 pw.println(" Processes that are on old until the system is ready:"); 11657 dumpProcessList(pw, this, mProcessesOnHold, " ", 11658 "OnHold Norm", "OnHold PERS", dumpPackage); 11659 } 11660 11661 needSep = dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, dumpPackage); 11662 11663 if (mProcessCrashTimes.getMap().size() > 0) { 11664 boolean printed = false; 11665 long now = SystemClock.uptimeMillis(); 11666 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 11667 final int NP = pmap.size(); 11668 for (int ip=0; ip<NP; ip++) { 11669 String pname = pmap.keyAt(ip); 11670 SparseArray<Long> uids = pmap.valueAt(ip); 11671 final int N = uids.size(); 11672 for (int i=0; i<N; i++) { 11673 int puid = uids.keyAt(i); 11674 ProcessRecord r = mProcessNames.get(pname, puid); 11675 if (dumpPackage != null && (r == null 11676 || !r.pkgList.containsKey(dumpPackage))) { 11677 continue; 11678 } 11679 if (!printed) { 11680 if (needSep) pw.println(); 11681 needSep = true; 11682 pw.println(" Time since processes crashed:"); 11683 printed = true; 11684 printedAnything = true; 11685 } 11686 pw.print(" Process "); pw.print(pname); 11687 pw.print(" uid "); pw.print(puid); 11688 pw.print(": last crashed "); 11689 TimeUtils.formatDuration(now-uids.valueAt(i), pw); 11690 pw.println(" ago"); 11691 } 11692 } 11693 } 11694 11695 if (mBadProcesses.getMap().size() > 0) { 11696 boolean printed = false; 11697 final ArrayMap<String, SparseArray<BadProcessInfo>> pmap = mBadProcesses.getMap(); 11698 final int NP = pmap.size(); 11699 for (int ip=0; ip<NP; ip++) { 11700 String pname = pmap.keyAt(ip); 11701 SparseArray<BadProcessInfo> uids = pmap.valueAt(ip); 11702 final int N = uids.size(); 11703 for (int i=0; i<N; i++) { 11704 int puid = uids.keyAt(i); 11705 ProcessRecord r = mProcessNames.get(pname, puid); 11706 if (dumpPackage != null && (r == null 11707 || !r.pkgList.containsKey(dumpPackage))) { 11708 continue; 11709 } 11710 if (!printed) { 11711 if (needSep) pw.println(); 11712 needSep = true; 11713 pw.println(" Bad processes:"); 11714 printedAnything = true; 11715 } 11716 BadProcessInfo info = uids.valueAt(i); 11717 pw.print(" Bad process "); pw.print(pname); 11718 pw.print(" uid "); pw.print(puid); 11719 pw.print(": crashed at time "); pw.println(info.time); 11720 if (info.shortMsg != null) { 11721 pw.print(" Short msg: "); pw.println(info.shortMsg); 11722 } 11723 if (info.longMsg != null) { 11724 pw.print(" Long msg: "); pw.println(info.longMsg); 11725 } 11726 if (info.stack != null) { 11727 pw.println(" Stack:"); 11728 int lastPos = 0; 11729 for (int pos=0; pos<info.stack.length(); pos++) { 11730 if (info.stack.charAt(pos) == '\n') { 11731 pw.print(" "); 11732 pw.write(info.stack, lastPos, pos-lastPos); 11733 pw.println(); 11734 lastPos = pos+1; 11735 } 11736 } 11737 if (lastPos < info.stack.length()) { 11738 pw.print(" "); 11739 pw.write(info.stack, lastPos, info.stack.length()-lastPos); 11740 pw.println(); 11741 } 11742 } 11743 } 11744 } 11745 } 11746 11747 if (dumpPackage == null) { 11748 pw.println(); 11749 needSep = false; 11750 pw.println(" mStartedUsers:"); 11751 for (int i=0; i<mStartedUsers.size(); i++) { 11752 UserStartedState uss = mStartedUsers.valueAt(i); 11753 pw.print(" User #"); pw.print(uss.mHandle.getIdentifier()); 11754 pw.print(": "); uss.dump("", pw); 11755 } 11756 pw.print(" mStartedUserArray: ["); 11757 for (int i=0; i<mStartedUserArray.length; i++) { 11758 if (i > 0) pw.print(", "); 11759 pw.print(mStartedUserArray[i]); 11760 } 11761 pw.println("]"); 11762 pw.print(" mUserLru: ["); 11763 for (int i=0; i<mUserLru.size(); i++) { 11764 if (i > 0) pw.print(", "); 11765 pw.print(mUserLru.get(i)); 11766 } 11767 pw.println("]"); 11768 if (dumpAll) { 11769 pw.print(" mStartedUserArray: "); pw.println(Arrays.toString(mStartedUserArray)); 11770 } 11771 synchronized (mUserProfileGroupIdsSelfLocked) { 11772 if (mUserProfileGroupIdsSelfLocked.size() > 0) { 11773 pw.println(" mUserProfileGroupIds:"); 11774 for (int i=0; i<mUserProfileGroupIdsSelfLocked.size(); i++) { 11775 pw.print(" User #"); 11776 pw.print(mUserProfileGroupIdsSelfLocked.keyAt(i)); 11777 pw.print(" -> profile #"); 11778 pw.println(mUserProfileGroupIdsSelfLocked.valueAt(i)); 11779 } 11780 } 11781 } 11782 } 11783 if (mHomeProcess != null && (dumpPackage == null 11784 || mHomeProcess.pkgList.containsKey(dumpPackage))) { 11785 if (needSep) { 11786 pw.println(); 11787 needSep = false; 11788 } 11789 pw.println(" mHomeProcess: " + mHomeProcess); 11790 } 11791 if (mPreviousProcess != null && (dumpPackage == null 11792 || mPreviousProcess.pkgList.containsKey(dumpPackage))) { 11793 if (needSep) { 11794 pw.println(); 11795 needSep = false; 11796 } 11797 pw.println(" mPreviousProcess: " + mPreviousProcess); 11798 } 11799 if (dumpAll) { 11800 StringBuilder sb = new StringBuilder(128); 11801 sb.append(" mPreviousProcessVisibleTime: "); 11802 TimeUtils.formatDuration(mPreviousProcessVisibleTime, sb); 11803 pw.println(sb); 11804 } 11805 if (mHeavyWeightProcess != null && (dumpPackage == null 11806 || mHeavyWeightProcess.pkgList.containsKey(dumpPackage))) { 11807 if (needSep) { 11808 pw.println(); 11809 needSep = false; 11810 } 11811 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 11812 } 11813 if (dumpPackage == null) { 11814 pw.println(" mConfiguration: " + mConfiguration); 11815 } 11816 if (dumpAll) { 11817 pw.println(" mConfigWillChange: " + getFocusedStack().mConfigWillChange); 11818 if (mCompatModePackages.getPackages().size() > 0) { 11819 boolean printed = false; 11820 for (Map.Entry<String, Integer> entry 11821 : mCompatModePackages.getPackages().entrySet()) { 11822 String pkg = entry.getKey(); 11823 int mode = entry.getValue(); 11824 if (dumpPackage != null && !dumpPackage.equals(pkg)) { 11825 continue; 11826 } 11827 if (!printed) { 11828 pw.println(" mScreenCompatPackages:"); 11829 printed = true; 11830 } 11831 pw.print(" "); pw.print(pkg); pw.print(": "); 11832 pw.print(mode); pw.println(); 11833 } 11834 } 11835 } 11836 if (dumpPackage == null) { 11837 if (mSleeping || mWentToSleep || mLockScreenShown) { 11838 pw.println(" mSleeping=" + mSleeping + " mWentToSleep=" + mWentToSleep 11839 + " mLockScreenShown " + mLockScreenShown); 11840 } 11841 if (mShuttingDown || mRunningVoice) { 11842 pw.print(" mShuttingDown=" + mShuttingDown + " mRunningVoice=" + mRunningVoice); 11843 } 11844 } 11845 if (mDebugApp != null || mOrigDebugApp != null || mDebugTransient 11846 || mOrigWaitForDebugger) { 11847 if (dumpPackage == null || dumpPackage.equals(mDebugApp) 11848 || dumpPackage.equals(mOrigDebugApp)) { 11849 if (needSep) { 11850 pw.println(); 11851 needSep = false; 11852 } 11853 pw.println(" mDebugApp=" + mDebugApp + "/orig=" + mOrigDebugApp 11854 + " mDebugTransient=" + mDebugTransient 11855 + " mOrigWaitForDebugger=" + mOrigWaitForDebugger); 11856 } 11857 } 11858 if (mOpenGlTraceApp != null) { 11859 if (dumpPackage == null || dumpPackage.equals(mOpenGlTraceApp)) { 11860 if (needSep) { 11861 pw.println(); 11862 needSep = false; 11863 } 11864 pw.println(" mOpenGlTraceApp=" + mOpenGlTraceApp); 11865 } 11866 } 11867 if (mProfileApp != null || mProfileProc != null || mProfileFile != null 11868 || mProfileFd != null) { 11869 if (dumpPackage == null || dumpPackage.equals(mProfileApp)) { 11870 if (needSep) { 11871 pw.println(); 11872 needSep = false; 11873 } 11874 pw.println(" mProfileApp=" + mProfileApp + " mProfileProc=" + mProfileProc); 11875 pw.println(" mProfileFile=" + mProfileFile + " mProfileFd=" + mProfileFd); 11876 pw.println(" mProfileType=" + mProfileType + " mAutoStopProfiler=" 11877 + mAutoStopProfiler); 11878 } 11879 } 11880 if (dumpPackage == null) { 11881 if (mAlwaysFinishActivities || mController != null) { 11882 pw.println(" mAlwaysFinishActivities=" + mAlwaysFinishActivities 11883 + " mController=" + mController); 11884 } 11885 if (dumpAll) { 11886 pw.println(" Total persistent processes: " + numPers); 11887 pw.println(" mProcessesReady=" + mProcessesReady 11888 + " mSystemReady=" + mSystemReady); 11889 pw.println(" mBooting=" + mBooting 11890 + " mBooted=" + mBooted 11891 + " mFactoryTest=" + mFactoryTest); 11892 pw.print(" mLastPowerCheckRealtime="); 11893 TimeUtils.formatDuration(mLastPowerCheckRealtime, pw); 11894 pw.println(""); 11895 pw.print(" mLastPowerCheckUptime="); 11896 TimeUtils.formatDuration(mLastPowerCheckUptime, pw); 11897 pw.println(""); 11898 pw.println(" mGoingToSleep=" + mStackSupervisor.mGoingToSleep); 11899 pw.println(" mLaunchingActivity=" + mStackSupervisor.mLaunchingActivity); 11900 pw.println(" mAdjSeq=" + mAdjSeq + " mLruSeq=" + mLruSeq); 11901 pw.println(" mNumNonCachedProcs=" + mNumNonCachedProcs 11902 + " (" + mLruProcesses.size() + " total)" 11903 + " mNumCachedHiddenProcs=" + mNumCachedHiddenProcs 11904 + " mNumServiceProcs=" + mNumServiceProcs 11905 + " mNewNumServiceProcs=" + mNewNumServiceProcs); 11906 pw.println(" mAllowLowerMemLevel=" + mAllowLowerMemLevel 11907 + " mLastMemoryLevel" + mLastMemoryLevel 11908 + " mLastNumProcesses" + mLastNumProcesses); 11909 long now = SystemClock.uptimeMillis(); 11910 pw.print(" mLastIdleTime="); 11911 TimeUtils.formatDuration(now, mLastIdleTime, pw); 11912 pw.print(" mLowRamSinceLastIdle="); 11913 TimeUtils.formatDuration(getLowRamTimeSinceIdle(now), pw); 11914 pw.println(); 11915 } 11916 } 11917 11918 if (!printedAnything) { 11919 pw.println(" (nothing)"); 11920 } 11921 } 11922 11923 boolean dumpProcessesToGc(FileDescriptor fd, PrintWriter pw, String[] args, 11924 int opti, boolean needSep, boolean dumpAll, String dumpPackage) { 11925 if (mProcessesToGc.size() > 0) { 11926 boolean printed = false; 11927 long now = SystemClock.uptimeMillis(); 11928 for (int i=0; i<mProcessesToGc.size(); i++) { 11929 ProcessRecord proc = mProcessesToGc.get(i); 11930 if (dumpPackage != null && !dumpPackage.equals(proc.info.packageName)) { 11931 continue; 11932 } 11933 if (!printed) { 11934 if (needSep) pw.println(); 11935 needSep = true; 11936 pw.println(" Processes that are waiting to GC:"); 11937 printed = true; 11938 } 11939 pw.print(" Process "); pw.println(proc); 11940 pw.print(" lowMem="); pw.print(proc.reportLowMemory); 11941 pw.print(", last gced="); 11942 pw.print(now-proc.lastRequestedGc); 11943 pw.print(" ms ago, last lowMem="); 11944 pw.print(now-proc.lastLowMemory); 11945 pw.println(" ms ago"); 11946 11947 } 11948 } 11949 return needSep; 11950 } 11951 11952 void printOomLevel(PrintWriter pw, String name, int adj) { 11953 pw.print(" "); 11954 if (adj >= 0) { 11955 pw.print(' '); 11956 if (adj < 10) pw.print(' '); 11957 } else { 11958 if (adj > -10) pw.print(' '); 11959 } 11960 pw.print(adj); 11961 pw.print(": "); 11962 pw.print(name); 11963 pw.print(" ("); 11964 pw.print(mProcessList.getMemLevel(adj)/1024); 11965 pw.println(" kB)"); 11966 } 11967 11968 boolean dumpOomLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11969 int opti, boolean dumpAll) { 11970 boolean needSep = false; 11971 11972 if (mLruProcesses.size() > 0) { 11973 if (needSep) pw.println(); 11974 needSep = true; 11975 pw.println(" OOM levels:"); 11976 printOomLevel(pw, "SYSTEM_ADJ", ProcessList.SYSTEM_ADJ); 11977 printOomLevel(pw, "PERSISTENT_PROC_ADJ", ProcessList.PERSISTENT_PROC_ADJ); 11978 printOomLevel(pw, "FOREGROUND_APP_ADJ", ProcessList.FOREGROUND_APP_ADJ); 11979 printOomLevel(pw, "VISIBLE_APP_ADJ", ProcessList.VISIBLE_APP_ADJ); 11980 printOomLevel(pw, "PERCEPTIBLE_APP_ADJ", ProcessList.PERCEPTIBLE_APP_ADJ); 11981 printOomLevel(pw, "BACKUP_APP_ADJ", ProcessList.BACKUP_APP_ADJ); 11982 printOomLevel(pw, "HEAVY_WEIGHT_APP_ADJ", ProcessList.HEAVY_WEIGHT_APP_ADJ); 11983 printOomLevel(pw, "SERVICE_ADJ", ProcessList.SERVICE_ADJ); 11984 printOomLevel(pw, "HOME_APP_ADJ", ProcessList.HOME_APP_ADJ); 11985 printOomLevel(pw, "PREVIOUS_APP_ADJ", ProcessList.PREVIOUS_APP_ADJ); 11986 printOomLevel(pw, "SERVICE_B_ADJ", ProcessList.SERVICE_B_ADJ); 11987 printOomLevel(pw, "CACHED_APP_MIN_ADJ", ProcessList.CACHED_APP_MIN_ADJ); 11988 printOomLevel(pw, "CACHED_APP_MAX_ADJ", ProcessList.CACHED_APP_MAX_ADJ); 11989 11990 if (needSep) pw.println(); 11991 pw.print(" Process OOM control ("); pw.print(mLruProcesses.size()); 11992 pw.print(" total, non-act at "); 11993 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 11994 pw.print(", non-svc at "); 11995 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 11996 pw.println("):"); 11997 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", true, null); 11998 needSep = true; 11999 } 12000 12001 dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, null); 12002 12003 pw.println(); 12004 pw.println(" mHomeProcess: " + mHomeProcess); 12005 pw.println(" mPreviousProcess: " + mPreviousProcess); 12006 if (mHeavyWeightProcess != null) { 12007 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 12008 } 12009 12010 return true; 12011 } 12012 12013 /** 12014 * There are three ways to call this: 12015 * - no provider specified: dump all the providers 12016 * - a flattened component name that matched an existing provider was specified as the 12017 * first arg: dump that one provider 12018 * - the first arg isn't the flattened component name of an existing provider: 12019 * dump all providers whose component contains the first arg as a substring 12020 */ 12021 protected boolean dumpProvider(FileDescriptor fd, PrintWriter pw, String name, String[] args, 12022 int opti, boolean dumpAll) { 12023 return mProviderMap.dumpProvider(fd, pw, name, args, opti, dumpAll); 12024 } 12025 12026 static class ItemMatcher { 12027 ArrayList<ComponentName> components; 12028 ArrayList<String> strings; 12029 ArrayList<Integer> objects; 12030 boolean all; 12031 12032 ItemMatcher() { 12033 all = true; 12034 } 12035 12036 void build(String name) { 12037 ComponentName componentName = ComponentName.unflattenFromString(name); 12038 if (componentName != null) { 12039 if (components == null) { 12040 components = new ArrayList<ComponentName>(); 12041 } 12042 components.add(componentName); 12043 all = false; 12044 } else { 12045 int objectId = 0; 12046 // Not a '/' separated full component name; maybe an object ID? 12047 try { 12048 objectId = Integer.parseInt(name, 16); 12049 if (objects == null) { 12050 objects = new ArrayList<Integer>(); 12051 } 12052 objects.add(objectId); 12053 all = false; 12054 } catch (RuntimeException e) { 12055 // Not an integer; just do string match. 12056 if (strings == null) { 12057 strings = new ArrayList<String>(); 12058 } 12059 strings.add(name); 12060 all = false; 12061 } 12062 } 12063 } 12064 12065 int build(String[] args, int opti) { 12066 for (; opti<args.length; opti++) { 12067 String name = args[opti]; 12068 if ("--".equals(name)) { 12069 return opti+1; 12070 } 12071 build(name); 12072 } 12073 return opti; 12074 } 12075 12076 boolean match(Object object, ComponentName comp) { 12077 if (all) { 12078 return true; 12079 } 12080 if (components != null) { 12081 for (int i=0; i<components.size(); i++) { 12082 if (components.get(i).equals(comp)) { 12083 return true; 12084 } 12085 } 12086 } 12087 if (objects != null) { 12088 for (int i=0; i<objects.size(); i++) { 12089 if (System.identityHashCode(object) == objects.get(i)) { 12090 return true; 12091 } 12092 } 12093 } 12094 if (strings != null) { 12095 String flat = comp.flattenToString(); 12096 for (int i=0; i<strings.size(); i++) { 12097 if (flat.contains(strings.get(i))) { 12098 return true; 12099 } 12100 } 12101 } 12102 return false; 12103 } 12104 } 12105 12106 /** 12107 * There are three things that cmd can be: 12108 * - a flattened component name that matches an existing activity 12109 * - the cmd arg isn't the flattened component name of an existing activity: 12110 * dump all activity whose component contains the cmd as a substring 12111 * - A hex number of the ActivityRecord object instance. 12112 */ 12113 protected boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name, String[] args, 12114 int opti, boolean dumpAll) { 12115 ArrayList<ActivityRecord> activities; 12116 12117 synchronized (this) { 12118 activities = mStackSupervisor.getDumpActivitiesLocked(name); 12119 } 12120 12121 if (activities.size() <= 0) { 12122 return false; 12123 } 12124 12125 String[] newArgs = new String[args.length - opti]; 12126 System.arraycopy(args, opti, newArgs, 0, args.length - opti); 12127 12128 TaskRecord lastTask = null; 12129 boolean needSep = false; 12130 for (int i=activities.size()-1; i>=0; i--) { 12131 ActivityRecord r = activities.get(i); 12132 if (needSep) { 12133 pw.println(); 12134 } 12135 needSep = true; 12136 synchronized (this) { 12137 if (lastTask != r.task) { 12138 lastTask = r.task; 12139 pw.print("TASK "); pw.print(lastTask.affinity); 12140 pw.print(" id="); pw.println(lastTask.taskId); 12141 if (dumpAll) { 12142 lastTask.dump(pw, " "); 12143 } 12144 } 12145 } 12146 dumpActivity(" ", fd, pw, activities.get(i), newArgs, dumpAll); 12147 } 12148 return true; 12149 } 12150 12151 /** 12152 * Invokes IApplicationThread.dumpActivity() on the thread of the specified activity if 12153 * there is a thread associated with the activity. 12154 */ 12155 private void dumpActivity(String prefix, FileDescriptor fd, PrintWriter pw, 12156 final ActivityRecord r, String[] args, boolean dumpAll) { 12157 String innerPrefix = prefix + " "; 12158 synchronized (this) { 12159 pw.print(prefix); pw.print("ACTIVITY "); pw.print(r.shortComponentName); 12160 pw.print(" "); pw.print(Integer.toHexString(System.identityHashCode(r))); 12161 pw.print(" pid="); 12162 if (r.app != null) pw.println(r.app.pid); 12163 else pw.println("(not running)"); 12164 if (dumpAll) { 12165 r.dump(pw, innerPrefix); 12166 } 12167 } 12168 if (r.app != null && r.app.thread != null) { 12169 // flush anything that is already in the PrintWriter since the thread is going 12170 // to write to the file descriptor directly 12171 pw.flush(); 12172 try { 12173 TransferPipe tp = new TransferPipe(); 12174 try { 12175 r.app.thread.dumpActivity(tp.getWriteFd().getFileDescriptor(), 12176 r.appToken, innerPrefix, args); 12177 tp.go(fd); 12178 } finally { 12179 tp.kill(); 12180 } 12181 } catch (IOException e) { 12182 pw.println(innerPrefix + "Failure while dumping the activity: " + e); 12183 } catch (RemoteException e) { 12184 pw.println(innerPrefix + "Got a RemoteException while dumping the activity"); 12185 } 12186 } 12187 } 12188 12189 void dumpBroadcastsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12190 int opti, boolean dumpAll, String dumpPackage) { 12191 boolean needSep = false; 12192 boolean onlyHistory = false; 12193 boolean printedAnything = false; 12194 12195 if ("history".equals(dumpPackage)) { 12196 if (opti < args.length && "-s".equals(args[opti])) { 12197 dumpAll = false; 12198 } 12199 onlyHistory = true; 12200 dumpPackage = null; 12201 } 12202 12203 pw.println("ACTIVITY MANAGER BROADCAST STATE (dumpsys activity broadcasts)"); 12204 if (!onlyHistory && dumpAll) { 12205 if (mRegisteredReceivers.size() > 0) { 12206 boolean printed = false; 12207 Iterator it = mRegisteredReceivers.values().iterator(); 12208 while (it.hasNext()) { 12209 ReceiverList r = (ReceiverList)it.next(); 12210 if (dumpPackage != null && (r.app == null || 12211 !dumpPackage.equals(r.app.info.packageName))) { 12212 continue; 12213 } 12214 if (!printed) { 12215 pw.println(" Registered Receivers:"); 12216 needSep = true; 12217 printed = true; 12218 printedAnything = true; 12219 } 12220 pw.print(" * "); pw.println(r); 12221 r.dump(pw, " "); 12222 } 12223 } 12224 12225 if (mReceiverResolver.dump(pw, needSep ? 12226 "\n Receiver Resolver Table:" : " Receiver Resolver Table:", 12227 " ", dumpPackage, false)) { 12228 needSep = true; 12229 printedAnything = true; 12230 } 12231 } 12232 12233 for (BroadcastQueue q : mBroadcastQueues) { 12234 needSep = q.dumpLocked(fd, pw, args, opti, dumpAll, dumpPackage, needSep); 12235 printedAnything |= needSep; 12236 } 12237 12238 needSep = true; 12239 12240 if (!onlyHistory && mStickyBroadcasts != null && dumpPackage == null) { 12241 for (int user=0; user<mStickyBroadcasts.size(); user++) { 12242 if (needSep) { 12243 pw.println(); 12244 } 12245 needSep = true; 12246 printedAnything = true; 12247 pw.print(" Sticky broadcasts for user "); 12248 pw.print(mStickyBroadcasts.keyAt(user)); pw.println(":"); 12249 StringBuilder sb = new StringBuilder(128); 12250 for (Map.Entry<String, ArrayList<Intent>> ent 12251 : mStickyBroadcasts.valueAt(user).entrySet()) { 12252 pw.print(" * Sticky action "); pw.print(ent.getKey()); 12253 if (dumpAll) { 12254 pw.println(":"); 12255 ArrayList<Intent> intents = ent.getValue(); 12256 final int N = intents.size(); 12257 for (int i=0; i<N; i++) { 12258 sb.setLength(0); 12259 sb.append(" Intent: "); 12260 intents.get(i).toShortString(sb, false, true, false, false); 12261 pw.println(sb.toString()); 12262 Bundle bundle = intents.get(i).getExtras(); 12263 if (bundle != null) { 12264 pw.print(" "); 12265 pw.println(bundle.toString()); 12266 } 12267 } 12268 } else { 12269 pw.println(""); 12270 } 12271 } 12272 } 12273 } 12274 12275 if (!onlyHistory && dumpAll) { 12276 pw.println(); 12277 for (BroadcastQueue queue : mBroadcastQueues) { 12278 pw.println(" mBroadcastsScheduled [" + queue.mQueueName + "]=" 12279 + queue.mBroadcastsScheduled); 12280 } 12281 pw.println(" mHandler:"); 12282 mHandler.dump(new PrintWriterPrinter(pw), " "); 12283 needSep = true; 12284 printedAnything = true; 12285 } 12286 12287 if (!printedAnything) { 12288 pw.println(" (nothing)"); 12289 } 12290 } 12291 12292 void dumpProvidersLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12293 int opti, boolean dumpAll, String dumpPackage) { 12294 boolean needSep; 12295 boolean printedAnything = false; 12296 12297 ItemMatcher matcher = new ItemMatcher(); 12298 matcher.build(args, opti); 12299 12300 pw.println("ACTIVITY MANAGER CONTENT PROVIDERS (dumpsys activity providers)"); 12301 12302 needSep = mProviderMap.dumpProvidersLocked(pw, dumpAll, dumpPackage); 12303 printedAnything |= needSep; 12304 12305 if (mLaunchingProviders.size() > 0) { 12306 boolean printed = false; 12307 for (int i=mLaunchingProviders.size()-1; i>=0; i--) { 12308 ContentProviderRecord r = mLaunchingProviders.get(i); 12309 if (dumpPackage != null && !dumpPackage.equals(r.name.getPackageName())) { 12310 continue; 12311 } 12312 if (!printed) { 12313 if (needSep) pw.println(); 12314 needSep = true; 12315 pw.println(" Launching content providers:"); 12316 printed = true; 12317 printedAnything = true; 12318 } 12319 pw.print(" Launching #"); pw.print(i); pw.print(": "); 12320 pw.println(r); 12321 } 12322 } 12323 12324 if (mGrantedUriPermissions.size() > 0) { 12325 boolean printed = false; 12326 int dumpUid = -2; 12327 if (dumpPackage != null) { 12328 try { 12329 dumpUid = mContext.getPackageManager().getPackageUid(dumpPackage, 0); 12330 } catch (NameNotFoundException e) { 12331 dumpUid = -1; 12332 } 12333 } 12334 for (int i=0; i<mGrantedUriPermissions.size(); i++) { 12335 int uid = mGrantedUriPermissions.keyAt(i); 12336 if (dumpUid >= -1 && UserHandle.getAppId(uid) != dumpUid) { 12337 continue; 12338 } 12339 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 12340 if (!printed) { 12341 if (needSep) pw.println(); 12342 needSep = true; 12343 pw.println(" Granted Uri Permissions:"); 12344 printed = true; 12345 printedAnything = true; 12346 } 12347 pw.print(" * UID "); pw.print(uid); pw.println(" holds:"); 12348 for (UriPermission perm : perms.values()) { 12349 pw.print(" "); pw.println(perm); 12350 if (dumpAll) { 12351 perm.dump(pw, " "); 12352 } 12353 } 12354 } 12355 } 12356 12357 if (!printedAnything) { 12358 pw.println(" (nothing)"); 12359 } 12360 } 12361 12362 void dumpPendingIntentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12363 int opti, boolean dumpAll, String dumpPackage) { 12364 boolean printed = false; 12365 12366 pw.println("ACTIVITY MANAGER PENDING INTENTS (dumpsys activity intents)"); 12367 12368 if (mIntentSenderRecords.size() > 0) { 12369 Iterator<WeakReference<PendingIntentRecord>> it 12370 = mIntentSenderRecords.values().iterator(); 12371 while (it.hasNext()) { 12372 WeakReference<PendingIntentRecord> ref = it.next(); 12373 PendingIntentRecord rec = ref != null ? ref.get(): null; 12374 if (dumpPackage != null && (rec == null 12375 || !dumpPackage.equals(rec.key.packageName))) { 12376 continue; 12377 } 12378 printed = true; 12379 if (rec != null) { 12380 pw.print(" * "); pw.println(rec); 12381 if (dumpAll) { 12382 rec.dump(pw, " "); 12383 } 12384 } else { 12385 pw.print(" * "); pw.println(ref); 12386 } 12387 } 12388 } 12389 12390 if (!printed) { 12391 pw.println(" (nothing)"); 12392 } 12393 } 12394 12395 private static final int dumpProcessList(PrintWriter pw, 12396 ActivityManagerService service, List list, 12397 String prefix, String normalLabel, String persistentLabel, 12398 String dumpPackage) { 12399 int numPers = 0; 12400 final int N = list.size()-1; 12401 for (int i=N; i>=0; i--) { 12402 ProcessRecord r = (ProcessRecord)list.get(i); 12403 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 12404 continue; 12405 } 12406 pw.println(String.format("%s%s #%2d: %s", 12407 prefix, (r.persistent ? persistentLabel : normalLabel), 12408 i, r.toString())); 12409 if (r.persistent) { 12410 numPers++; 12411 } 12412 } 12413 return numPers; 12414 } 12415 12416 private static final boolean dumpProcessOomList(PrintWriter pw, 12417 ActivityManagerService service, List<ProcessRecord> origList, 12418 String prefix, String normalLabel, String persistentLabel, 12419 boolean inclDetails, String dumpPackage) { 12420 12421 ArrayList<Pair<ProcessRecord, Integer>> list 12422 = new ArrayList<Pair<ProcessRecord, Integer>>(origList.size()); 12423 for (int i=0; i<origList.size(); i++) { 12424 ProcessRecord r = origList.get(i); 12425 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 12426 continue; 12427 } 12428 list.add(new Pair<ProcessRecord, Integer>(origList.get(i), i)); 12429 } 12430 12431 if (list.size() <= 0) { 12432 return false; 12433 } 12434 12435 Comparator<Pair<ProcessRecord, Integer>> comparator 12436 = new Comparator<Pair<ProcessRecord, Integer>>() { 12437 @Override 12438 public int compare(Pair<ProcessRecord, Integer> object1, 12439 Pair<ProcessRecord, Integer> object2) { 12440 if (object1.first.setAdj != object2.first.setAdj) { 12441 return object1.first.setAdj > object2.first.setAdj ? -1 : 1; 12442 } 12443 if (object1.second.intValue() != object2.second.intValue()) { 12444 return object1.second.intValue() > object2.second.intValue() ? -1 : 1; 12445 } 12446 return 0; 12447 } 12448 }; 12449 12450 Collections.sort(list, comparator); 12451 12452 final long curRealtime = SystemClock.elapsedRealtime(); 12453 final long realtimeSince = curRealtime - service.mLastPowerCheckRealtime; 12454 final long curUptime = SystemClock.uptimeMillis(); 12455 final long uptimeSince = curUptime - service.mLastPowerCheckUptime; 12456 12457 for (int i=list.size()-1; i>=0; i--) { 12458 ProcessRecord r = list.get(i).first; 12459 String oomAdj = ProcessList.makeOomAdjString(r.setAdj); 12460 char schedGroup; 12461 switch (r.setSchedGroup) { 12462 case Process.THREAD_GROUP_BG_NONINTERACTIVE: 12463 schedGroup = 'B'; 12464 break; 12465 case Process.THREAD_GROUP_DEFAULT: 12466 schedGroup = 'F'; 12467 break; 12468 default: 12469 schedGroup = '?'; 12470 break; 12471 } 12472 char foreground; 12473 if (r.foregroundActivities) { 12474 foreground = 'A'; 12475 } else if (r.foregroundServices) { 12476 foreground = 'S'; 12477 } else { 12478 foreground = ' '; 12479 } 12480 String procState = ProcessList.makeProcStateString(r.curProcState); 12481 pw.print(prefix); 12482 pw.print(r.persistent ? persistentLabel : normalLabel); 12483 pw.print(" #"); 12484 int num = (origList.size()-1)-list.get(i).second; 12485 if (num < 10) pw.print(' '); 12486 pw.print(num); 12487 pw.print(": "); 12488 pw.print(oomAdj); 12489 pw.print(' '); 12490 pw.print(schedGroup); 12491 pw.print('/'); 12492 pw.print(foreground); 12493 pw.print('/'); 12494 pw.print(procState); 12495 pw.print(" trm:"); 12496 if (r.trimMemoryLevel < 10) pw.print(' '); 12497 pw.print(r.trimMemoryLevel); 12498 pw.print(' '); 12499 pw.print(r.toShortString()); 12500 pw.print(" ("); 12501 pw.print(r.adjType); 12502 pw.println(')'); 12503 if (r.adjSource != null || r.adjTarget != null) { 12504 pw.print(prefix); 12505 pw.print(" "); 12506 if (r.adjTarget instanceof ComponentName) { 12507 pw.print(((ComponentName)r.adjTarget).flattenToShortString()); 12508 } else if (r.adjTarget != null) { 12509 pw.print(r.adjTarget.toString()); 12510 } else { 12511 pw.print("{null}"); 12512 } 12513 pw.print("<="); 12514 if (r.adjSource instanceof ProcessRecord) { 12515 pw.print("Proc{"); 12516 pw.print(((ProcessRecord)r.adjSource).toShortString()); 12517 pw.println("}"); 12518 } else if (r.adjSource != null) { 12519 pw.println(r.adjSource.toString()); 12520 } else { 12521 pw.println("{null}"); 12522 } 12523 } 12524 if (inclDetails) { 12525 pw.print(prefix); 12526 pw.print(" "); 12527 pw.print("oom: max="); pw.print(r.maxAdj); 12528 pw.print(" curRaw="); pw.print(r.curRawAdj); 12529 pw.print(" setRaw="); pw.print(r.setRawAdj); 12530 pw.print(" cur="); pw.print(r.curAdj); 12531 pw.print(" set="); pw.println(r.setAdj); 12532 pw.print(prefix); 12533 pw.print(" "); 12534 pw.print("state: cur="); pw.print(ProcessList.makeProcStateString(r.curProcState)); 12535 pw.print(" set="); pw.print(ProcessList.makeProcStateString(r.setProcState)); 12536 pw.print(" lastPss="); pw.print(r.lastPss); 12537 pw.print(" lastCachedPss="); pw.println(r.lastCachedPss); 12538 pw.print(prefix); 12539 pw.print(" "); 12540 pw.print("cached="); pw.print(r.cached); 12541 pw.print(" empty="); pw.print(r.empty); 12542 pw.print(" hasAboveClient="); pw.println(r.hasAboveClient); 12543 12544 if (r.setProcState >= ActivityManager.PROCESS_STATE_SERVICE) { 12545 if (r.lastWakeTime != 0) { 12546 long wtime; 12547 BatteryStatsImpl stats = service.mBatteryStatsService.getActiveStatistics(); 12548 synchronized (stats) { 12549 wtime = stats.getProcessWakeTime(r.info.uid, 12550 r.pid, curRealtime); 12551 } 12552 long timeUsed = wtime - r.lastWakeTime; 12553 pw.print(prefix); 12554 pw.print(" "); 12555 pw.print("keep awake over "); 12556 TimeUtils.formatDuration(realtimeSince, pw); 12557 pw.print(" used "); 12558 TimeUtils.formatDuration(timeUsed, pw); 12559 pw.print(" ("); 12560 pw.print((timeUsed*100)/realtimeSince); 12561 pw.println("%)"); 12562 } 12563 if (r.lastCpuTime != 0) { 12564 long timeUsed = r.curCpuTime - r.lastCpuTime; 12565 pw.print(prefix); 12566 pw.print(" "); 12567 pw.print("run cpu over "); 12568 TimeUtils.formatDuration(uptimeSince, pw); 12569 pw.print(" used "); 12570 TimeUtils.formatDuration(timeUsed, pw); 12571 pw.print(" ("); 12572 pw.print((timeUsed*100)/uptimeSince); 12573 pw.println("%)"); 12574 } 12575 } 12576 } 12577 } 12578 return true; 12579 } 12580 12581 ArrayList<ProcessRecord> collectProcesses(PrintWriter pw, int start, String[] args) { 12582 ArrayList<ProcessRecord> procs; 12583 synchronized (this) { 12584 if (args != null && args.length > start 12585 && args[start].charAt(0) != '-') { 12586 procs = new ArrayList<ProcessRecord>(); 12587 int pid = -1; 12588 try { 12589 pid = Integer.parseInt(args[start]); 12590 } catch (NumberFormatException e) { 12591 } 12592 for (int i=mLruProcesses.size()-1; i>=0; i--) { 12593 ProcessRecord proc = mLruProcesses.get(i); 12594 if (proc.pid == pid) { 12595 procs.add(proc); 12596 } else if (proc.processName.equals(args[start])) { 12597 procs.add(proc); 12598 } 12599 } 12600 if (procs.size() <= 0) { 12601 return null; 12602 } 12603 } else { 12604 procs = new ArrayList<ProcessRecord>(mLruProcesses); 12605 } 12606 } 12607 return procs; 12608 } 12609 12610 final void dumpGraphicsHardwareUsage(FileDescriptor fd, 12611 PrintWriter pw, String[] args) { 12612 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 12613 if (procs == null) { 12614 pw.println("No process found for: " + args[0]); 12615 return; 12616 } 12617 12618 long uptime = SystemClock.uptimeMillis(); 12619 long realtime = SystemClock.elapsedRealtime(); 12620 pw.println("Applications Graphics Acceleration Info:"); 12621 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 12622 12623 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12624 ProcessRecord r = procs.get(i); 12625 if (r.thread != null) { 12626 pw.println("\n** Graphics info for pid " + r.pid + " [" + r.processName + "] **"); 12627 pw.flush(); 12628 try { 12629 TransferPipe tp = new TransferPipe(); 12630 try { 12631 r.thread.dumpGfxInfo(tp.getWriteFd().getFileDescriptor(), args); 12632 tp.go(fd); 12633 } finally { 12634 tp.kill(); 12635 } 12636 } catch (IOException e) { 12637 pw.println("Failure while dumping the app: " + r); 12638 pw.flush(); 12639 } catch (RemoteException e) { 12640 pw.println("Got a RemoteException while dumping the app " + r); 12641 pw.flush(); 12642 } 12643 } 12644 } 12645 } 12646 12647 final void dumpDbInfo(FileDescriptor fd, PrintWriter pw, String[] args) { 12648 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 12649 if (procs == null) { 12650 pw.println("No process found for: " + args[0]); 12651 return; 12652 } 12653 12654 pw.println("Applications Database Info:"); 12655 12656 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12657 ProcessRecord r = procs.get(i); 12658 if (r.thread != null) { 12659 pw.println("\n** Database info for pid " + r.pid + " [" + r.processName + "] **"); 12660 pw.flush(); 12661 try { 12662 TransferPipe tp = new TransferPipe(); 12663 try { 12664 r.thread.dumpDbInfo(tp.getWriteFd().getFileDescriptor(), args); 12665 tp.go(fd); 12666 } finally { 12667 tp.kill(); 12668 } 12669 } catch (IOException e) { 12670 pw.println("Failure while dumping the app: " + r); 12671 pw.flush(); 12672 } catch (RemoteException e) { 12673 pw.println("Got a RemoteException while dumping the app " + r); 12674 pw.flush(); 12675 } 12676 } 12677 } 12678 } 12679 12680 final static class MemItem { 12681 final boolean isProc; 12682 final String label; 12683 final String shortLabel; 12684 final long pss; 12685 final int id; 12686 final boolean hasActivities; 12687 ArrayList<MemItem> subitems; 12688 12689 public MemItem(String _label, String _shortLabel, long _pss, int _id, 12690 boolean _hasActivities) { 12691 isProc = true; 12692 label = _label; 12693 shortLabel = _shortLabel; 12694 pss = _pss; 12695 id = _id; 12696 hasActivities = _hasActivities; 12697 } 12698 12699 public MemItem(String _label, String _shortLabel, long _pss, int _id) { 12700 isProc = false; 12701 label = _label; 12702 shortLabel = _shortLabel; 12703 pss = _pss; 12704 id = _id; 12705 hasActivities = false; 12706 } 12707 } 12708 12709 static final void dumpMemItems(PrintWriter pw, String prefix, String tag, 12710 ArrayList<MemItem> items, boolean sort, boolean isCompact) { 12711 if (sort && !isCompact) { 12712 Collections.sort(items, new Comparator<MemItem>() { 12713 @Override 12714 public int compare(MemItem lhs, MemItem rhs) { 12715 if (lhs.pss < rhs.pss) { 12716 return 1; 12717 } else if (lhs.pss > rhs.pss) { 12718 return -1; 12719 } 12720 return 0; 12721 } 12722 }); 12723 } 12724 12725 for (int i=0; i<items.size(); i++) { 12726 MemItem mi = items.get(i); 12727 if (!isCompact) { 12728 pw.print(prefix); pw.printf("%7d kB: ", mi.pss); pw.println(mi.label); 12729 } else if (mi.isProc) { 12730 pw.print("proc,"); pw.print(tag); pw.print(","); pw.print(mi.shortLabel); 12731 pw.print(","); pw.print(mi.id); pw.print(","); pw.print(mi.pss); 12732 pw.println(mi.hasActivities ? ",a" : ",e"); 12733 } else { 12734 pw.print(tag); pw.print(","); pw.print(mi.shortLabel); pw.print(","); 12735 pw.println(mi.pss); 12736 } 12737 if (mi.subitems != null) { 12738 dumpMemItems(pw, prefix + " ", mi.shortLabel, mi.subitems, 12739 true, isCompact); 12740 } 12741 } 12742 } 12743 12744 // These are in KB. 12745 static final long[] DUMP_MEM_BUCKETS = new long[] { 12746 5*1024, 7*1024, 10*1024, 15*1024, 20*1024, 30*1024, 40*1024, 80*1024, 12747 120*1024, 160*1024, 200*1024, 12748 250*1024, 300*1024, 350*1024, 400*1024, 500*1024, 600*1024, 800*1024, 12749 1*1024*1024, 2*1024*1024, 5*1024*1024, 10*1024*1024, 20*1024*1024 12750 }; 12751 12752 static final void appendMemBucket(StringBuilder out, long memKB, String label, 12753 boolean stackLike) { 12754 int start = label.lastIndexOf('.'); 12755 if (start >= 0) start++; 12756 else start = 0; 12757 int end = label.length(); 12758 for (int i=0; i<DUMP_MEM_BUCKETS.length; i++) { 12759 if (DUMP_MEM_BUCKETS[i] >= memKB) { 12760 long bucket = DUMP_MEM_BUCKETS[i]/1024; 12761 out.append(bucket); 12762 out.append(stackLike ? "MB." : "MB "); 12763 out.append(label, start, end); 12764 return; 12765 } 12766 } 12767 out.append(memKB/1024); 12768 out.append(stackLike ? "MB." : "MB "); 12769 out.append(label, start, end); 12770 } 12771 12772 static final int[] DUMP_MEM_OOM_ADJ = new int[] { 12773 ProcessList.NATIVE_ADJ, 12774 ProcessList.SYSTEM_ADJ, ProcessList.PERSISTENT_PROC_ADJ, ProcessList.FOREGROUND_APP_ADJ, 12775 ProcessList.VISIBLE_APP_ADJ, ProcessList.PERCEPTIBLE_APP_ADJ, 12776 ProcessList.BACKUP_APP_ADJ, ProcessList.HEAVY_WEIGHT_APP_ADJ, 12777 ProcessList.SERVICE_ADJ, ProcessList.HOME_APP_ADJ, 12778 ProcessList.PREVIOUS_APP_ADJ, ProcessList.SERVICE_B_ADJ, ProcessList.CACHED_APP_MAX_ADJ 12779 }; 12780 static final String[] DUMP_MEM_OOM_LABEL = new String[] { 12781 "Native", 12782 "System", "Persistent", "Foreground", 12783 "Visible", "Perceptible", 12784 "Heavy Weight", "Backup", 12785 "A Services", "Home", 12786 "Previous", "B Services", "Cached" 12787 }; 12788 static final String[] DUMP_MEM_OOM_COMPACT_LABEL = new String[] { 12789 "native", 12790 "sys", "pers", "fore", 12791 "vis", "percept", 12792 "heavy", "backup", 12793 "servicea", "home", 12794 "prev", "serviceb", "cached" 12795 }; 12796 12797 private final void dumpApplicationMemoryUsageHeader(PrintWriter pw, long uptime, 12798 long realtime, boolean isCheckinRequest, boolean isCompact) { 12799 if (isCheckinRequest || isCompact) { 12800 // short checkin version 12801 pw.print("time,"); pw.print(uptime); pw.print(","); pw.println(realtime); 12802 } else { 12803 pw.println("Applications Memory Usage (kB):"); 12804 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 12805 } 12806 } 12807 12808 final void dumpApplicationMemoryUsage(FileDescriptor fd, 12809 PrintWriter pw, String prefix, String[] args, boolean brief, PrintWriter categoryPw) { 12810 boolean dumpDetails = false; 12811 boolean dumpFullDetails = false; 12812 boolean dumpDalvik = false; 12813 boolean oomOnly = false; 12814 boolean isCompact = false; 12815 boolean localOnly = false; 12816 12817 int opti = 0; 12818 while (opti < args.length) { 12819 String opt = args[opti]; 12820 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 12821 break; 12822 } 12823 opti++; 12824 if ("-a".equals(opt)) { 12825 dumpDetails = true; 12826 dumpFullDetails = true; 12827 dumpDalvik = true; 12828 } else if ("-d".equals(opt)) { 12829 dumpDalvik = true; 12830 } else if ("-c".equals(opt)) { 12831 isCompact = true; 12832 } else if ("--oom".equals(opt)) { 12833 oomOnly = true; 12834 } else if ("--local".equals(opt)) { 12835 localOnly = true; 12836 } else if ("-h".equals(opt)) { 12837 pw.println("meminfo dump options: [-a] [-d] [-c] [--oom] [process]"); 12838 pw.println(" -a: include all available information for each process."); 12839 pw.println(" -d: include dalvik details when dumping process details."); 12840 pw.println(" -c: dump in a compact machine-parseable representation."); 12841 pw.println(" --oom: only show processes organized by oom adj."); 12842 pw.println(" --local: only collect details locally, don't call process."); 12843 pw.println("If [process] is specified it can be the name or "); 12844 pw.println("pid of a specific process to dump."); 12845 return; 12846 } else { 12847 pw.println("Unknown argument: " + opt + "; use -h for help"); 12848 } 12849 } 12850 12851 final boolean isCheckinRequest = scanArgs(args, "--checkin"); 12852 long uptime = SystemClock.uptimeMillis(); 12853 long realtime = SystemClock.elapsedRealtime(); 12854 final long[] tmpLong = new long[1]; 12855 12856 ArrayList<ProcessRecord> procs = collectProcesses(pw, opti, args); 12857 if (procs == null) { 12858 // No Java processes. Maybe they want to print a native process. 12859 if (args != null && args.length > opti 12860 && args[opti].charAt(0) != '-') { 12861 ArrayList<ProcessCpuTracker.Stats> nativeProcs 12862 = new ArrayList<ProcessCpuTracker.Stats>(); 12863 updateCpuStatsNow(); 12864 int findPid = -1; 12865 try { 12866 findPid = Integer.parseInt(args[opti]); 12867 } catch (NumberFormatException e) { 12868 } 12869 synchronized (mProcessCpuThread) { 12870 final int N = mProcessCpuTracker.countStats(); 12871 for (int i=0; i<N; i++) { 12872 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 12873 if (st.pid == findPid || (st.baseName != null 12874 && st.baseName.equals(args[opti]))) { 12875 nativeProcs.add(st); 12876 } 12877 } 12878 } 12879 if (nativeProcs.size() > 0) { 12880 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, 12881 isCompact); 12882 Debug.MemoryInfo mi = null; 12883 for (int i = nativeProcs.size() - 1 ; i >= 0 ; i--) { 12884 final ProcessCpuTracker.Stats r = nativeProcs.get(i); 12885 final int pid = r.pid; 12886 if (!isCheckinRequest && dumpDetails) { 12887 pw.println("\n** MEMINFO in pid " + pid + " [" + r.baseName + "] **"); 12888 } 12889 if (mi == null) { 12890 mi = new Debug.MemoryInfo(); 12891 } 12892 if (dumpDetails || (!brief && !oomOnly)) { 12893 Debug.getMemoryInfo(pid, mi); 12894 } else { 12895 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 12896 mi.dalvikPrivateDirty = (int)tmpLong[0]; 12897 } 12898 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 12899 dumpDalvik, pid, r.baseName, 0, 0, 0, 0, 0, 0); 12900 if (isCheckinRequest) { 12901 pw.println(); 12902 } 12903 } 12904 return; 12905 } 12906 } 12907 pw.println("No process found for: " + args[opti]); 12908 return; 12909 } 12910 12911 if (!brief && !oomOnly && (procs.size() == 1 || isCheckinRequest)) { 12912 dumpDetails = true; 12913 } 12914 12915 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, isCompact); 12916 12917 String[] innerArgs = new String[args.length-opti]; 12918 System.arraycopy(args, opti, innerArgs, 0, args.length-opti); 12919 12920 ArrayList<MemItem> procMems = new ArrayList<MemItem>(); 12921 final SparseArray<MemItem> procMemsMap = new SparseArray<MemItem>(); 12922 long nativePss=0, dalvikPss=0, otherPss=0; 12923 long[] miscPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 12924 12925 long oomPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 12926 ArrayList<MemItem>[] oomProcs = (ArrayList<MemItem>[]) 12927 new ArrayList[DUMP_MEM_OOM_LABEL.length]; 12928 12929 long totalPss = 0; 12930 long cachedPss = 0; 12931 12932 Debug.MemoryInfo mi = null; 12933 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12934 final ProcessRecord r = procs.get(i); 12935 final IApplicationThread thread; 12936 final int pid; 12937 final int oomAdj; 12938 final boolean hasActivities; 12939 synchronized (this) { 12940 thread = r.thread; 12941 pid = r.pid; 12942 oomAdj = r.getSetAdjWithServices(); 12943 hasActivities = r.activities.size() > 0; 12944 } 12945 if (thread != null) { 12946 if (!isCheckinRequest && dumpDetails) { 12947 pw.println("\n** MEMINFO in pid " + pid + " [" + r.processName + "] **"); 12948 } 12949 if (mi == null) { 12950 mi = new Debug.MemoryInfo(); 12951 } 12952 if (dumpDetails || (!brief && !oomOnly)) { 12953 Debug.getMemoryInfo(pid, mi); 12954 } else { 12955 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 12956 mi.dalvikPrivateDirty = (int)tmpLong[0]; 12957 } 12958 if (dumpDetails) { 12959 if (localOnly) { 12960 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 12961 dumpDalvik, pid, r.processName, 0, 0, 0, 0, 0, 0); 12962 if (isCheckinRequest) { 12963 pw.println(); 12964 } 12965 } else { 12966 try { 12967 pw.flush(); 12968 thread.dumpMemInfo(fd, mi, isCheckinRequest, dumpFullDetails, 12969 dumpDalvik, innerArgs); 12970 } catch (RemoteException e) { 12971 if (!isCheckinRequest) { 12972 pw.println("Got RemoteException!"); 12973 pw.flush(); 12974 } 12975 } 12976 } 12977 } 12978 12979 final long myTotalPss = mi.getTotalPss(); 12980 final long myTotalUss = mi.getTotalUss(); 12981 12982 synchronized (this) { 12983 if (r.thread != null && oomAdj == r.getSetAdjWithServices()) { 12984 // Record this for posterity if the process has been stable. 12985 r.baseProcessTracker.addPss(myTotalPss, myTotalUss, true, r.pkgList); 12986 } 12987 } 12988 12989 if (!isCheckinRequest && mi != null) { 12990 totalPss += myTotalPss; 12991 MemItem pssItem = new MemItem(r.processName + " (pid " + pid + 12992 (hasActivities ? " / activities)" : ")"), 12993 r.processName, myTotalPss, pid, hasActivities); 12994 procMems.add(pssItem); 12995 procMemsMap.put(pid, pssItem); 12996 12997 nativePss += mi.nativePss; 12998 dalvikPss += mi.dalvikPss; 12999 otherPss += mi.otherPss; 13000 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 13001 long mem = mi.getOtherPss(j); 13002 miscPss[j] += mem; 13003 otherPss -= mem; 13004 } 13005 13006 if (oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 13007 cachedPss += myTotalPss; 13008 } 13009 13010 for (int oomIndex=0; oomIndex<oomPss.length; oomIndex++) { 13011 if (oomAdj <= DUMP_MEM_OOM_ADJ[oomIndex] 13012 || oomIndex == (oomPss.length-1)) { 13013 oomPss[oomIndex] += myTotalPss; 13014 if (oomProcs[oomIndex] == null) { 13015 oomProcs[oomIndex] = new ArrayList<MemItem>(); 13016 } 13017 oomProcs[oomIndex].add(pssItem); 13018 break; 13019 } 13020 } 13021 } 13022 } 13023 } 13024 13025 long nativeProcTotalPss = 0; 13026 13027 if (!isCheckinRequest && procs.size() > 1) { 13028 // If we are showing aggregations, also look for native processes to 13029 // include so that our aggregations are more accurate. 13030 updateCpuStatsNow(); 13031 synchronized (mProcessCpuThread) { 13032 final int N = mProcessCpuTracker.countStats(); 13033 for (int i=0; i<N; i++) { 13034 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 13035 if (st.vsize > 0 && procMemsMap.indexOfKey(st.pid) < 0) { 13036 if (mi == null) { 13037 mi = new Debug.MemoryInfo(); 13038 } 13039 if (!brief && !oomOnly) { 13040 Debug.getMemoryInfo(st.pid, mi); 13041 } else { 13042 mi.nativePss = (int)Debug.getPss(st.pid, tmpLong); 13043 mi.nativePrivateDirty = (int)tmpLong[0]; 13044 } 13045 13046 final long myTotalPss = mi.getTotalPss(); 13047 totalPss += myTotalPss; 13048 nativeProcTotalPss += myTotalPss; 13049 13050 MemItem pssItem = new MemItem(st.name + " (pid " + st.pid + ")", 13051 st.name, myTotalPss, st.pid, false); 13052 procMems.add(pssItem); 13053 13054 nativePss += mi.nativePss; 13055 dalvikPss += mi.dalvikPss; 13056 otherPss += mi.otherPss; 13057 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 13058 long mem = mi.getOtherPss(j); 13059 miscPss[j] += mem; 13060 otherPss -= mem; 13061 } 13062 oomPss[0] += myTotalPss; 13063 if (oomProcs[0] == null) { 13064 oomProcs[0] = new ArrayList<MemItem>(); 13065 } 13066 oomProcs[0].add(pssItem); 13067 } 13068 } 13069 } 13070 13071 ArrayList<MemItem> catMems = new ArrayList<MemItem>(); 13072 13073 catMems.add(new MemItem("Native", "Native", nativePss, -1)); 13074 catMems.add(new MemItem("Dalvik", "Dalvik", dalvikPss, -2)); 13075 catMems.add(new MemItem("Unknown", "Unknown", otherPss, -3)); 13076 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 13077 String label = Debug.MemoryInfo.getOtherLabel(j); 13078 catMems.add(new MemItem(label, label, miscPss[j], j)); 13079 } 13080 13081 ArrayList<MemItem> oomMems = new ArrayList<MemItem>(); 13082 for (int j=0; j<oomPss.length; j++) { 13083 if (oomPss[j] != 0) { 13084 String label = isCompact ? DUMP_MEM_OOM_COMPACT_LABEL[j] 13085 : DUMP_MEM_OOM_LABEL[j]; 13086 MemItem item = new MemItem(label, label, oomPss[j], 13087 DUMP_MEM_OOM_ADJ[j]); 13088 item.subitems = oomProcs[j]; 13089 oomMems.add(item); 13090 } 13091 } 13092 13093 if (!brief && !oomOnly && !isCompact) { 13094 pw.println(); 13095 pw.println("Total PSS by process:"); 13096 dumpMemItems(pw, " ", "proc", procMems, true, isCompact); 13097 pw.println(); 13098 } 13099 if (!isCompact) { 13100 pw.println("Total PSS by OOM adjustment:"); 13101 } 13102 dumpMemItems(pw, " ", "oom", oomMems, false, isCompact); 13103 if (!brief && !oomOnly) { 13104 PrintWriter out = categoryPw != null ? categoryPw : pw; 13105 if (!isCompact) { 13106 out.println(); 13107 out.println("Total PSS by category:"); 13108 } 13109 dumpMemItems(out, " ", "cat", catMems, true, isCompact); 13110 } 13111 if (!isCompact) { 13112 pw.println(); 13113 } 13114 MemInfoReader memInfo = new MemInfoReader(); 13115 memInfo.readMemInfo(); 13116 if (nativeProcTotalPss > 0) { 13117 synchronized (this) { 13118 mProcessStats.addSysMemUsageLocked(memInfo.getCachedSizeKb(), 13119 memInfo.getFreeSizeKb(), memInfo.getZramTotalSizeKb(), 13120 memInfo.getBuffersSizeKb()+memInfo.getShmemSizeKb()+memInfo.getSlabSizeKb(), 13121 nativeProcTotalPss); 13122 } 13123 } 13124 if (!brief) { 13125 if (!isCompact) { 13126 pw.print("Total RAM: "); pw.print(memInfo.getTotalSizeKb()); 13127 pw.print(" kB (status "); 13128 switch (mLastMemoryLevel) { 13129 case ProcessStats.ADJ_MEM_FACTOR_NORMAL: 13130 pw.println("normal)"); 13131 break; 13132 case ProcessStats.ADJ_MEM_FACTOR_MODERATE: 13133 pw.println("moderate)"); 13134 break; 13135 case ProcessStats.ADJ_MEM_FACTOR_LOW: 13136 pw.println("low)"); 13137 break; 13138 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 13139 pw.println("critical)"); 13140 break; 13141 default: 13142 pw.print(mLastMemoryLevel); 13143 pw.println(")"); 13144 break; 13145 } 13146 pw.print(" Free RAM: "); pw.print(cachedPss + memInfo.getCachedSizeKb() 13147 + memInfo.getFreeSizeKb()); pw.print(" kB ("); 13148 pw.print(cachedPss); pw.print(" cached pss + "); 13149 pw.print(memInfo.getCachedSizeKb()); pw.print(" cached + "); 13150 pw.print(memInfo.getFreeSizeKb()); pw.println(" free)"); 13151 } else { 13152 pw.print("ram,"); pw.print(memInfo.getTotalSizeKb()); pw.print(","); 13153 pw.print(cachedPss + memInfo.getCachedSizeKb() 13154 + memInfo.getFreeSizeKb()); pw.print(","); 13155 pw.println(totalPss - cachedPss); 13156 } 13157 } 13158 if (!isCompact) { 13159 pw.print(" Used RAM: "); pw.print(totalPss - cachedPss 13160 + memInfo.getBuffersSizeKb() + memInfo.getShmemSizeKb() 13161 + memInfo.getSlabSizeKb()); pw.print(" kB ("); 13162 pw.print(totalPss - cachedPss); pw.print(" used pss + "); 13163 pw.print(memInfo.getBuffersSizeKb()); pw.print(" buffers + "); 13164 pw.print(memInfo.getShmemSizeKb()); pw.print(" shmem + "); 13165 pw.print(memInfo.getSlabSizeKb()); pw.println(" slab)"); 13166 pw.print(" Lost RAM: "); pw.print(memInfo.getTotalSizeKb() 13167 - totalPss - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 13168 - memInfo.getBuffersSizeKb() - memInfo.getShmemSizeKb() 13169 - memInfo.getSlabSizeKb()); pw.println(" kB"); 13170 } 13171 if (!brief) { 13172 if (memInfo.getZramTotalSizeKb() != 0) { 13173 if (!isCompact) { 13174 pw.print(" ZRAM: "); pw.print(memInfo.getZramTotalSizeKb()); 13175 pw.print(" kB physical used for "); 13176 pw.print(memInfo.getSwapTotalSizeKb() 13177 - memInfo.getSwapFreeSizeKb()); 13178 pw.print(" kB in swap ("); 13179 pw.print(memInfo.getSwapTotalSizeKb()); 13180 pw.println(" kB total swap)"); 13181 } else { 13182 pw.print("zram,"); pw.print(memInfo.getZramTotalSizeKb()); pw.print(","); 13183 pw.print(memInfo.getSwapTotalSizeKb()); pw.print(","); 13184 pw.println(memInfo.getSwapFreeSizeKb()); 13185 } 13186 } 13187 final int[] SINGLE_LONG_FORMAT = new int[] { 13188 Process.PROC_SPACE_TERM|Process.PROC_OUT_LONG 13189 }; 13190 long[] longOut = new long[1]; 13191 Process.readProcFile("/sys/kernel/mm/ksm/pages_shared", 13192 SINGLE_LONG_FORMAT, null, longOut, null); 13193 long shared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13194 longOut[0] = 0; 13195 Process.readProcFile("/sys/kernel/mm/ksm/pages_sharing", 13196 SINGLE_LONG_FORMAT, null, longOut, null); 13197 long sharing = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13198 longOut[0] = 0; 13199 Process.readProcFile("/sys/kernel/mm/ksm/pages_unshared", 13200 SINGLE_LONG_FORMAT, null, longOut, null); 13201 long unshared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13202 longOut[0] = 0; 13203 Process.readProcFile("/sys/kernel/mm/ksm/pages_volatile", 13204 SINGLE_LONG_FORMAT, null, longOut, null); 13205 long voltile = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13206 if (!isCompact) { 13207 if (sharing != 0 || shared != 0 || unshared != 0 || voltile != 0) { 13208 pw.print(" KSM: "); pw.print(sharing); 13209 pw.print(" kB saved from shared "); 13210 pw.print(shared); pw.println(" kB"); 13211 pw.print(" "); pw.print(unshared); pw.print(" kB unshared; "); 13212 pw.print(voltile); pw.println(" kB volatile"); 13213 } 13214 pw.print(" Tuning: "); 13215 pw.print(ActivityManager.staticGetMemoryClass()); 13216 pw.print(" (large "); 13217 pw.print(ActivityManager.staticGetLargeMemoryClass()); 13218 pw.print("), oom "); 13219 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 13220 pw.print(" kB"); 13221 pw.print(", restore limit "); 13222 pw.print(mProcessList.getCachedRestoreThresholdKb()); 13223 pw.print(" kB"); 13224 if (ActivityManager.isLowRamDeviceStatic()) { 13225 pw.print(" (low-ram)"); 13226 } 13227 if (ActivityManager.isHighEndGfx()) { 13228 pw.print(" (high-end-gfx)"); 13229 } 13230 pw.println(); 13231 } else { 13232 pw.print("ksm,"); pw.print(sharing); pw.print(","); 13233 pw.print(shared); pw.print(","); pw.print(unshared); pw.print(","); 13234 pw.println(voltile); 13235 pw.print("tuning,"); 13236 pw.print(ActivityManager.staticGetMemoryClass()); 13237 pw.print(','); 13238 pw.print(ActivityManager.staticGetLargeMemoryClass()); 13239 pw.print(','); 13240 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 13241 if (ActivityManager.isLowRamDeviceStatic()) { 13242 pw.print(",low-ram"); 13243 } 13244 if (ActivityManager.isHighEndGfx()) { 13245 pw.print(",high-end-gfx"); 13246 } 13247 pw.println(); 13248 } 13249 } 13250 } 13251 } 13252 13253 /** 13254 * Searches array of arguments for the specified string 13255 * @param args array of argument strings 13256 * @param value value to search for 13257 * @return true if the value is contained in the array 13258 */ 13259 private static boolean scanArgs(String[] args, String value) { 13260 if (args != null) { 13261 for (String arg : args) { 13262 if (value.equals(arg)) { 13263 return true; 13264 } 13265 } 13266 } 13267 return false; 13268 } 13269 13270 private final boolean removeDyingProviderLocked(ProcessRecord proc, 13271 ContentProviderRecord cpr, boolean always) { 13272 final boolean inLaunching = mLaunchingProviders.contains(cpr); 13273 13274 if (!inLaunching || always) { 13275 synchronized (cpr) { 13276 cpr.launchingApp = null; 13277 cpr.notifyAll(); 13278 } 13279 mProviderMap.removeProviderByClass(cpr.name, UserHandle.getUserId(cpr.uid)); 13280 String names[] = cpr.info.authority.split(";"); 13281 for (int j = 0; j < names.length; j++) { 13282 mProviderMap.removeProviderByName(names[j], UserHandle.getUserId(cpr.uid)); 13283 } 13284 } 13285 13286 for (int i=0; i<cpr.connections.size(); i++) { 13287 ContentProviderConnection conn = cpr.connections.get(i); 13288 if (conn.waiting) { 13289 // If this connection is waiting for the provider, then we don't 13290 // need to mess with its process unless we are always removing 13291 // or for some reason the provider is not currently launching. 13292 if (inLaunching && !always) { 13293 continue; 13294 } 13295 } 13296 ProcessRecord capp = conn.client; 13297 conn.dead = true; 13298 if (conn.stableCount > 0) { 13299 if (!capp.persistent && capp.thread != null 13300 && capp.pid != 0 13301 && capp.pid != MY_PID) { 13302 killUnneededProcessLocked(capp, "depends on provider " 13303 + cpr.name.flattenToShortString() 13304 + " in dying proc " + (proc != null ? proc.processName : "??")); 13305 } 13306 } else if (capp.thread != null && conn.provider.provider != null) { 13307 try { 13308 capp.thread.unstableProviderDied(conn.provider.provider.asBinder()); 13309 } catch (RemoteException e) { 13310 } 13311 // In the protocol here, we don't expect the client to correctly 13312 // clean up this connection, we'll just remove it. 13313 cpr.connections.remove(i); 13314 conn.client.conProviders.remove(conn); 13315 } 13316 } 13317 13318 if (inLaunching && always) { 13319 mLaunchingProviders.remove(cpr); 13320 } 13321 return inLaunching; 13322 } 13323 13324 /** 13325 * Main code for cleaning up a process when it has gone away. This is 13326 * called both as a result of the process dying, or directly when stopping 13327 * a process when running in single process mode. 13328 */ 13329 private final void cleanUpApplicationRecordLocked(ProcessRecord app, 13330 boolean restarting, boolean allowRestart, int index) { 13331 if (index >= 0) { 13332 removeLruProcessLocked(app); 13333 ProcessList.remove(app.pid); 13334 } 13335 13336 mProcessesToGc.remove(app); 13337 mPendingPssProcesses.remove(app); 13338 13339 // Dismiss any open dialogs. 13340 if (app.crashDialog != null && !app.forceCrashReport) { 13341 app.crashDialog.dismiss(); 13342 app.crashDialog = null; 13343 } 13344 if (app.anrDialog != null) { 13345 app.anrDialog.dismiss(); 13346 app.anrDialog = null; 13347 } 13348 if (app.waitDialog != null) { 13349 app.waitDialog.dismiss(); 13350 app.waitDialog = null; 13351 } 13352 13353 app.crashing = false; 13354 app.notResponding = false; 13355 13356 app.resetPackageList(mProcessStats); 13357 app.unlinkDeathRecipient(); 13358 app.makeInactive(mProcessStats); 13359 app.waitingToKill = null; 13360 app.forcingToForeground = null; 13361 updateProcessForegroundLocked(app, false, false); 13362 app.foregroundActivities = false; 13363 app.hasShownUi = false; 13364 app.treatLikeActivity = false; 13365 app.hasAboveClient = false; 13366 app.hasClientActivities = false; 13367 13368 mServices.killServicesLocked(app, allowRestart); 13369 13370 boolean restart = false; 13371 13372 // Remove published content providers. 13373 for (int i=app.pubProviders.size()-1; i>=0; i--) { 13374 ContentProviderRecord cpr = app.pubProviders.valueAt(i); 13375 final boolean always = app.bad || !allowRestart; 13376 if (removeDyingProviderLocked(app, cpr, always) || always) { 13377 // We left the provider in the launching list, need to 13378 // restart it. 13379 restart = true; 13380 } 13381 13382 cpr.provider = null; 13383 cpr.proc = null; 13384 } 13385 app.pubProviders.clear(); 13386 13387 // Take care of any launching providers waiting for this process. 13388 if (checkAppInLaunchingProvidersLocked(app, false)) { 13389 restart = true; 13390 } 13391 13392 // Unregister from connected content providers. 13393 if (!app.conProviders.isEmpty()) { 13394 for (int i=0; i<app.conProviders.size(); i++) { 13395 ContentProviderConnection conn = app.conProviders.get(i); 13396 conn.provider.connections.remove(conn); 13397 } 13398 app.conProviders.clear(); 13399 } 13400 13401 // At this point there may be remaining entries in mLaunchingProviders 13402 // where we were the only one waiting, so they are no longer of use. 13403 // Look for these and clean up if found. 13404 // XXX Commented out for now. Trying to figure out a way to reproduce 13405 // the actual situation to identify what is actually going on. 13406 if (false) { 13407 for (int i=0; i<mLaunchingProviders.size(); i++) { 13408 ContentProviderRecord cpr = (ContentProviderRecord) 13409 mLaunchingProviders.get(i); 13410 if (cpr.connections.size() <= 0 && !cpr.hasExternalProcessHandles()) { 13411 synchronized (cpr) { 13412 cpr.launchingApp = null; 13413 cpr.notifyAll(); 13414 } 13415 } 13416 } 13417 } 13418 13419 skipCurrentReceiverLocked(app); 13420 13421 // Unregister any receivers. 13422 for (int i=app.receivers.size()-1; i>=0; i--) { 13423 removeReceiverLocked(app.receivers.valueAt(i)); 13424 } 13425 app.receivers.clear(); 13426 13427 // If the app is undergoing backup, tell the backup manager about it 13428 if (mBackupTarget != null && app.pid == mBackupTarget.app.pid) { 13429 if (DEBUG_BACKUP || DEBUG_CLEANUP) Slog.d(TAG, "App " 13430 + mBackupTarget.appInfo + " died during backup"); 13431 try { 13432 IBackupManager bm = IBackupManager.Stub.asInterface( 13433 ServiceManager.getService(Context.BACKUP_SERVICE)); 13434 bm.agentDisconnected(app.info.packageName); 13435 } catch (RemoteException e) { 13436 // can't happen; backup manager is local 13437 } 13438 } 13439 13440 for (int i = mPendingProcessChanges.size()-1; i>=0; i--) { 13441 ProcessChangeItem item = mPendingProcessChanges.get(i); 13442 if (item.pid == app.pid) { 13443 mPendingProcessChanges.remove(i); 13444 mAvailProcessChanges.add(item); 13445 } 13446 } 13447 mHandler.obtainMessage(DISPATCH_PROCESS_DIED, app.pid, app.info.uid, null).sendToTarget(); 13448 13449 // If the caller is restarting this app, then leave it in its 13450 // current lists and let the caller take care of it. 13451 if (restarting) { 13452 return; 13453 } 13454 13455 if (!app.persistent || app.isolated) { 13456 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, 13457 "Removing non-persistent process during cleanup: " + app); 13458 mProcessNames.remove(app.processName, app.uid); 13459 mIsolatedProcesses.remove(app.uid); 13460 if (mHeavyWeightProcess == app) { 13461 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 13462 mHeavyWeightProcess.userId, 0)); 13463 mHeavyWeightProcess = null; 13464 } 13465 } else if (!app.removed) { 13466 // This app is persistent, so we need to keep its record around. 13467 // If it is not already on the pending app list, add it there 13468 // and start a new process for it. 13469 if (mPersistentStartingProcesses.indexOf(app) < 0) { 13470 mPersistentStartingProcesses.add(app); 13471 restart = true; 13472 } 13473 } 13474 if ((DEBUG_PROCESSES || DEBUG_CLEANUP) && mProcessesOnHold.contains(app)) Slog.v(TAG, 13475 "Clean-up removing on hold: " + app); 13476 mProcessesOnHold.remove(app); 13477 13478 if (app == mHomeProcess) { 13479 mHomeProcess = null; 13480 } 13481 if (app == mPreviousProcess) { 13482 mPreviousProcess = null; 13483 } 13484 13485 if (restart && !app.isolated) { 13486 // We have components that still need to be running in the 13487 // process, so re-launch it. 13488 mProcessNames.put(app.processName, app.uid, app); 13489 startProcessLocked(app, "restart", app.processName, null /* ABI override */); 13490 } else if (app.pid > 0 && app.pid != MY_PID) { 13491 // Goodbye! 13492 boolean removed; 13493 synchronized (mPidsSelfLocked) { 13494 mPidsSelfLocked.remove(app.pid); 13495 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 13496 } 13497 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 13498 if (app.isolated) { 13499 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 13500 } 13501 app.setPid(0); 13502 } 13503 } 13504 13505 boolean checkAppInLaunchingProvidersLocked(ProcessRecord app, boolean alwaysBad) { 13506 // Look through the content providers we are waiting to have launched, 13507 // and if any run in this process then either schedule a restart of 13508 // the process or kill the client waiting for it if this process has 13509 // gone bad. 13510 int NL = mLaunchingProviders.size(); 13511 boolean restart = false; 13512 for (int i=0; i<NL; i++) { 13513 ContentProviderRecord cpr = mLaunchingProviders.get(i); 13514 if (cpr.launchingApp == app) { 13515 if (!alwaysBad && !app.bad) { 13516 restart = true; 13517 } else { 13518 removeDyingProviderLocked(app, cpr, true); 13519 // cpr should have been removed from mLaunchingProviders 13520 NL = mLaunchingProviders.size(); 13521 i--; 13522 } 13523 } 13524 } 13525 return restart; 13526 } 13527 13528 // ========================================================= 13529 // SERVICES 13530 // ========================================================= 13531 13532 @Override 13533 public List<ActivityManager.RunningServiceInfo> getServices(int maxNum, 13534 int flags) { 13535 enforceNotIsolatedCaller("getServices"); 13536 synchronized (this) { 13537 return mServices.getRunningServiceInfoLocked(maxNum, flags); 13538 } 13539 } 13540 13541 @Override 13542 public PendingIntent getRunningServiceControlPanel(ComponentName name) { 13543 enforceNotIsolatedCaller("getRunningServiceControlPanel"); 13544 synchronized (this) { 13545 return mServices.getRunningServiceControlPanelLocked(name); 13546 } 13547 } 13548 13549 @Override 13550 public ComponentName startService(IApplicationThread caller, Intent service, 13551 String resolvedType, int userId) { 13552 enforceNotIsolatedCaller("startService"); 13553 // Refuse possible leaked file descriptors 13554 if (service != null && service.hasFileDescriptors() == true) { 13555 throw new IllegalArgumentException("File descriptors passed in Intent"); 13556 } 13557 13558 if (DEBUG_SERVICE) 13559 Slog.v(TAG, "startService: " + service + " type=" + resolvedType); 13560 synchronized(this) { 13561 final int callingPid = Binder.getCallingPid(); 13562 final int callingUid = Binder.getCallingUid(); 13563 final long origId = Binder.clearCallingIdentity(); 13564 ComponentName res = mServices.startServiceLocked(caller, service, 13565 resolvedType, callingPid, callingUid, userId); 13566 Binder.restoreCallingIdentity(origId); 13567 return res; 13568 } 13569 } 13570 13571 ComponentName startServiceInPackage(int uid, 13572 Intent service, String resolvedType, int userId) { 13573 synchronized(this) { 13574 if (DEBUG_SERVICE) 13575 Slog.v(TAG, "startServiceInPackage: " + service + " type=" + resolvedType); 13576 final long origId = Binder.clearCallingIdentity(); 13577 ComponentName res = mServices.startServiceLocked(null, service, 13578 resolvedType, -1, uid, userId); 13579 Binder.restoreCallingIdentity(origId); 13580 return res; 13581 } 13582 } 13583 13584 @Override 13585 public int stopService(IApplicationThread caller, Intent service, 13586 String resolvedType, int userId) { 13587 enforceNotIsolatedCaller("stopService"); 13588 // Refuse possible leaked file descriptors 13589 if (service != null && service.hasFileDescriptors() == true) { 13590 throw new IllegalArgumentException("File descriptors passed in Intent"); 13591 } 13592 13593 synchronized(this) { 13594 return mServices.stopServiceLocked(caller, service, resolvedType, userId); 13595 } 13596 } 13597 13598 @Override 13599 public IBinder peekService(Intent service, String resolvedType) { 13600 enforceNotIsolatedCaller("peekService"); 13601 // Refuse possible leaked file descriptors 13602 if (service != null && service.hasFileDescriptors() == true) { 13603 throw new IllegalArgumentException("File descriptors passed in Intent"); 13604 } 13605 synchronized(this) { 13606 return mServices.peekServiceLocked(service, resolvedType); 13607 } 13608 } 13609 13610 @Override 13611 public boolean stopServiceToken(ComponentName className, IBinder token, 13612 int startId) { 13613 synchronized(this) { 13614 return mServices.stopServiceTokenLocked(className, token, startId); 13615 } 13616 } 13617 13618 @Override 13619 public void setServiceForeground(ComponentName className, IBinder token, 13620 int id, Notification notification, boolean removeNotification) { 13621 synchronized(this) { 13622 mServices.setServiceForegroundLocked(className, token, id, notification, 13623 removeNotification); 13624 } 13625 } 13626 13627 @Override 13628 public int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 13629 boolean requireFull, String name, String callerPackage) { 13630 return handleIncomingUser(callingPid, callingUid, userId, allowAll, 13631 requireFull ? ALLOW_FULL_ONLY : ALLOW_NON_FULL, name, callerPackage); 13632 } 13633 13634 int unsafeConvertIncomingUser(int userId) { 13635 return (userId == UserHandle.USER_CURRENT || userId == UserHandle.USER_CURRENT_OR_SELF) 13636 ? mCurrentUserId : userId; 13637 } 13638 13639 int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 13640 int allowMode, String name, String callerPackage) { 13641 final int callingUserId = UserHandle.getUserId(callingUid); 13642 if (callingUserId == userId) { 13643 return userId; 13644 } 13645 13646 // Note that we may be accessing mCurrentUserId outside of a lock... 13647 // shouldn't be a big deal, if this is being called outside 13648 // of a locked context there is intrinsically a race with 13649 // the value the caller will receive and someone else changing it. 13650 // We assume that USER_CURRENT_OR_SELF will use the current user; later 13651 // we will switch to the calling user if access to the current user fails. 13652 int targetUserId = unsafeConvertIncomingUser(userId); 13653 13654 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 13655 final boolean allow; 13656 if (checkComponentPermission(INTERACT_ACROSS_USERS_FULL, callingPid, 13657 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED) { 13658 // If the caller has this permission, they always pass go. And collect $200. 13659 allow = true; 13660 } else if (allowMode == ALLOW_FULL_ONLY) { 13661 // We require full access, sucks to be you. 13662 allow = false; 13663 } else if (checkComponentPermission(INTERACT_ACROSS_USERS, callingPid, 13664 callingUid, -1, true) != PackageManager.PERMISSION_GRANTED) { 13665 // If the caller does not have either permission, they are always doomed. 13666 allow = false; 13667 } else if (allowMode == ALLOW_NON_FULL) { 13668 // We are blanket allowing non-full access, you lucky caller! 13669 allow = true; 13670 } else if (allowMode == ALLOW_NON_FULL_IN_PROFILE) { 13671 // We may or may not allow this depending on whether the two users are 13672 // in the same profile. 13673 synchronized (mUserProfileGroupIdsSelfLocked) { 13674 int callingProfile = mUserProfileGroupIdsSelfLocked.get(callingUserId, 13675 UserInfo.NO_PROFILE_GROUP_ID); 13676 int targetProfile = mUserProfileGroupIdsSelfLocked.get(targetUserId, 13677 UserInfo.NO_PROFILE_GROUP_ID); 13678 allow = callingProfile != UserInfo.NO_PROFILE_GROUP_ID 13679 && callingProfile == targetProfile; 13680 } 13681 } else { 13682 throw new IllegalArgumentException("Unknown mode: " + allowMode); 13683 } 13684 if (!allow) { 13685 if (userId == UserHandle.USER_CURRENT_OR_SELF) { 13686 // In this case, they would like to just execute as their 13687 // owner user instead of failing. 13688 targetUserId = callingUserId; 13689 } else { 13690 StringBuilder builder = new StringBuilder(128); 13691 builder.append("Permission Denial: "); 13692 builder.append(name); 13693 if (callerPackage != null) { 13694 builder.append(" from "); 13695 builder.append(callerPackage); 13696 } 13697 builder.append(" asks to run as user "); 13698 builder.append(userId); 13699 builder.append(" but is calling from user "); 13700 builder.append(UserHandle.getUserId(callingUid)); 13701 builder.append("; this requires "); 13702 builder.append(INTERACT_ACROSS_USERS_FULL); 13703 if (allowMode != ALLOW_FULL_ONLY) { 13704 builder.append(" or "); 13705 builder.append(INTERACT_ACROSS_USERS); 13706 } 13707 String msg = builder.toString(); 13708 Slog.w(TAG, msg); 13709 throw new SecurityException(msg); 13710 } 13711 } 13712 } 13713 if (!allowAll && targetUserId < 0) { 13714 throw new IllegalArgumentException( 13715 "Call does not support special user #" + targetUserId); 13716 } 13717 return targetUserId; 13718 } 13719 13720 boolean isSingleton(String componentProcessName, ApplicationInfo aInfo, 13721 String className, int flags) { 13722 boolean result = false; 13723 // For apps that don't have pre-defined UIDs, check for permission 13724 if (UserHandle.getAppId(aInfo.uid) >= Process.FIRST_APPLICATION_UID) { 13725 if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 13726 if (ActivityManager.checkUidPermission( 13727 INTERACT_ACROSS_USERS, 13728 aInfo.uid) != PackageManager.PERMISSION_GRANTED) { 13729 ComponentName comp = new ComponentName(aInfo.packageName, className); 13730 String msg = "Permission Denial: Component " + comp.flattenToShortString() 13731 + " requests FLAG_SINGLE_USER, but app does not hold " 13732 + INTERACT_ACROSS_USERS; 13733 Slog.w(TAG, msg); 13734 throw new SecurityException(msg); 13735 } 13736 // Permission passed 13737 result = true; 13738 } 13739 } else if ("system".equals(componentProcessName)) { 13740 result = true; 13741 } else { 13742 // App with pre-defined UID, check if it's a persistent app 13743 result = (aInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0; 13744 } 13745 if (DEBUG_MU) { 13746 Slog.v(TAG, "isSingleton(" + componentProcessName + ", " + aInfo 13747 + ", " + className + ", 0x" + Integer.toHexString(flags) + ") = " + result); 13748 } 13749 return result; 13750 } 13751 13752 /** 13753 * Checks to see if the caller is in the same app as the singleton 13754 * component, or the component is in a special app. It allows special apps 13755 * to export singleton components but prevents exporting singleton 13756 * components for regular apps. 13757 */ 13758 boolean isValidSingletonCall(int callingUid, int componentUid) { 13759 int componentAppId = UserHandle.getAppId(componentUid); 13760 return UserHandle.isSameApp(callingUid, componentUid) 13761 || componentAppId == Process.SYSTEM_UID 13762 || componentAppId == Process.PHONE_UID 13763 || ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, componentUid) 13764 == PackageManager.PERMISSION_GRANTED; 13765 } 13766 13767 public int bindService(IApplicationThread caller, IBinder token, 13768 Intent service, String resolvedType, 13769 IServiceConnection connection, int flags, int userId) { 13770 enforceNotIsolatedCaller("bindService"); 13771 // Refuse possible leaked file descriptors 13772 if (service != null && service.hasFileDescriptors() == true) { 13773 throw new IllegalArgumentException("File descriptors passed in Intent"); 13774 } 13775 13776 synchronized(this) { 13777 return mServices.bindServiceLocked(caller, token, service, resolvedType, 13778 connection, flags, userId); 13779 } 13780 } 13781 13782 public boolean unbindService(IServiceConnection connection) { 13783 synchronized (this) { 13784 return mServices.unbindServiceLocked(connection); 13785 } 13786 } 13787 13788 public void publishService(IBinder token, Intent intent, IBinder service) { 13789 // Refuse possible leaked file descriptors 13790 if (intent != null && intent.hasFileDescriptors() == true) { 13791 throw new IllegalArgumentException("File descriptors passed in Intent"); 13792 } 13793 13794 synchronized(this) { 13795 if (!(token instanceof ServiceRecord)) { 13796 throw new IllegalArgumentException("Invalid service token"); 13797 } 13798 mServices.publishServiceLocked((ServiceRecord)token, intent, service); 13799 } 13800 } 13801 13802 public void unbindFinished(IBinder token, Intent intent, boolean doRebind) { 13803 // Refuse possible leaked file descriptors 13804 if (intent != null && intent.hasFileDescriptors() == true) { 13805 throw new IllegalArgumentException("File descriptors passed in Intent"); 13806 } 13807 13808 synchronized(this) { 13809 mServices.unbindFinishedLocked((ServiceRecord)token, intent, doRebind); 13810 } 13811 } 13812 13813 public void serviceDoneExecuting(IBinder token, int type, int startId, int res) { 13814 synchronized(this) { 13815 if (!(token instanceof ServiceRecord)) { 13816 throw new IllegalArgumentException("Invalid service token"); 13817 } 13818 mServices.serviceDoneExecutingLocked((ServiceRecord)token, type, startId, res); 13819 } 13820 } 13821 13822 // ========================================================= 13823 // BACKUP AND RESTORE 13824 // ========================================================= 13825 13826 // Cause the target app to be launched if necessary and its backup agent 13827 // instantiated. The backup agent will invoke backupAgentCreated() on the 13828 // activity manager to announce its creation. 13829 public boolean bindBackupAgent(ApplicationInfo app, int backupMode) { 13830 if (DEBUG_BACKUP) Slog.v(TAG, "bindBackupAgent: app=" + app + " mode=" + backupMode); 13831 enforceCallingPermission("android.permission.CONFIRM_FULL_BACKUP", "bindBackupAgent"); 13832 13833 synchronized(this) { 13834 // !!! TODO: currently no check here that we're already bound 13835 BatteryStatsImpl.Uid.Pkg.Serv ss = null; 13836 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 13837 synchronized (stats) { 13838 ss = stats.getServiceStatsLocked(app.uid, app.packageName, app.name); 13839 } 13840 13841 // Backup agent is now in use, its package can't be stopped. 13842 try { 13843 AppGlobals.getPackageManager().setPackageStoppedState( 13844 app.packageName, false, UserHandle.getUserId(app.uid)); 13845 } catch (RemoteException e) { 13846 } catch (IllegalArgumentException e) { 13847 Slog.w(TAG, "Failed trying to unstop package " 13848 + app.packageName + ": " + e); 13849 } 13850 13851 BackupRecord r = new BackupRecord(ss, app, backupMode); 13852 ComponentName hostingName = (backupMode == IApplicationThread.BACKUP_MODE_INCREMENTAL) 13853 ? new ComponentName(app.packageName, app.backupAgentName) 13854 : new ComponentName("android", "FullBackupAgent"); 13855 // startProcessLocked() returns existing proc's record if it's already running 13856 ProcessRecord proc = startProcessLocked(app.processName, app, 13857 false, 0, "backup", hostingName, false, false, false); 13858 if (proc == null) { 13859 Slog.e(TAG, "Unable to start backup agent process " + r); 13860 return false; 13861 } 13862 13863 r.app = proc; 13864 mBackupTarget = r; 13865 mBackupAppName = app.packageName; 13866 13867 // Try not to kill the process during backup 13868 updateOomAdjLocked(proc); 13869 13870 // If the process is already attached, schedule the creation of the backup agent now. 13871 // If it is not yet live, this will be done when it attaches to the framework. 13872 if (proc.thread != null) { 13873 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc already running: " + proc); 13874 try { 13875 proc.thread.scheduleCreateBackupAgent(app, 13876 compatibilityInfoForPackageLocked(app), backupMode); 13877 } catch (RemoteException e) { 13878 // Will time out on the backup manager side 13879 } 13880 } else { 13881 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc not running, waiting for attach"); 13882 } 13883 // Invariants: at this point, the target app process exists and the application 13884 // is either already running or in the process of coming up. mBackupTarget and 13885 // mBackupAppName describe the app, so that when it binds back to the AM we 13886 // know that it's scheduled for a backup-agent operation. 13887 } 13888 13889 return true; 13890 } 13891 13892 @Override 13893 public void clearPendingBackup() { 13894 if (DEBUG_BACKUP) Slog.v(TAG, "clearPendingBackup"); 13895 enforceCallingPermission("android.permission.BACKUP", "clearPendingBackup"); 13896 13897 synchronized (this) { 13898 mBackupTarget = null; 13899 mBackupAppName = null; 13900 } 13901 } 13902 13903 // A backup agent has just come up 13904 public void backupAgentCreated(String agentPackageName, IBinder agent) { 13905 if (DEBUG_BACKUP) Slog.v(TAG, "backupAgentCreated: " + agentPackageName 13906 + " = " + agent); 13907 13908 synchronized(this) { 13909 if (!agentPackageName.equals(mBackupAppName)) { 13910 Slog.e(TAG, "Backup agent created for " + agentPackageName + " but not requested!"); 13911 return; 13912 } 13913 } 13914 13915 long oldIdent = Binder.clearCallingIdentity(); 13916 try { 13917 IBackupManager bm = IBackupManager.Stub.asInterface( 13918 ServiceManager.getService(Context.BACKUP_SERVICE)); 13919 bm.agentConnected(agentPackageName, agent); 13920 } catch (RemoteException e) { 13921 // can't happen; the backup manager service is local 13922 } catch (Exception e) { 13923 Slog.w(TAG, "Exception trying to deliver BackupAgent binding: "); 13924 e.printStackTrace(); 13925 } finally { 13926 Binder.restoreCallingIdentity(oldIdent); 13927 } 13928 } 13929 13930 // done with this agent 13931 public void unbindBackupAgent(ApplicationInfo appInfo) { 13932 if (DEBUG_BACKUP) Slog.v(TAG, "unbindBackupAgent: " + appInfo); 13933 if (appInfo == null) { 13934 Slog.w(TAG, "unbind backup agent for null app"); 13935 return; 13936 } 13937 13938 synchronized(this) { 13939 try { 13940 if (mBackupAppName == null) { 13941 Slog.w(TAG, "Unbinding backup agent with no active backup"); 13942 return; 13943 } 13944 13945 if (!mBackupAppName.equals(appInfo.packageName)) { 13946 Slog.e(TAG, "Unbind of " + appInfo + " but is not the current backup target"); 13947 return; 13948 } 13949 13950 // Not backing this app up any more; reset its OOM adjustment 13951 final ProcessRecord proc = mBackupTarget.app; 13952 updateOomAdjLocked(proc); 13953 13954 // If the app crashed during backup, 'thread' will be null here 13955 if (proc.thread != null) { 13956 try { 13957 proc.thread.scheduleDestroyBackupAgent(appInfo, 13958 compatibilityInfoForPackageLocked(appInfo)); 13959 } catch (Exception e) { 13960 Slog.e(TAG, "Exception when unbinding backup agent:"); 13961 e.printStackTrace(); 13962 } 13963 } 13964 } finally { 13965 mBackupTarget = null; 13966 mBackupAppName = null; 13967 } 13968 } 13969 } 13970 // ========================================================= 13971 // BROADCASTS 13972 // ========================================================= 13973 13974 private final List getStickiesLocked(String action, IntentFilter filter, 13975 List cur, int userId) { 13976 final ContentResolver resolver = mContext.getContentResolver(); 13977 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 13978 if (stickies == null) { 13979 return cur; 13980 } 13981 final ArrayList<Intent> list = stickies.get(action); 13982 if (list == null) { 13983 return cur; 13984 } 13985 int N = list.size(); 13986 for (int i=0; i<N; i++) { 13987 Intent intent = list.get(i); 13988 if (filter.match(resolver, intent, true, TAG) >= 0) { 13989 if (cur == null) { 13990 cur = new ArrayList<Intent>(); 13991 } 13992 cur.add(intent); 13993 } 13994 } 13995 return cur; 13996 } 13997 13998 boolean isPendingBroadcastProcessLocked(int pid) { 13999 return mFgBroadcastQueue.isPendingBroadcastProcessLocked(pid) 14000 || mBgBroadcastQueue.isPendingBroadcastProcessLocked(pid); 14001 } 14002 14003 void skipPendingBroadcastLocked(int pid) { 14004 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 14005 for (BroadcastQueue queue : mBroadcastQueues) { 14006 queue.skipPendingBroadcastLocked(pid); 14007 } 14008 } 14009 14010 // The app just attached; send any pending broadcasts that it should receive 14011 boolean sendPendingBroadcastsLocked(ProcessRecord app) { 14012 boolean didSomething = false; 14013 for (BroadcastQueue queue : mBroadcastQueues) { 14014 didSomething |= queue.sendPendingBroadcastsLocked(app); 14015 } 14016 return didSomething; 14017 } 14018 14019 public Intent registerReceiver(IApplicationThread caller, String callerPackage, 14020 IIntentReceiver receiver, IntentFilter filter, String permission, int userId) { 14021 enforceNotIsolatedCaller("registerReceiver"); 14022 int callingUid; 14023 int callingPid; 14024 synchronized(this) { 14025 ProcessRecord callerApp = null; 14026 if (caller != null) { 14027 callerApp = getRecordForAppLocked(caller); 14028 if (callerApp == null) { 14029 throw new SecurityException( 14030 "Unable to find app for caller " + caller 14031 + " (pid=" + Binder.getCallingPid() 14032 + ") when registering receiver " + receiver); 14033 } 14034 if (callerApp.info.uid != Process.SYSTEM_UID && 14035 !callerApp.pkgList.containsKey(callerPackage) && 14036 !"android".equals(callerPackage)) { 14037 throw new SecurityException("Given caller package " + callerPackage 14038 + " is not running in process " + callerApp); 14039 } 14040 callingUid = callerApp.info.uid; 14041 callingPid = callerApp.pid; 14042 } else { 14043 callerPackage = null; 14044 callingUid = Binder.getCallingUid(); 14045 callingPid = Binder.getCallingPid(); 14046 } 14047 14048 userId = this.handleIncomingUser(callingPid, callingUid, userId, 14049 true, ALLOW_FULL_ONLY, "registerReceiver", callerPackage); 14050 14051 List allSticky = null; 14052 14053 // Look for any matching sticky broadcasts... 14054 Iterator actions = filter.actionsIterator(); 14055 if (actions != null) { 14056 while (actions.hasNext()) { 14057 String action = (String)actions.next(); 14058 allSticky = getStickiesLocked(action, filter, allSticky, 14059 UserHandle.USER_ALL); 14060 allSticky = getStickiesLocked(action, filter, allSticky, 14061 UserHandle.getUserId(callingUid)); 14062 } 14063 } else { 14064 allSticky = getStickiesLocked(null, filter, allSticky, 14065 UserHandle.USER_ALL); 14066 allSticky = getStickiesLocked(null, filter, allSticky, 14067 UserHandle.getUserId(callingUid)); 14068 } 14069 14070 // The first sticky in the list is returned directly back to 14071 // the client. 14072 Intent sticky = allSticky != null ? (Intent)allSticky.get(0) : null; 14073 14074 if (DEBUG_BROADCAST) Slog.v(TAG, "Register receiver " + filter 14075 + ": " + sticky); 14076 14077 if (receiver == null) { 14078 return sticky; 14079 } 14080 14081 ReceiverList rl 14082 = (ReceiverList)mRegisteredReceivers.get(receiver.asBinder()); 14083 if (rl == null) { 14084 rl = new ReceiverList(this, callerApp, callingPid, callingUid, 14085 userId, receiver); 14086 if (rl.app != null) { 14087 rl.app.receivers.add(rl); 14088 } else { 14089 try { 14090 receiver.asBinder().linkToDeath(rl, 0); 14091 } catch (RemoteException e) { 14092 return sticky; 14093 } 14094 rl.linkedToDeath = true; 14095 } 14096 mRegisteredReceivers.put(receiver.asBinder(), rl); 14097 } else if (rl.uid != callingUid) { 14098 throw new IllegalArgumentException( 14099 "Receiver requested to register for uid " + callingUid 14100 + " was previously registered for uid " + rl.uid); 14101 } else if (rl.pid != callingPid) { 14102 throw new IllegalArgumentException( 14103 "Receiver requested to register for pid " + callingPid 14104 + " was previously registered for pid " + rl.pid); 14105 } else if (rl.userId != userId) { 14106 throw new IllegalArgumentException( 14107 "Receiver requested to register for user " + userId 14108 + " was previously registered for user " + rl.userId); 14109 } 14110 BroadcastFilter bf = new BroadcastFilter(filter, rl, callerPackage, 14111 permission, callingUid, userId); 14112 rl.add(bf); 14113 if (!bf.debugCheck()) { 14114 Slog.w(TAG, "==> For Dynamic broadast"); 14115 } 14116 mReceiverResolver.addFilter(bf); 14117 14118 // Enqueue broadcasts for all existing stickies that match 14119 // this filter. 14120 if (allSticky != null) { 14121 ArrayList receivers = new ArrayList(); 14122 receivers.add(bf); 14123 14124 int N = allSticky.size(); 14125 for (int i=0; i<N; i++) { 14126 Intent intent = (Intent)allSticky.get(i); 14127 BroadcastQueue queue = broadcastQueueForIntent(intent); 14128 BroadcastRecord r = new BroadcastRecord(queue, intent, null, 14129 null, -1, -1, null, null, AppOpsManager.OP_NONE, receivers, null, 0, 14130 null, null, false, true, true, -1); 14131 queue.enqueueParallelBroadcastLocked(r); 14132 queue.scheduleBroadcastsLocked(); 14133 } 14134 } 14135 14136 return sticky; 14137 } 14138 } 14139 14140 public void unregisterReceiver(IIntentReceiver receiver) { 14141 if (DEBUG_BROADCAST) Slog.v(TAG, "Unregister receiver: " + receiver); 14142 14143 final long origId = Binder.clearCallingIdentity(); 14144 try { 14145 boolean doTrim = false; 14146 14147 synchronized(this) { 14148 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder()); 14149 if (rl != null) { 14150 if (rl.curBroadcast != null) { 14151 BroadcastRecord r = rl.curBroadcast; 14152 final boolean doNext = finishReceiverLocked( 14153 receiver.asBinder(), r.resultCode, r.resultData, 14154 r.resultExtras, r.resultAbort); 14155 if (doNext) { 14156 doTrim = true; 14157 r.queue.processNextBroadcast(false); 14158 } 14159 } 14160 14161 if (rl.app != null) { 14162 rl.app.receivers.remove(rl); 14163 } 14164 removeReceiverLocked(rl); 14165 if (rl.linkedToDeath) { 14166 rl.linkedToDeath = false; 14167 rl.receiver.asBinder().unlinkToDeath(rl, 0); 14168 } 14169 } 14170 } 14171 14172 // If we actually concluded any broadcasts, we might now be able 14173 // to trim the recipients' apps from our working set 14174 if (doTrim) { 14175 trimApplications(); 14176 return; 14177 } 14178 14179 } finally { 14180 Binder.restoreCallingIdentity(origId); 14181 } 14182 } 14183 14184 void removeReceiverLocked(ReceiverList rl) { 14185 mRegisteredReceivers.remove(rl.receiver.asBinder()); 14186 int N = rl.size(); 14187 for (int i=0; i<N; i++) { 14188 mReceiverResolver.removeFilter(rl.get(i)); 14189 } 14190 } 14191 14192 private final void sendPackageBroadcastLocked(int cmd, String[] packages, int userId) { 14193 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 14194 ProcessRecord r = mLruProcesses.get(i); 14195 if (r.thread != null && (userId == UserHandle.USER_ALL || r.userId == userId)) { 14196 try { 14197 r.thread.dispatchPackageBroadcast(cmd, packages); 14198 } catch (RemoteException ex) { 14199 } 14200 } 14201 } 14202 } 14203 14204 private List<ResolveInfo> collectReceiverComponents(Intent intent, String resolvedType, 14205 int[] users) { 14206 List<ResolveInfo> receivers = null; 14207 try { 14208 HashSet<ComponentName> singleUserReceivers = null; 14209 boolean scannedFirstReceivers = false; 14210 for (int user : users) { 14211 List<ResolveInfo> newReceivers = AppGlobals.getPackageManager() 14212 .queryIntentReceivers(intent, resolvedType, STOCK_PM_FLAGS, user); 14213 if (user != 0 && newReceivers != null) { 14214 // If this is not the primary user, we need to check for 14215 // any receivers that should be filtered out. 14216 for (int i=0; i<newReceivers.size(); i++) { 14217 ResolveInfo ri = newReceivers.get(i); 14218 if ((ri.activityInfo.flags&ActivityInfo.FLAG_PRIMARY_USER_ONLY) != 0) { 14219 newReceivers.remove(i); 14220 i--; 14221 } 14222 } 14223 } 14224 if (newReceivers != null && newReceivers.size() == 0) { 14225 newReceivers = null; 14226 } 14227 if (receivers == null) { 14228 receivers = newReceivers; 14229 } else if (newReceivers != null) { 14230 // We need to concatenate the additional receivers 14231 // found with what we have do far. This would be easy, 14232 // but we also need to de-dup any receivers that are 14233 // singleUser. 14234 if (!scannedFirstReceivers) { 14235 // Collect any single user receivers we had already retrieved. 14236 scannedFirstReceivers = true; 14237 for (int i=0; i<receivers.size(); i++) { 14238 ResolveInfo ri = receivers.get(i); 14239 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 14240 ComponentName cn = new ComponentName( 14241 ri.activityInfo.packageName, ri.activityInfo.name); 14242 if (singleUserReceivers == null) { 14243 singleUserReceivers = new HashSet<ComponentName>(); 14244 } 14245 singleUserReceivers.add(cn); 14246 } 14247 } 14248 } 14249 // Add the new results to the existing results, tracking 14250 // and de-dupping single user receivers. 14251 for (int i=0; i<newReceivers.size(); i++) { 14252 ResolveInfo ri = newReceivers.get(i); 14253 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 14254 ComponentName cn = new ComponentName( 14255 ri.activityInfo.packageName, ri.activityInfo.name); 14256 if (singleUserReceivers == null) { 14257 singleUserReceivers = new HashSet<ComponentName>(); 14258 } 14259 if (!singleUserReceivers.contains(cn)) { 14260 singleUserReceivers.add(cn); 14261 receivers.add(ri); 14262 } 14263 } else { 14264 receivers.add(ri); 14265 } 14266 } 14267 } 14268 } 14269 } catch (RemoteException ex) { 14270 // pm is in same process, this will never happen. 14271 } 14272 return receivers; 14273 } 14274 14275 private final int broadcastIntentLocked(ProcessRecord callerApp, 14276 String callerPackage, Intent intent, String resolvedType, 14277 IIntentReceiver resultTo, int resultCode, String resultData, 14278 Bundle map, String requiredPermission, int appOp, 14279 boolean ordered, boolean sticky, int callingPid, int callingUid, 14280 int userId) { 14281 intent = new Intent(intent); 14282 14283 // By default broadcasts do not go to stopped apps. 14284 intent.addFlags(Intent.FLAG_EXCLUDE_STOPPED_PACKAGES); 14285 14286 if (DEBUG_BROADCAST_LIGHT) Slog.v( 14287 TAG, (sticky ? "Broadcast sticky: ": "Broadcast: ") + intent 14288 + " ordered=" + ordered + " userid=" + userId); 14289 if ((resultTo != null) && !ordered) { 14290 Slog.w(TAG, "Broadcast " + intent + " not ordered but result callback requested!"); 14291 } 14292 14293 userId = handleIncomingUser(callingPid, callingUid, userId, 14294 true, ALLOW_NON_FULL, "broadcast", callerPackage); 14295 14296 // Make sure that the user who is receiving this broadcast is started. 14297 // If not, we will just skip it. 14298 14299 14300 if (userId != UserHandle.USER_ALL && mStartedUsers.get(userId) == null) { 14301 if (callingUid != Process.SYSTEM_UID || (intent.getFlags() 14302 & Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) { 14303 Slog.w(TAG, "Skipping broadcast of " + intent 14304 + ": user " + userId + " is stopped"); 14305 return ActivityManager.BROADCAST_SUCCESS; 14306 } 14307 } 14308 14309 /* 14310 * Prevent non-system code (defined here to be non-persistent 14311 * processes) from sending protected broadcasts. 14312 */ 14313 int callingAppId = UserHandle.getAppId(callingUid); 14314 if (callingAppId == Process.SYSTEM_UID || callingAppId == Process.PHONE_UID 14315 || callingAppId == Process.SHELL_UID || callingAppId == Process.BLUETOOTH_UID 14316 || callingAppId == Process.NFC_UID || callingUid == 0) { 14317 // Always okay. 14318 } else if (callerApp == null || !callerApp.persistent) { 14319 try { 14320 if (AppGlobals.getPackageManager().isProtectedBroadcast( 14321 intent.getAction())) { 14322 String msg = "Permission Denial: not allowed to send broadcast " 14323 + intent.getAction() + " from pid=" 14324 + callingPid + ", uid=" + callingUid; 14325 Slog.w(TAG, msg); 14326 throw new SecurityException(msg); 14327 } else if (AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(intent.getAction())) { 14328 // Special case for compatibility: we don't want apps to send this, 14329 // but historically it has not been protected and apps may be using it 14330 // to poke their own app widget. So, instead of making it protected, 14331 // just limit it to the caller. 14332 if (callerApp == null) { 14333 String msg = "Permission Denial: not allowed to send broadcast " 14334 + intent.getAction() + " from unknown caller."; 14335 Slog.w(TAG, msg); 14336 throw new SecurityException(msg); 14337 } else if (intent.getComponent() != null) { 14338 // They are good enough to send to an explicit component... verify 14339 // it is being sent to the calling app. 14340 if (!intent.getComponent().getPackageName().equals( 14341 callerApp.info.packageName)) { 14342 String msg = "Permission Denial: not allowed to send broadcast " 14343 + intent.getAction() + " to " 14344 + intent.getComponent().getPackageName() + " from " 14345 + callerApp.info.packageName; 14346 Slog.w(TAG, msg); 14347 throw new SecurityException(msg); 14348 } 14349 } else { 14350 // Limit broadcast to their own package. 14351 intent.setPackage(callerApp.info.packageName); 14352 } 14353 } 14354 } catch (RemoteException e) { 14355 Slog.w(TAG, "Remote exception", e); 14356 return ActivityManager.BROADCAST_SUCCESS; 14357 } 14358 } 14359 14360 // Handle special intents: if this broadcast is from the package 14361 // manager about a package being removed, we need to remove all of 14362 // its activities from the history stack. 14363 final boolean uidRemoved = Intent.ACTION_UID_REMOVED.equals( 14364 intent.getAction()); 14365 if (Intent.ACTION_PACKAGE_REMOVED.equals(intent.getAction()) 14366 || Intent.ACTION_PACKAGE_CHANGED.equals(intent.getAction()) 14367 || Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction()) 14368 || uidRemoved) { 14369 if (checkComponentPermission( 14370 android.Manifest.permission.BROADCAST_PACKAGE_REMOVED, 14371 callingPid, callingUid, -1, true) 14372 == PackageManager.PERMISSION_GRANTED) { 14373 if (uidRemoved) { 14374 final Bundle intentExtras = intent.getExtras(); 14375 final int uid = intentExtras != null 14376 ? intentExtras.getInt(Intent.EXTRA_UID) : -1; 14377 if (uid >= 0) { 14378 BatteryStatsImpl bs = mBatteryStatsService.getActiveStatistics(); 14379 synchronized (bs) { 14380 bs.removeUidStatsLocked(uid); 14381 } 14382 mAppOpsService.uidRemoved(uid); 14383 } 14384 } else { 14385 // If resources are unavailable just force stop all 14386 // those packages and flush the attribute cache as well. 14387 if (Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction())) { 14388 String list[] = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 14389 if (list != null && (list.length > 0)) { 14390 for (String pkg : list) { 14391 forceStopPackageLocked(pkg, -1, false, true, true, false, false, userId, 14392 "storage unmount"); 14393 } 14394 sendPackageBroadcastLocked( 14395 IApplicationThread.EXTERNAL_STORAGE_UNAVAILABLE, list, userId); 14396 } 14397 } else { 14398 Uri data = intent.getData(); 14399 String ssp; 14400 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 14401 boolean removed = Intent.ACTION_PACKAGE_REMOVED.equals( 14402 intent.getAction()); 14403 boolean fullUninstall = removed && 14404 !intent.getBooleanExtra(Intent.EXTRA_REPLACING, false); 14405 if (!intent.getBooleanExtra(Intent.EXTRA_DONT_KILL_APP, false)) { 14406 forceStopPackageLocked(ssp, UserHandle.getAppId( 14407 intent.getIntExtra(Intent.EXTRA_UID, -1)), false, true, true, 14408 false, fullUninstall, userId, 14409 removed ? "pkg removed" : "pkg changed"); 14410 } 14411 if (removed) { 14412 sendPackageBroadcastLocked(IApplicationThread.PACKAGE_REMOVED, 14413 new String[] {ssp}, userId); 14414 if (!intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)) { 14415 mAppOpsService.packageRemoved( 14416 intent.getIntExtra(Intent.EXTRA_UID, -1), ssp); 14417 14418 // Remove all permissions granted from/to this package 14419 removeUriPermissionsForPackageLocked(ssp, userId, true); 14420 } 14421 } 14422 } 14423 } 14424 } 14425 } else { 14426 String msg = "Permission Denial: " + intent.getAction() 14427 + " broadcast from " + callerPackage + " (pid=" + callingPid 14428 + ", uid=" + callingUid + ")" 14429 + " requires " 14430 + android.Manifest.permission.BROADCAST_PACKAGE_REMOVED; 14431 Slog.w(TAG, msg); 14432 throw new SecurityException(msg); 14433 } 14434 14435 // Special case for adding a package: by default turn on compatibility 14436 // mode. 14437 } else if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction())) { 14438 Uri data = intent.getData(); 14439 String ssp; 14440 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 14441 mCompatModePackages.handlePackageAddedLocked(ssp, 14442 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)); 14443 } 14444 } 14445 14446 /* 14447 * If this is the time zone changed action, queue up a message that will reset the timezone 14448 * of all currently running processes. This message will get queued up before the broadcast 14449 * happens. 14450 */ 14451 if (Intent.ACTION_TIMEZONE_CHANGED.equals(intent.getAction())) { 14452 mHandler.sendEmptyMessage(UPDATE_TIME_ZONE); 14453 } 14454 14455 /* 14456 * If the user set the time, let all running processes know. 14457 */ 14458 if (Intent.ACTION_TIME_CHANGED.equals(intent.getAction())) { 14459 final int is24Hour = intent.getBooleanExtra( 14460 Intent.EXTRA_TIME_PREF_24_HOUR_FORMAT, false) ? 1 : 0; 14461 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_TIME, is24Hour, 0)); 14462 } 14463 14464 if (Intent.ACTION_CLEAR_DNS_CACHE.equals(intent.getAction())) { 14465 mHandler.sendEmptyMessage(CLEAR_DNS_CACHE_MSG); 14466 } 14467 14468 if (Proxy.PROXY_CHANGE_ACTION.equals(intent.getAction())) { 14469 ProxyInfo proxy = intent.getParcelableExtra(Proxy.EXTRA_PROXY_INFO); 14470 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_HTTP_PROXY_MSG, proxy)); 14471 } 14472 14473 // Add to the sticky list if requested. 14474 if (sticky) { 14475 if (checkPermission(android.Manifest.permission.BROADCAST_STICKY, 14476 callingPid, callingUid) 14477 != PackageManager.PERMISSION_GRANTED) { 14478 String msg = "Permission Denial: broadcastIntent() requesting a sticky broadcast from pid=" 14479 + callingPid + ", uid=" + callingUid 14480 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 14481 Slog.w(TAG, msg); 14482 throw new SecurityException(msg); 14483 } 14484 if (requiredPermission != null) { 14485 Slog.w(TAG, "Can't broadcast sticky intent " + intent 14486 + " and enforce permission " + requiredPermission); 14487 return ActivityManager.BROADCAST_STICKY_CANT_HAVE_PERMISSION; 14488 } 14489 if (intent.getComponent() != null) { 14490 throw new SecurityException( 14491 "Sticky broadcasts can't target a specific component"); 14492 } 14493 // We use userId directly here, since the "all" target is maintained 14494 // as a separate set of sticky broadcasts. 14495 if (userId != UserHandle.USER_ALL) { 14496 // But first, if this is not a broadcast to all users, then 14497 // make sure it doesn't conflict with an existing broadcast to 14498 // all users. 14499 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get( 14500 UserHandle.USER_ALL); 14501 if (stickies != null) { 14502 ArrayList<Intent> list = stickies.get(intent.getAction()); 14503 if (list != null) { 14504 int N = list.size(); 14505 int i; 14506 for (i=0; i<N; i++) { 14507 if (intent.filterEquals(list.get(i))) { 14508 throw new IllegalArgumentException( 14509 "Sticky broadcast " + intent + " for user " 14510 + userId + " conflicts with existing global broadcast"); 14511 } 14512 } 14513 } 14514 } 14515 } 14516 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 14517 if (stickies == null) { 14518 stickies = new ArrayMap<String, ArrayList<Intent>>(); 14519 mStickyBroadcasts.put(userId, stickies); 14520 } 14521 ArrayList<Intent> list = stickies.get(intent.getAction()); 14522 if (list == null) { 14523 list = new ArrayList<Intent>(); 14524 stickies.put(intent.getAction(), list); 14525 } 14526 int N = list.size(); 14527 int i; 14528 for (i=0; i<N; i++) { 14529 if (intent.filterEquals(list.get(i))) { 14530 // This sticky already exists, replace it. 14531 list.set(i, new Intent(intent)); 14532 break; 14533 } 14534 } 14535 if (i >= N) { 14536 list.add(new Intent(intent)); 14537 } 14538 } 14539 14540 int[] users; 14541 if (userId == UserHandle.USER_ALL) { 14542 // Caller wants broadcast to go to all started users. 14543 users = mStartedUserArray; 14544 } else { 14545 // Caller wants broadcast to go to one specific user. 14546 users = new int[] {userId}; 14547 } 14548 14549 // Figure out who all will receive this broadcast. 14550 List receivers = null; 14551 List<BroadcastFilter> registeredReceivers = null; 14552 // Need to resolve the intent to interested receivers... 14553 if ((intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) 14554 == 0) { 14555 receivers = collectReceiverComponents(intent, resolvedType, users); 14556 } 14557 if (intent.getComponent() == null) { 14558 registeredReceivers = mReceiverResolver.queryIntent(intent, 14559 resolvedType, false, userId); 14560 } 14561 14562 final boolean replacePending = 14563 (intent.getFlags()&Intent.FLAG_RECEIVER_REPLACE_PENDING) != 0; 14564 14565 if (DEBUG_BROADCAST) Slog.v(TAG, "Enqueing broadcast: " + intent.getAction() 14566 + " replacePending=" + replacePending); 14567 14568 int NR = registeredReceivers != null ? registeredReceivers.size() : 0; 14569 if (!ordered && NR > 0) { 14570 // If we are not serializing this broadcast, then send the 14571 // registered receivers separately so they don't wait for the 14572 // components to be launched. 14573 final BroadcastQueue queue = broadcastQueueForIntent(intent); 14574 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 14575 callerPackage, callingPid, callingUid, resolvedType, requiredPermission, 14576 appOp, registeredReceivers, resultTo, resultCode, resultData, map, 14577 ordered, sticky, false, userId); 14578 if (DEBUG_BROADCAST) Slog.v( 14579 TAG, "Enqueueing parallel broadcast " + r); 14580 final boolean replaced = replacePending && queue.replaceParallelBroadcastLocked(r); 14581 if (!replaced) { 14582 queue.enqueueParallelBroadcastLocked(r); 14583 queue.scheduleBroadcastsLocked(); 14584 } 14585 registeredReceivers = null; 14586 NR = 0; 14587 } 14588 14589 // Merge into one list. 14590 int ir = 0; 14591 if (receivers != null) { 14592 // A special case for PACKAGE_ADDED: do not allow the package 14593 // being added to see this broadcast. This prevents them from 14594 // using this as a back door to get run as soon as they are 14595 // installed. Maybe in the future we want to have a special install 14596 // broadcast or such for apps, but we'd like to deliberately make 14597 // this decision. 14598 String skipPackages[] = null; 14599 if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction()) 14600 || Intent.ACTION_PACKAGE_RESTARTED.equals(intent.getAction()) 14601 || Intent.ACTION_PACKAGE_DATA_CLEARED.equals(intent.getAction())) { 14602 Uri data = intent.getData(); 14603 if (data != null) { 14604 String pkgName = data.getSchemeSpecificPart(); 14605 if (pkgName != null) { 14606 skipPackages = new String[] { pkgName }; 14607 } 14608 } 14609 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction())) { 14610 skipPackages = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 14611 } 14612 if (skipPackages != null && (skipPackages.length > 0)) { 14613 for (String skipPackage : skipPackages) { 14614 if (skipPackage != null) { 14615 int NT = receivers.size(); 14616 for (int it=0; it<NT; it++) { 14617 ResolveInfo curt = (ResolveInfo)receivers.get(it); 14618 if (curt.activityInfo.packageName.equals(skipPackage)) { 14619 receivers.remove(it); 14620 it--; 14621 NT--; 14622 } 14623 } 14624 } 14625 } 14626 } 14627 14628 int NT = receivers != null ? receivers.size() : 0; 14629 int it = 0; 14630 ResolveInfo curt = null; 14631 BroadcastFilter curr = null; 14632 while (it < NT && ir < NR) { 14633 if (curt == null) { 14634 curt = (ResolveInfo)receivers.get(it); 14635 } 14636 if (curr == null) { 14637 curr = registeredReceivers.get(ir); 14638 } 14639 if (curr.getPriority() >= curt.priority) { 14640 // Insert this broadcast record into the final list. 14641 receivers.add(it, curr); 14642 ir++; 14643 curr = null; 14644 it++; 14645 NT++; 14646 } else { 14647 // Skip to the next ResolveInfo in the final list. 14648 it++; 14649 curt = null; 14650 } 14651 } 14652 } 14653 while (ir < NR) { 14654 if (receivers == null) { 14655 receivers = new ArrayList(); 14656 } 14657 receivers.add(registeredReceivers.get(ir)); 14658 ir++; 14659 } 14660 14661 if ((receivers != null && receivers.size() > 0) 14662 || resultTo != null) { 14663 BroadcastQueue queue = broadcastQueueForIntent(intent); 14664 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 14665 callerPackage, callingPid, callingUid, resolvedType, 14666 requiredPermission, appOp, receivers, resultTo, resultCode, 14667 resultData, map, ordered, sticky, false, userId); 14668 if (DEBUG_BROADCAST) Slog.v( 14669 TAG, "Enqueueing ordered broadcast " + r 14670 + ": prev had " + queue.mOrderedBroadcasts.size()); 14671 if (DEBUG_BROADCAST) { 14672 int seq = r.intent.getIntExtra("seq", -1); 14673 Slog.i(TAG, "Enqueueing broadcast " + r.intent.getAction() + " seq=" + seq); 14674 } 14675 boolean replaced = replacePending && queue.replaceOrderedBroadcastLocked(r); 14676 if (!replaced) { 14677 queue.enqueueOrderedBroadcastLocked(r); 14678 queue.scheduleBroadcastsLocked(); 14679 } 14680 } 14681 14682 return ActivityManager.BROADCAST_SUCCESS; 14683 } 14684 14685 final Intent verifyBroadcastLocked(Intent intent) { 14686 // Refuse possible leaked file descriptors 14687 if (intent != null && intent.hasFileDescriptors() == true) { 14688 throw new IllegalArgumentException("File descriptors passed in Intent"); 14689 } 14690 14691 int flags = intent.getFlags(); 14692 14693 if (!mProcessesReady) { 14694 // if the caller really truly claims to know what they're doing, go 14695 // ahead and allow the broadcast without launching any receivers 14696 if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT) != 0) { 14697 intent = new Intent(intent); 14698 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 14699 } else if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) { 14700 Slog.e(TAG, "Attempt to launch receivers of broadcast intent " + intent 14701 + " before boot completion"); 14702 throw new IllegalStateException("Cannot broadcast before boot completed"); 14703 } 14704 } 14705 14706 if ((flags&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 14707 throw new IllegalArgumentException( 14708 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 14709 } 14710 14711 return intent; 14712 } 14713 14714 public final int broadcastIntent(IApplicationThread caller, 14715 Intent intent, String resolvedType, IIntentReceiver resultTo, 14716 int resultCode, String resultData, Bundle map, 14717 String requiredPermission, int appOp, boolean serialized, boolean sticky, int userId) { 14718 enforceNotIsolatedCaller("broadcastIntent"); 14719 synchronized(this) { 14720 intent = verifyBroadcastLocked(intent); 14721 14722 final ProcessRecord callerApp = getRecordForAppLocked(caller); 14723 final int callingPid = Binder.getCallingPid(); 14724 final int callingUid = Binder.getCallingUid(); 14725 final long origId = Binder.clearCallingIdentity(); 14726 int res = broadcastIntentLocked(callerApp, 14727 callerApp != null ? callerApp.info.packageName : null, 14728 intent, resolvedType, resultTo, 14729 resultCode, resultData, map, requiredPermission, appOp, serialized, sticky, 14730 callingPid, callingUid, userId); 14731 Binder.restoreCallingIdentity(origId); 14732 return res; 14733 } 14734 } 14735 14736 int broadcastIntentInPackage(String packageName, int uid, 14737 Intent intent, String resolvedType, IIntentReceiver resultTo, 14738 int resultCode, String resultData, Bundle map, 14739 String requiredPermission, boolean serialized, boolean sticky, int userId) { 14740 synchronized(this) { 14741 intent = verifyBroadcastLocked(intent); 14742 14743 final long origId = Binder.clearCallingIdentity(); 14744 int res = broadcastIntentLocked(null, packageName, intent, resolvedType, 14745 resultTo, resultCode, resultData, map, requiredPermission, 14746 AppOpsManager.OP_NONE, serialized, sticky, -1, uid, userId); 14747 Binder.restoreCallingIdentity(origId); 14748 return res; 14749 } 14750 } 14751 14752 public final void unbroadcastIntent(IApplicationThread caller, Intent intent, int userId) { 14753 // Refuse possible leaked file descriptors 14754 if (intent != null && intent.hasFileDescriptors() == true) { 14755 throw new IllegalArgumentException("File descriptors passed in Intent"); 14756 } 14757 14758 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 14759 userId, true, ALLOW_NON_FULL, "removeStickyBroadcast", null); 14760 14761 synchronized(this) { 14762 if (checkCallingPermission(android.Manifest.permission.BROADCAST_STICKY) 14763 != PackageManager.PERMISSION_GRANTED) { 14764 String msg = "Permission Denial: unbroadcastIntent() from pid=" 14765 + Binder.getCallingPid() 14766 + ", uid=" + Binder.getCallingUid() 14767 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 14768 Slog.w(TAG, msg); 14769 throw new SecurityException(msg); 14770 } 14771 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 14772 if (stickies != null) { 14773 ArrayList<Intent> list = stickies.get(intent.getAction()); 14774 if (list != null) { 14775 int N = list.size(); 14776 int i; 14777 for (i=0; i<N; i++) { 14778 if (intent.filterEquals(list.get(i))) { 14779 list.remove(i); 14780 break; 14781 } 14782 } 14783 if (list.size() <= 0) { 14784 stickies.remove(intent.getAction()); 14785 } 14786 } 14787 if (stickies.size() <= 0) { 14788 mStickyBroadcasts.remove(userId); 14789 } 14790 } 14791 } 14792 } 14793 14794 private final boolean finishReceiverLocked(IBinder receiver, int resultCode, 14795 String resultData, Bundle resultExtras, boolean resultAbort) { 14796 final BroadcastRecord r = broadcastRecordForReceiverLocked(receiver); 14797 if (r == null) { 14798 Slog.w(TAG, "finishReceiver called but not found on queue"); 14799 return false; 14800 } 14801 14802 return r.queue.finishReceiverLocked(r, resultCode, resultData, resultExtras, resultAbort, false); 14803 } 14804 14805 void backgroundServicesFinishedLocked(int userId) { 14806 for (BroadcastQueue queue : mBroadcastQueues) { 14807 queue.backgroundServicesFinishedLocked(userId); 14808 } 14809 } 14810 14811 public void finishReceiver(IBinder who, int resultCode, String resultData, 14812 Bundle resultExtras, boolean resultAbort) { 14813 if (DEBUG_BROADCAST) Slog.v(TAG, "Finish receiver: " + who); 14814 14815 // Refuse possible leaked file descriptors 14816 if (resultExtras != null && resultExtras.hasFileDescriptors()) { 14817 throw new IllegalArgumentException("File descriptors passed in Bundle"); 14818 } 14819 14820 final long origId = Binder.clearCallingIdentity(); 14821 try { 14822 boolean doNext = false; 14823 BroadcastRecord r; 14824 14825 synchronized(this) { 14826 r = broadcastRecordForReceiverLocked(who); 14827 if (r != null) { 14828 doNext = r.queue.finishReceiverLocked(r, resultCode, 14829 resultData, resultExtras, resultAbort, true); 14830 } 14831 } 14832 14833 if (doNext) { 14834 r.queue.processNextBroadcast(false); 14835 } 14836 trimApplications(); 14837 } finally { 14838 Binder.restoreCallingIdentity(origId); 14839 } 14840 } 14841 14842 // ========================================================= 14843 // INSTRUMENTATION 14844 // ========================================================= 14845 14846 public boolean startInstrumentation(ComponentName className, 14847 String profileFile, int flags, Bundle arguments, 14848 IInstrumentationWatcher watcher, IUiAutomationConnection uiAutomationConnection, 14849 int userId, String abiOverride) { 14850 enforceNotIsolatedCaller("startInstrumentation"); 14851 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 14852 userId, false, ALLOW_FULL_ONLY, "startInstrumentation", null); 14853 // Refuse possible leaked file descriptors 14854 if (arguments != null && arguments.hasFileDescriptors()) { 14855 throw new IllegalArgumentException("File descriptors passed in Bundle"); 14856 } 14857 14858 synchronized(this) { 14859 InstrumentationInfo ii = null; 14860 ApplicationInfo ai = null; 14861 try { 14862 ii = mContext.getPackageManager().getInstrumentationInfo( 14863 className, STOCK_PM_FLAGS); 14864 ai = AppGlobals.getPackageManager().getApplicationInfo( 14865 ii.targetPackage, STOCK_PM_FLAGS, userId); 14866 } catch (PackageManager.NameNotFoundException e) { 14867 } catch (RemoteException e) { 14868 } 14869 if (ii == null) { 14870 reportStartInstrumentationFailure(watcher, className, 14871 "Unable to find instrumentation info for: " + className); 14872 return false; 14873 } 14874 if (ai == null) { 14875 reportStartInstrumentationFailure(watcher, className, 14876 "Unable to find instrumentation target package: " + ii.targetPackage); 14877 return false; 14878 } 14879 14880 int match = mContext.getPackageManager().checkSignatures( 14881 ii.targetPackage, ii.packageName); 14882 if (match < 0 && match != PackageManager.SIGNATURE_FIRST_NOT_SIGNED) { 14883 String msg = "Permission Denial: starting instrumentation " 14884 + className + " from pid=" 14885 + Binder.getCallingPid() 14886 + ", uid=" + Binder.getCallingPid() 14887 + " not allowed because package " + ii.packageName 14888 + " does not have a signature matching the target " 14889 + ii.targetPackage; 14890 reportStartInstrumentationFailure(watcher, className, msg); 14891 throw new SecurityException(msg); 14892 } 14893 14894 final long origId = Binder.clearCallingIdentity(); 14895 // Instrumentation can kill and relaunch even persistent processes 14896 forceStopPackageLocked(ii.targetPackage, -1, true, false, true, true, false, userId, 14897 "start instr"); 14898 ProcessRecord app = addAppLocked(ai, false, abiOverride); 14899 app.instrumentationClass = className; 14900 app.instrumentationInfo = ai; 14901 app.instrumentationProfileFile = profileFile; 14902 app.instrumentationArguments = arguments; 14903 app.instrumentationWatcher = watcher; 14904 app.instrumentationUiAutomationConnection = uiAutomationConnection; 14905 app.instrumentationResultClass = className; 14906 Binder.restoreCallingIdentity(origId); 14907 } 14908 14909 return true; 14910 } 14911 14912 /** 14913 * Report errors that occur while attempting to start Instrumentation. Always writes the 14914 * error to the logs, but if somebody is watching, send the report there too. This enables 14915 * the "am" command to report errors with more information. 14916 * 14917 * @param watcher The IInstrumentationWatcher. Null if there isn't one. 14918 * @param cn The component name of the instrumentation. 14919 * @param report The error report. 14920 */ 14921 private void reportStartInstrumentationFailure(IInstrumentationWatcher watcher, 14922 ComponentName cn, String report) { 14923 Slog.w(TAG, report); 14924 try { 14925 if (watcher != null) { 14926 Bundle results = new Bundle(); 14927 results.putString(Instrumentation.REPORT_KEY_IDENTIFIER, "ActivityManagerService"); 14928 results.putString("Error", report); 14929 watcher.instrumentationStatus(cn, -1, results); 14930 } 14931 } catch (RemoteException e) { 14932 Slog.w(TAG, e); 14933 } 14934 } 14935 14936 void finishInstrumentationLocked(ProcessRecord app, int resultCode, Bundle results) { 14937 if (app.instrumentationWatcher != null) { 14938 try { 14939 // NOTE: IInstrumentationWatcher *must* be oneway here 14940 app.instrumentationWatcher.instrumentationFinished( 14941 app.instrumentationClass, 14942 resultCode, 14943 results); 14944 } catch (RemoteException e) { 14945 } 14946 } 14947 if (app.instrumentationUiAutomationConnection != null) { 14948 try { 14949 app.instrumentationUiAutomationConnection.shutdown(); 14950 } catch (RemoteException re) { 14951 /* ignore */ 14952 } 14953 // Only a UiAutomation can set this flag and now that 14954 // it is finished we make sure it is reset to its default. 14955 mUserIsMonkey = false; 14956 } 14957 app.instrumentationWatcher = null; 14958 app.instrumentationUiAutomationConnection = null; 14959 app.instrumentationClass = null; 14960 app.instrumentationInfo = null; 14961 app.instrumentationProfileFile = null; 14962 app.instrumentationArguments = null; 14963 14964 forceStopPackageLocked(app.info.packageName, -1, false, false, true, true, false, app.userId, 14965 "finished inst"); 14966 } 14967 14968 public void finishInstrumentation(IApplicationThread target, 14969 int resultCode, Bundle results) { 14970 int userId = UserHandle.getCallingUserId(); 14971 // Refuse possible leaked file descriptors 14972 if (results != null && results.hasFileDescriptors()) { 14973 throw new IllegalArgumentException("File descriptors passed in Intent"); 14974 } 14975 14976 synchronized(this) { 14977 ProcessRecord app = getRecordForAppLocked(target); 14978 if (app == null) { 14979 Slog.w(TAG, "finishInstrumentation: no app for " + target); 14980 return; 14981 } 14982 final long origId = Binder.clearCallingIdentity(); 14983 finishInstrumentationLocked(app, resultCode, results); 14984 Binder.restoreCallingIdentity(origId); 14985 } 14986 } 14987 14988 // ========================================================= 14989 // CONFIGURATION 14990 // ========================================================= 14991 14992 public ConfigurationInfo getDeviceConfigurationInfo() { 14993 ConfigurationInfo config = new ConfigurationInfo(); 14994 synchronized (this) { 14995 config.reqTouchScreen = mConfiguration.touchscreen; 14996 config.reqKeyboardType = mConfiguration.keyboard; 14997 config.reqNavigation = mConfiguration.navigation; 14998 if (mConfiguration.navigation == Configuration.NAVIGATION_DPAD 14999 || mConfiguration.navigation == Configuration.NAVIGATION_TRACKBALL) { 15000 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_FIVE_WAY_NAV; 15001 } 15002 if (mConfiguration.keyboard != Configuration.KEYBOARD_UNDEFINED 15003 && mConfiguration.keyboard != Configuration.KEYBOARD_NOKEYS) { 15004 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_HARD_KEYBOARD; 15005 } 15006 config.reqGlEsVersion = GL_ES_VERSION; 15007 } 15008 return config; 15009 } 15010 15011 ActivityStack getFocusedStack() { 15012 return mStackSupervisor.getFocusedStack(); 15013 } 15014 15015 public Configuration getConfiguration() { 15016 Configuration ci; 15017 synchronized(this) { 15018 ci = new Configuration(mConfiguration); 15019 } 15020 return ci; 15021 } 15022 15023 public void updatePersistentConfiguration(Configuration values) { 15024 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 15025 "updateConfiguration()"); 15026 enforceCallingPermission(android.Manifest.permission.WRITE_SETTINGS, 15027 "updateConfiguration()"); 15028 if (values == null) { 15029 throw new NullPointerException("Configuration must not be null"); 15030 } 15031 15032 synchronized(this) { 15033 final long origId = Binder.clearCallingIdentity(); 15034 updateConfigurationLocked(values, null, true, false); 15035 Binder.restoreCallingIdentity(origId); 15036 } 15037 } 15038 15039 public void updateConfiguration(Configuration values) { 15040 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 15041 "updateConfiguration()"); 15042 15043 synchronized(this) { 15044 if (values == null && mWindowManager != null) { 15045 // sentinel: fetch the current configuration from the window manager 15046 values = mWindowManager.computeNewConfiguration(); 15047 } 15048 15049 if (mWindowManager != null) { 15050 mProcessList.applyDisplaySize(mWindowManager); 15051 } 15052 15053 final long origId = Binder.clearCallingIdentity(); 15054 if (values != null) { 15055 Settings.System.clearConfiguration(values); 15056 } 15057 updateConfigurationLocked(values, null, false, false); 15058 Binder.restoreCallingIdentity(origId); 15059 } 15060 } 15061 15062 /** 15063 * Do either or both things: (1) change the current configuration, and (2) 15064 * make sure the given activity is running with the (now) current 15065 * configuration. Returns true if the activity has been left running, or 15066 * false if <var>starting</var> is being destroyed to match the new 15067 * configuration. 15068 * @param persistent TODO 15069 */ 15070 boolean updateConfigurationLocked(Configuration values, 15071 ActivityRecord starting, boolean persistent, boolean initLocale) { 15072 int changes = 0; 15073 15074 if (values != null) { 15075 Configuration newConfig = new Configuration(mConfiguration); 15076 changes = newConfig.updateFrom(values); 15077 if (changes != 0) { 15078 if (DEBUG_SWITCH || DEBUG_CONFIGURATION) { 15079 Slog.i(TAG, "Updating configuration to: " + values); 15080 } 15081 15082 EventLog.writeEvent(EventLogTags.CONFIGURATION_CHANGED, changes); 15083 15084 if (values.locale != null && !initLocale) { 15085 saveLocaleLocked(values.locale, 15086 !values.locale.equals(mConfiguration.locale), 15087 values.userSetLocale); 15088 } 15089 15090 mConfigurationSeq++; 15091 if (mConfigurationSeq <= 0) { 15092 mConfigurationSeq = 1; 15093 } 15094 newConfig.seq = mConfigurationSeq; 15095 mConfiguration = newConfig; 15096 Slog.i(TAG, "Config changes=" + Integer.toHexString(changes) + " " + newConfig); 15097 //mUsageStatsService.noteStartConfig(newConfig); 15098 15099 final Configuration configCopy = new Configuration(mConfiguration); 15100 15101 // TODO: If our config changes, should we auto dismiss any currently 15102 // showing dialogs? 15103 mShowDialogs = shouldShowDialogs(newConfig); 15104 15105 AttributeCache ac = AttributeCache.instance(); 15106 if (ac != null) { 15107 ac.updateConfiguration(configCopy); 15108 } 15109 15110 // Make sure all resources in our process are updated 15111 // right now, so that anyone who is going to retrieve 15112 // resource values after we return will be sure to get 15113 // the new ones. This is especially important during 15114 // boot, where the first config change needs to guarantee 15115 // all resources have that config before following boot 15116 // code is executed. 15117 mSystemThread.applyConfigurationToResources(configCopy); 15118 15119 if (persistent && Settings.System.hasInterestingConfigurationChanges(changes)) { 15120 Message msg = mHandler.obtainMessage(UPDATE_CONFIGURATION_MSG); 15121 msg.obj = new Configuration(configCopy); 15122 mHandler.sendMessage(msg); 15123 } 15124 15125 for (int i=mLruProcesses.size()-1; i>=0; i--) { 15126 ProcessRecord app = mLruProcesses.get(i); 15127 try { 15128 if (app.thread != null) { 15129 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Sending to proc " 15130 + app.processName + " new config " + mConfiguration); 15131 app.thread.scheduleConfigurationChanged(configCopy); 15132 } 15133 } catch (Exception e) { 15134 } 15135 } 15136 Intent intent = new Intent(Intent.ACTION_CONFIGURATION_CHANGED); 15137 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 15138 | Intent.FLAG_RECEIVER_REPLACE_PENDING 15139 | Intent.FLAG_RECEIVER_FOREGROUND); 15140 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, 15141 null, AppOpsManager.OP_NONE, false, false, MY_PID, 15142 Process.SYSTEM_UID, UserHandle.USER_ALL); 15143 if ((changes&ActivityInfo.CONFIG_LOCALE) != 0) { 15144 intent = new Intent(Intent.ACTION_LOCALE_CHANGED); 15145 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 15146 broadcastIntentLocked(null, null, intent, 15147 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 15148 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 15149 } 15150 } 15151 } 15152 15153 boolean kept = true; 15154 final ActivityStack mainStack = mStackSupervisor.getFocusedStack(); 15155 // mainStack is null during startup. 15156 if (mainStack != null) { 15157 if (changes != 0 && starting == null) { 15158 // If the configuration changed, and the caller is not already 15159 // in the process of starting an activity, then find the top 15160 // activity to check if its configuration needs to change. 15161 starting = mainStack.topRunningActivityLocked(null); 15162 } 15163 15164 if (starting != null) { 15165 kept = mainStack.ensureActivityConfigurationLocked(starting, changes); 15166 // And we need to make sure at this point that all other activities 15167 // are made visible with the correct configuration. 15168 mStackSupervisor.ensureActivitiesVisibleLocked(starting, changes); 15169 } 15170 } 15171 15172 if (values != null && mWindowManager != null) { 15173 mWindowManager.setNewConfiguration(mConfiguration); 15174 } 15175 15176 return kept; 15177 } 15178 15179 /** 15180 * Decide based on the configuration whether we should shouw the ANR, 15181 * crash, etc dialogs. The idea is that if there is no affordnace to 15182 * press the on-screen buttons, we shouldn't show the dialog. 15183 * 15184 * A thought: SystemUI might also want to get told about this, the Power 15185 * dialog / global actions also might want different behaviors. 15186 */ 15187 private static final boolean shouldShowDialogs(Configuration config) { 15188 return !(config.keyboard == Configuration.KEYBOARD_NOKEYS 15189 && config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH); 15190 } 15191 15192 /** 15193 * Save the locale. You must be inside a synchronized (this) block. 15194 */ 15195 private void saveLocaleLocked(Locale l, boolean isDiff, boolean isPersist) { 15196 if(isDiff) { 15197 SystemProperties.set("user.language", l.getLanguage()); 15198 SystemProperties.set("user.region", l.getCountry()); 15199 } 15200 15201 if(isPersist) { 15202 SystemProperties.set("persist.sys.language", l.getLanguage()); 15203 SystemProperties.set("persist.sys.country", l.getCountry()); 15204 SystemProperties.set("persist.sys.localevar", l.getVariant()); 15205 } 15206 } 15207 15208 @Override 15209 public boolean targetTaskAffinityMatchesActivity(IBinder token, String destAffinity) { 15210 ActivityRecord srec = ActivityRecord.forToken(token); 15211 return srec != null && srec.task.affinity != null && 15212 srec.task.affinity.equals(destAffinity); 15213 } 15214 15215 public boolean navigateUpTo(IBinder token, Intent destIntent, int resultCode, 15216 Intent resultData) { 15217 15218 synchronized (this) { 15219 final ActivityStack stack = ActivityRecord.getStackLocked(token); 15220 if (stack != null) { 15221 return stack.navigateUpToLocked(token, destIntent, resultCode, resultData); 15222 } 15223 return false; 15224 } 15225 } 15226 15227 public int getLaunchedFromUid(IBinder activityToken) { 15228 ActivityRecord srec = ActivityRecord.forToken(activityToken); 15229 if (srec == null) { 15230 return -1; 15231 } 15232 return srec.launchedFromUid; 15233 } 15234 15235 public String getLaunchedFromPackage(IBinder activityToken) { 15236 ActivityRecord srec = ActivityRecord.forToken(activityToken); 15237 if (srec == null) { 15238 return null; 15239 } 15240 return srec.launchedFromPackage; 15241 } 15242 15243 // ========================================================= 15244 // LIFETIME MANAGEMENT 15245 // ========================================================= 15246 15247 // Returns which broadcast queue the app is the current [or imminent] receiver 15248 // on, or 'null' if the app is not an active broadcast recipient. 15249 private BroadcastQueue isReceivingBroadcast(ProcessRecord app) { 15250 BroadcastRecord r = app.curReceiver; 15251 if (r != null) { 15252 return r.queue; 15253 } 15254 15255 // It's not the current receiver, but it might be starting up to become one 15256 synchronized (this) { 15257 for (BroadcastQueue queue : mBroadcastQueues) { 15258 r = queue.mPendingBroadcast; 15259 if (r != null && r.curApp == app) { 15260 // found it; report which queue it's in 15261 return queue; 15262 } 15263 } 15264 } 15265 15266 return null; 15267 } 15268 15269 private final int computeOomAdjLocked(ProcessRecord app, int cachedAdj, ProcessRecord TOP_APP, 15270 boolean doingAll, long now) { 15271 if (mAdjSeq == app.adjSeq) { 15272 // This adjustment has already been computed. 15273 return app.curRawAdj; 15274 } 15275 15276 if (app.thread == null) { 15277 app.adjSeq = mAdjSeq; 15278 app.curSchedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15279 app.curProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15280 return (app.curAdj=app.curRawAdj=ProcessList.CACHED_APP_MAX_ADJ); 15281 } 15282 15283 app.adjTypeCode = ActivityManager.RunningAppProcessInfo.REASON_UNKNOWN; 15284 app.adjSource = null; 15285 app.adjTarget = null; 15286 app.empty = false; 15287 app.cached = false; 15288 15289 final int activitiesSize = app.activities.size(); 15290 15291 if (app.maxAdj <= ProcessList.FOREGROUND_APP_ADJ) { 15292 // The max adjustment doesn't allow this app to be anything 15293 // below foreground, so it is not worth doing work for it. 15294 app.adjType = "fixed"; 15295 app.adjSeq = mAdjSeq; 15296 app.curRawAdj = app.maxAdj; 15297 app.foregroundActivities = false; 15298 app.curSchedGroup = Process.THREAD_GROUP_DEFAULT; 15299 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT; 15300 // System processes can do UI, and when they do we want to have 15301 // them trim their memory after the user leaves the UI. To 15302 // facilitate this, here we need to determine whether or not it 15303 // is currently showing UI. 15304 app.systemNoUi = true; 15305 if (app == TOP_APP) { 15306 app.systemNoUi = false; 15307 } else if (activitiesSize > 0) { 15308 for (int j = 0; j < activitiesSize; j++) { 15309 final ActivityRecord r = app.activities.get(j); 15310 if (r.visible) { 15311 app.systemNoUi = false; 15312 } 15313 } 15314 } 15315 if (!app.systemNoUi) { 15316 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT_UI; 15317 } 15318 return (app.curAdj=app.maxAdj); 15319 } 15320 15321 app.systemNoUi = false; 15322 15323 // Determine the importance of the process, starting with most 15324 // important to least, and assign an appropriate OOM adjustment. 15325 int adj; 15326 int schedGroup; 15327 int procState; 15328 boolean foregroundActivities = false; 15329 BroadcastQueue queue; 15330 if (app == TOP_APP) { 15331 // The last app on the list is the foreground app. 15332 adj = ProcessList.FOREGROUND_APP_ADJ; 15333 schedGroup = Process.THREAD_GROUP_DEFAULT; 15334 app.adjType = "top-activity"; 15335 foregroundActivities = true; 15336 procState = ActivityManager.PROCESS_STATE_TOP; 15337 } else if (app.instrumentationClass != null) { 15338 // Don't want to kill running instrumentation. 15339 adj = ProcessList.FOREGROUND_APP_ADJ; 15340 schedGroup = Process.THREAD_GROUP_DEFAULT; 15341 app.adjType = "instrumentation"; 15342 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15343 } else if ((queue = isReceivingBroadcast(app)) != null) { 15344 // An app that is currently receiving a broadcast also 15345 // counts as being in the foreground for OOM killer purposes. 15346 // It's placed in a sched group based on the nature of the 15347 // broadcast as reflected by which queue it's active in. 15348 adj = ProcessList.FOREGROUND_APP_ADJ; 15349 schedGroup = (queue == mFgBroadcastQueue) 15350 ? Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 15351 app.adjType = "broadcast"; 15352 procState = ActivityManager.PROCESS_STATE_RECEIVER; 15353 } else if (app.executingServices.size() > 0) { 15354 // An app that is currently executing a service callback also 15355 // counts as being in the foreground. 15356 adj = ProcessList.FOREGROUND_APP_ADJ; 15357 schedGroup = app.execServicesFg ? 15358 Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 15359 app.adjType = "exec-service"; 15360 procState = ActivityManager.PROCESS_STATE_SERVICE; 15361 //Slog.i(TAG, "EXEC " + (app.execServicesFg ? "FG" : "BG") + ": " + app); 15362 } else { 15363 // As far as we know the process is empty. We may change our mind later. 15364 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15365 // At this point we don't actually know the adjustment. Use the cached adj 15366 // value that the caller wants us to. 15367 adj = cachedAdj; 15368 procState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15369 app.cached = true; 15370 app.empty = true; 15371 app.adjType = "cch-empty"; 15372 } 15373 15374 // Examine all activities if not already foreground. 15375 if (!foregroundActivities && activitiesSize > 0) { 15376 for (int j = 0; j < activitiesSize; j++) { 15377 final ActivityRecord r = app.activities.get(j); 15378 if (r.app != app) { 15379 Slog.w(TAG, "Wtf, activity " + r + " in proc activity list not using proc " 15380 + app + "?!?"); 15381 continue; 15382 } 15383 if (r.visible) { 15384 // App has a visible activity; only upgrade adjustment. 15385 if (adj > ProcessList.VISIBLE_APP_ADJ) { 15386 adj = ProcessList.VISIBLE_APP_ADJ; 15387 app.adjType = "visible"; 15388 } 15389 if (procState > ActivityManager.PROCESS_STATE_TOP) { 15390 procState = ActivityManager.PROCESS_STATE_TOP; 15391 } 15392 schedGroup = Process.THREAD_GROUP_DEFAULT; 15393 app.cached = false; 15394 app.empty = false; 15395 foregroundActivities = true; 15396 break; 15397 } else if (r.state == ActivityState.PAUSING || r.state == ActivityState.PAUSED) { 15398 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15399 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15400 app.adjType = "pausing"; 15401 } 15402 if (procState > ActivityManager.PROCESS_STATE_TOP) { 15403 procState = ActivityManager.PROCESS_STATE_TOP; 15404 } 15405 schedGroup = Process.THREAD_GROUP_DEFAULT; 15406 app.cached = false; 15407 app.empty = false; 15408 foregroundActivities = true; 15409 } else if (r.state == ActivityState.STOPPING) { 15410 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15411 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15412 app.adjType = "stopping"; 15413 } 15414 // For the process state, we will at this point consider the 15415 // process to be cached. It will be cached either as an activity 15416 // or empty depending on whether the activity is finishing. We do 15417 // this so that we can treat the process as cached for purposes of 15418 // memory trimming (determing current memory level, trim command to 15419 // send to process) since there can be an arbitrary number of stopping 15420 // processes and they should soon all go into the cached state. 15421 if (!r.finishing) { 15422 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15423 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 15424 } 15425 } 15426 app.cached = false; 15427 app.empty = false; 15428 foregroundActivities = true; 15429 } else { 15430 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15431 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 15432 app.adjType = "cch-act"; 15433 } 15434 } 15435 } 15436 } 15437 15438 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15439 if (app.foregroundServices) { 15440 // The user is aware of this app, so make it visible. 15441 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15442 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15443 app.cached = false; 15444 app.adjType = "fg-service"; 15445 schedGroup = Process.THREAD_GROUP_DEFAULT; 15446 } else if (app.forcingToForeground != null) { 15447 // The user is aware of this app, so make it visible. 15448 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15449 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15450 app.cached = false; 15451 app.adjType = "force-fg"; 15452 app.adjSource = app.forcingToForeground; 15453 schedGroup = Process.THREAD_GROUP_DEFAULT; 15454 } 15455 } 15456 15457 if (app == mHeavyWeightProcess) { 15458 if (adj > ProcessList.HEAVY_WEIGHT_APP_ADJ) { 15459 // We don't want to kill the current heavy-weight process. 15460 adj = ProcessList.HEAVY_WEIGHT_APP_ADJ; 15461 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15462 app.cached = false; 15463 app.adjType = "heavy"; 15464 } 15465 if (procState > ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 15466 procState = ActivityManager.PROCESS_STATE_HEAVY_WEIGHT; 15467 } 15468 } 15469 15470 if (app == mHomeProcess) { 15471 if (adj > ProcessList.HOME_APP_ADJ) { 15472 // This process is hosting what we currently consider to be the 15473 // home app, so we don't want to let it go into the background. 15474 adj = ProcessList.HOME_APP_ADJ; 15475 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15476 app.cached = false; 15477 app.adjType = "home"; 15478 } 15479 if (procState > ActivityManager.PROCESS_STATE_HOME) { 15480 procState = ActivityManager.PROCESS_STATE_HOME; 15481 } 15482 } 15483 15484 if (app == mPreviousProcess && app.activities.size() > 0) { 15485 if (adj > ProcessList.PREVIOUS_APP_ADJ) { 15486 // This was the previous process that showed UI to the user. 15487 // We want to try to keep it around more aggressively, to give 15488 // a good experience around switching between two apps. 15489 adj = ProcessList.PREVIOUS_APP_ADJ; 15490 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15491 app.cached = false; 15492 app.adjType = "previous"; 15493 } 15494 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 15495 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 15496 } 15497 } 15498 15499 if (false) Slog.i(TAG, "OOM " + app + ": initial adj=" + adj 15500 + " reason=" + app.adjType); 15501 15502 // By default, we use the computed adjustment. It may be changed if 15503 // there are applications dependent on our services or providers, but 15504 // this gives us a baseline and makes sure we don't get into an 15505 // infinite recursion. 15506 app.adjSeq = mAdjSeq; 15507 app.curRawAdj = adj; 15508 app.hasStartedServices = false; 15509 15510 if (mBackupTarget != null && app == mBackupTarget.app) { 15511 // If possible we want to avoid killing apps while they're being backed up 15512 if (adj > ProcessList.BACKUP_APP_ADJ) { 15513 if (DEBUG_BACKUP) Slog.v(TAG, "oom BACKUP_APP_ADJ for " + app); 15514 adj = ProcessList.BACKUP_APP_ADJ; 15515 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 15516 procState = ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 15517 } 15518 app.adjType = "backup"; 15519 app.cached = false; 15520 } 15521 if (procState > ActivityManager.PROCESS_STATE_BACKUP) { 15522 procState = ActivityManager.PROCESS_STATE_BACKUP; 15523 } 15524 } 15525 15526 boolean mayBeTop = false; 15527 15528 for (int is = app.services.size()-1; 15529 is >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15530 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15531 || procState > ActivityManager.PROCESS_STATE_TOP); 15532 is--) { 15533 ServiceRecord s = app.services.valueAt(is); 15534 if (s.startRequested) { 15535 app.hasStartedServices = true; 15536 if (procState > ActivityManager.PROCESS_STATE_SERVICE) { 15537 procState = ActivityManager.PROCESS_STATE_SERVICE; 15538 } 15539 if (app.hasShownUi && app != mHomeProcess) { 15540 // If this process has shown some UI, let it immediately 15541 // go to the LRU list because it may be pretty heavy with 15542 // UI stuff. We'll tag it with a label just to help 15543 // debug and understand what is going on. 15544 if (adj > ProcessList.SERVICE_ADJ) { 15545 app.adjType = "cch-started-ui-services"; 15546 } 15547 } else { 15548 if (now < (s.lastActivity + ActiveServices.MAX_SERVICE_INACTIVITY)) { 15549 // This service has seen some activity within 15550 // recent memory, so we will keep its process ahead 15551 // of the background processes. 15552 if (adj > ProcessList.SERVICE_ADJ) { 15553 adj = ProcessList.SERVICE_ADJ; 15554 app.adjType = "started-services"; 15555 app.cached = false; 15556 } 15557 } 15558 // If we have let the service slide into the background 15559 // state, still have some text describing what it is doing 15560 // even though the service no longer has an impact. 15561 if (adj > ProcessList.SERVICE_ADJ) { 15562 app.adjType = "cch-started-services"; 15563 } 15564 } 15565 } 15566 for (int conni = s.connections.size()-1; 15567 conni >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15568 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15569 || procState > ActivityManager.PROCESS_STATE_TOP); 15570 conni--) { 15571 ArrayList<ConnectionRecord> clist = s.connections.valueAt(conni); 15572 for (int i = 0; 15573 i < clist.size() && (adj > ProcessList.FOREGROUND_APP_ADJ 15574 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15575 || procState > ActivityManager.PROCESS_STATE_TOP); 15576 i++) { 15577 // XXX should compute this based on the max of 15578 // all connected clients. 15579 ConnectionRecord cr = clist.get(i); 15580 if (cr.binding.client == app) { 15581 // Binding to ourself is not interesting. 15582 continue; 15583 } 15584 if ((cr.flags&Context.BIND_WAIVE_PRIORITY) == 0) { 15585 ProcessRecord client = cr.binding.client; 15586 int clientAdj = computeOomAdjLocked(client, cachedAdj, 15587 TOP_APP, doingAll, now); 15588 int clientProcState = client.curProcState; 15589 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15590 // If the other app is cached for any reason, for purposes here 15591 // we are going to consider it empty. The specific cached state 15592 // doesn't propagate except under certain conditions. 15593 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15594 } 15595 String adjType = null; 15596 if ((cr.flags&Context.BIND_ALLOW_OOM_MANAGEMENT) != 0) { 15597 // Not doing bind OOM management, so treat 15598 // this guy more like a started service. 15599 if (app.hasShownUi && app != mHomeProcess) { 15600 // If this process has shown some UI, let it immediately 15601 // go to the LRU list because it may be pretty heavy with 15602 // UI stuff. We'll tag it with a label just to help 15603 // debug and understand what is going on. 15604 if (adj > clientAdj) { 15605 adjType = "cch-bound-ui-services"; 15606 } 15607 app.cached = false; 15608 clientAdj = adj; 15609 clientProcState = procState; 15610 } else { 15611 if (now >= (s.lastActivity 15612 + ActiveServices.MAX_SERVICE_INACTIVITY)) { 15613 // This service has not seen activity within 15614 // recent memory, so allow it to drop to the 15615 // LRU list if there is no other reason to keep 15616 // it around. We'll also tag it with a label just 15617 // to help debug and undertand what is going on. 15618 if (adj > clientAdj) { 15619 adjType = "cch-bound-services"; 15620 } 15621 clientAdj = adj; 15622 } 15623 } 15624 } 15625 if (adj > clientAdj) { 15626 // If this process has recently shown UI, and 15627 // the process that is binding to it is less 15628 // important than being visible, then we don't 15629 // care about the binding as much as we care 15630 // about letting this process get into the LRU 15631 // list to be killed and restarted if needed for 15632 // memory. 15633 if (app.hasShownUi && app != mHomeProcess 15634 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15635 adjType = "cch-bound-ui-services"; 15636 } else { 15637 if ((cr.flags&(Context.BIND_ABOVE_CLIENT 15638 |Context.BIND_IMPORTANT)) != 0) { 15639 adj = clientAdj; 15640 } else if ((cr.flags&Context.BIND_NOT_VISIBLE) != 0 15641 && clientAdj < ProcessList.PERCEPTIBLE_APP_ADJ 15642 && adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15643 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15644 } else if (clientAdj > ProcessList.VISIBLE_APP_ADJ) { 15645 adj = clientAdj; 15646 } else { 15647 if (adj > ProcessList.VISIBLE_APP_ADJ) { 15648 adj = ProcessList.VISIBLE_APP_ADJ; 15649 } 15650 } 15651 if (!client.cached) { 15652 app.cached = false; 15653 } 15654 adjType = "service"; 15655 } 15656 } 15657 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 15658 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 15659 schedGroup = Process.THREAD_GROUP_DEFAULT; 15660 } 15661 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 15662 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 15663 // Special handling of clients who are in the top state. 15664 // We *may* want to consider this process to be in the 15665 // top state as well, but only if there is not another 15666 // reason for it to be running. Being on the top is a 15667 // special state, meaning you are specifically running 15668 // for the current top app. If the process is already 15669 // running in the background for some other reason, it 15670 // is more important to continue considering it to be 15671 // in the background state. 15672 mayBeTop = true; 15673 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15674 } else { 15675 // Special handling for above-top states (persistent 15676 // processes). These should not bring the current process 15677 // into the top state, since they are not on top. Instead 15678 // give them the best state after that. 15679 clientProcState = 15680 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15681 } 15682 } 15683 } else { 15684 if (clientProcState < 15685 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 15686 clientProcState = 15687 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 15688 } 15689 } 15690 if (procState > clientProcState) { 15691 procState = clientProcState; 15692 } 15693 if (procState < ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 15694 && (cr.flags&Context.BIND_SHOWING_UI) != 0) { 15695 app.pendingUiClean = true; 15696 } 15697 if (adjType != null) { 15698 app.adjType = adjType; 15699 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15700 .REASON_SERVICE_IN_USE; 15701 app.adjSource = cr.binding.client; 15702 app.adjSourceProcState = clientProcState; 15703 app.adjTarget = s.name; 15704 } 15705 } 15706 if ((cr.flags&Context.BIND_TREAT_LIKE_ACTIVITY) != 0) { 15707 app.treatLikeActivity = true; 15708 } 15709 final ActivityRecord a = cr.activity; 15710 if ((cr.flags&Context.BIND_ADJUST_WITH_ACTIVITY) != 0) { 15711 if (a != null && adj > ProcessList.FOREGROUND_APP_ADJ && 15712 (a.visible || a.state == ActivityState.RESUMED 15713 || a.state == ActivityState.PAUSING)) { 15714 adj = ProcessList.FOREGROUND_APP_ADJ; 15715 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 15716 schedGroup = Process.THREAD_GROUP_DEFAULT; 15717 } 15718 app.cached = false; 15719 app.adjType = "service"; 15720 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15721 .REASON_SERVICE_IN_USE; 15722 app.adjSource = a; 15723 app.adjSourceProcState = procState; 15724 app.adjTarget = s.name; 15725 } 15726 } 15727 } 15728 } 15729 } 15730 15731 for (int provi = app.pubProviders.size()-1; 15732 provi >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15733 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15734 || procState > ActivityManager.PROCESS_STATE_TOP); 15735 provi--) { 15736 ContentProviderRecord cpr = app.pubProviders.valueAt(provi); 15737 for (int i = cpr.connections.size()-1; 15738 i >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15739 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15740 || procState > ActivityManager.PROCESS_STATE_TOP); 15741 i--) { 15742 ContentProviderConnection conn = cpr.connections.get(i); 15743 ProcessRecord client = conn.client; 15744 if (client == app) { 15745 // Being our own client is not interesting. 15746 continue; 15747 } 15748 int clientAdj = computeOomAdjLocked(client, cachedAdj, TOP_APP, doingAll, now); 15749 int clientProcState = client.curProcState; 15750 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15751 // If the other app is cached for any reason, for purposes here 15752 // we are going to consider it empty. 15753 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15754 } 15755 if (adj > clientAdj) { 15756 if (app.hasShownUi && app != mHomeProcess 15757 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15758 app.adjType = "cch-ui-provider"; 15759 } else { 15760 adj = clientAdj > ProcessList.FOREGROUND_APP_ADJ 15761 ? clientAdj : ProcessList.FOREGROUND_APP_ADJ; 15762 app.adjType = "provider"; 15763 } 15764 app.cached &= client.cached; 15765 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15766 .REASON_PROVIDER_IN_USE; 15767 app.adjSource = client; 15768 app.adjSourceProcState = clientProcState; 15769 app.adjTarget = cpr.name; 15770 } 15771 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 15772 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 15773 // Special handling of clients who are in the top state. 15774 // We *may* want to consider this process to be in the 15775 // top state as well, but only if there is not another 15776 // reason for it to be running. Being on the top is a 15777 // special state, meaning you are specifically running 15778 // for the current top app. If the process is already 15779 // running in the background for some other reason, it 15780 // is more important to continue considering it to be 15781 // in the background state. 15782 mayBeTop = true; 15783 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15784 } else { 15785 // Special handling for above-top states (persistent 15786 // processes). These should not bring the current process 15787 // into the top state, since they are not on top. Instead 15788 // give them the best state after that. 15789 clientProcState = 15790 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15791 } 15792 } 15793 if (procState > clientProcState) { 15794 procState = clientProcState; 15795 } 15796 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 15797 schedGroup = Process.THREAD_GROUP_DEFAULT; 15798 } 15799 } 15800 // If the provider has external (non-framework) process 15801 // dependencies, ensure that its adjustment is at least 15802 // FOREGROUND_APP_ADJ. 15803 if (cpr.hasExternalProcessHandles()) { 15804 if (adj > ProcessList.FOREGROUND_APP_ADJ) { 15805 adj = ProcessList.FOREGROUND_APP_ADJ; 15806 schedGroup = Process.THREAD_GROUP_DEFAULT; 15807 app.cached = false; 15808 app.adjType = "provider"; 15809 app.adjTarget = cpr.name; 15810 } 15811 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) { 15812 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15813 } 15814 } 15815 } 15816 15817 if (mayBeTop && procState > ActivityManager.PROCESS_STATE_TOP) { 15818 // A client of one of our services or providers is in the top state. We 15819 // *may* want to be in the top state, but not if we are already running in 15820 // the background for some other reason. For the decision here, we are going 15821 // to pick out a few specific states that we want to remain in when a client 15822 // is top (states that tend to be longer-term) and otherwise allow it to go 15823 // to the top state. 15824 switch (procState) { 15825 case ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND: 15826 case ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND: 15827 case ActivityManager.PROCESS_STATE_SERVICE: 15828 // These all are longer-term states, so pull them up to the top 15829 // of the background states, but not all the way to the top state. 15830 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15831 break; 15832 default: 15833 // Otherwise, top is a better choice, so take it. 15834 procState = ActivityManager.PROCESS_STATE_TOP; 15835 break; 15836 } 15837 } 15838 15839 if (procState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 15840 if (app.hasClientActivities) { 15841 // This is a cached process, but with client activities. Mark it so. 15842 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT; 15843 app.adjType = "cch-client-act"; 15844 } else if (app.treatLikeActivity) { 15845 // This is a cached process, but somebody wants us to treat it like it has 15846 // an activity, okay! 15847 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 15848 app.adjType = "cch-as-act"; 15849 } 15850 } 15851 15852 if (adj == ProcessList.SERVICE_ADJ) { 15853 if (doingAll) { 15854 app.serviceb = mNewNumAServiceProcs > (mNumServiceProcs/3); 15855 mNewNumServiceProcs++; 15856 //Slog.i(TAG, "ADJ " + app + " serviceb=" + app.serviceb); 15857 if (!app.serviceb) { 15858 // This service isn't far enough down on the LRU list to 15859 // normally be a B service, but if we are low on RAM and it 15860 // is large we want to force it down since we would prefer to 15861 // keep launcher over it. 15862 if (mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 15863 && app.lastPss >= mProcessList.getCachedRestoreThresholdKb()) { 15864 app.serviceHighRam = true; 15865 app.serviceb = true; 15866 //Slog.i(TAG, "ADJ " + app + " high ram!"); 15867 } else { 15868 mNewNumAServiceProcs++; 15869 //Slog.i(TAG, "ADJ " + app + " not high ram!"); 15870 } 15871 } else { 15872 app.serviceHighRam = false; 15873 } 15874 } 15875 if (app.serviceb) { 15876 adj = ProcessList.SERVICE_B_ADJ; 15877 } 15878 } 15879 15880 app.curRawAdj = adj; 15881 15882 //Slog.i(TAG, "OOM ADJ " + app + ": pid=" + app.pid + 15883 // " adj=" + adj + " curAdj=" + app.curAdj + " maxAdj=" + app.maxAdj); 15884 if (adj > app.maxAdj) { 15885 adj = app.maxAdj; 15886 if (app.maxAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 15887 schedGroup = Process.THREAD_GROUP_DEFAULT; 15888 } 15889 } 15890 15891 // Do final modification to adj. Everything we do between here and applying 15892 // the final setAdj must be done in this function, because we will also use 15893 // it when computing the final cached adj later. Note that we don't need to 15894 // worry about this for max adj above, since max adj will always be used to 15895 // keep it out of the cached vaues. 15896 app.curAdj = app.modifyRawOomAdj(adj); 15897 app.curSchedGroup = schedGroup; 15898 app.curProcState = procState; 15899 app.foregroundActivities = foregroundActivities; 15900 15901 return app.curRawAdj; 15902 } 15903 15904 /** 15905 * Schedule PSS collection of a process. 15906 */ 15907 void requestPssLocked(ProcessRecord proc, int procState) { 15908 if (mPendingPssProcesses.contains(proc)) { 15909 return; 15910 } 15911 if (mPendingPssProcesses.size() == 0) { 15912 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 15913 } 15914 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of: " + proc); 15915 proc.pssProcState = procState; 15916 mPendingPssProcesses.add(proc); 15917 } 15918 15919 /** 15920 * Schedule PSS collection of all processes. 15921 */ 15922 void requestPssAllProcsLocked(long now, boolean always, boolean memLowered) { 15923 if (!always) { 15924 if (now < (mLastFullPssTime + 15925 (memLowered ? FULL_PSS_LOWERED_INTERVAL : FULL_PSS_MIN_INTERVAL))) { 15926 return; 15927 } 15928 } 15929 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of all procs! memLowered=" + memLowered); 15930 mLastFullPssTime = now; 15931 mFullPssPending = true; 15932 mPendingPssProcesses.ensureCapacity(mLruProcesses.size()); 15933 mPendingPssProcesses.clear(); 15934 for (int i=mLruProcesses.size()-1; i>=0; i--) { 15935 ProcessRecord app = mLruProcesses.get(i); 15936 if (memLowered || now > (app.lastStateTime+ProcessList.PSS_ALL_INTERVAL)) { 15937 app.pssProcState = app.setProcState; 15938 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 15939 isSleeping(), now); 15940 mPendingPssProcesses.add(app); 15941 } 15942 } 15943 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 15944 } 15945 15946 /** 15947 * Ask a given process to GC right now. 15948 */ 15949 final void performAppGcLocked(ProcessRecord app) { 15950 try { 15951 app.lastRequestedGc = SystemClock.uptimeMillis(); 15952 if (app.thread != null) { 15953 if (app.reportLowMemory) { 15954 app.reportLowMemory = false; 15955 app.thread.scheduleLowMemory(); 15956 } else { 15957 app.thread.processInBackground(); 15958 } 15959 } 15960 } catch (Exception e) { 15961 // whatever. 15962 } 15963 } 15964 15965 /** 15966 * Returns true if things are idle enough to perform GCs. 15967 */ 15968 private final boolean canGcNowLocked() { 15969 boolean processingBroadcasts = false; 15970 for (BroadcastQueue q : mBroadcastQueues) { 15971 if (q.mParallelBroadcasts.size() != 0 || q.mOrderedBroadcasts.size() != 0) { 15972 processingBroadcasts = true; 15973 } 15974 } 15975 return !processingBroadcasts 15976 && (isSleeping() || mStackSupervisor.allResumedActivitiesIdle()); 15977 } 15978 15979 /** 15980 * Perform GCs on all processes that are waiting for it, but only 15981 * if things are idle. 15982 */ 15983 final void performAppGcsLocked() { 15984 final int N = mProcessesToGc.size(); 15985 if (N <= 0) { 15986 return; 15987 } 15988 if (canGcNowLocked()) { 15989 while (mProcessesToGc.size() > 0) { 15990 ProcessRecord proc = mProcessesToGc.remove(0); 15991 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ || proc.reportLowMemory) { 15992 if ((proc.lastRequestedGc+GC_MIN_INTERVAL) 15993 <= SystemClock.uptimeMillis()) { 15994 // To avoid spamming the system, we will GC processes one 15995 // at a time, waiting a few seconds between each. 15996 performAppGcLocked(proc); 15997 scheduleAppGcsLocked(); 15998 return; 15999 } else { 16000 // It hasn't been long enough since we last GCed this 16001 // process... put it in the list to wait for its time. 16002 addProcessToGcListLocked(proc); 16003 break; 16004 } 16005 } 16006 } 16007 16008 scheduleAppGcsLocked(); 16009 } 16010 } 16011 16012 /** 16013 * If all looks good, perform GCs on all processes waiting for them. 16014 */ 16015 final void performAppGcsIfAppropriateLocked() { 16016 if (canGcNowLocked()) { 16017 performAppGcsLocked(); 16018 return; 16019 } 16020 // Still not idle, wait some more. 16021 scheduleAppGcsLocked(); 16022 } 16023 16024 /** 16025 * Schedule the execution of all pending app GCs. 16026 */ 16027 final void scheduleAppGcsLocked() { 16028 mHandler.removeMessages(GC_BACKGROUND_PROCESSES_MSG); 16029 16030 if (mProcessesToGc.size() > 0) { 16031 // Schedule a GC for the time to the next process. 16032 ProcessRecord proc = mProcessesToGc.get(0); 16033 Message msg = mHandler.obtainMessage(GC_BACKGROUND_PROCESSES_MSG); 16034 16035 long when = proc.lastRequestedGc + GC_MIN_INTERVAL; 16036 long now = SystemClock.uptimeMillis(); 16037 if (when < (now+GC_TIMEOUT)) { 16038 when = now + GC_TIMEOUT; 16039 } 16040 mHandler.sendMessageAtTime(msg, when); 16041 } 16042 } 16043 16044 /** 16045 * Add a process to the array of processes waiting to be GCed. Keeps the 16046 * list in sorted order by the last GC time. The process can't already be 16047 * on the list. 16048 */ 16049 final void addProcessToGcListLocked(ProcessRecord proc) { 16050 boolean added = false; 16051 for (int i=mProcessesToGc.size()-1; i>=0; i--) { 16052 if (mProcessesToGc.get(i).lastRequestedGc < 16053 proc.lastRequestedGc) { 16054 added = true; 16055 mProcessesToGc.add(i+1, proc); 16056 break; 16057 } 16058 } 16059 if (!added) { 16060 mProcessesToGc.add(0, proc); 16061 } 16062 } 16063 16064 /** 16065 * Set up to ask a process to GC itself. This will either do it 16066 * immediately, or put it on the list of processes to gc the next 16067 * time things are idle. 16068 */ 16069 final void scheduleAppGcLocked(ProcessRecord app) { 16070 long now = SystemClock.uptimeMillis(); 16071 if ((app.lastRequestedGc+GC_MIN_INTERVAL) > now) { 16072 return; 16073 } 16074 if (!mProcessesToGc.contains(app)) { 16075 addProcessToGcListLocked(app); 16076 scheduleAppGcsLocked(); 16077 } 16078 } 16079 16080 final void checkExcessivePowerUsageLocked(boolean doKills) { 16081 updateCpuStatsNow(); 16082 16083 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 16084 boolean doWakeKills = doKills; 16085 boolean doCpuKills = doKills; 16086 if (mLastPowerCheckRealtime == 0) { 16087 doWakeKills = false; 16088 } 16089 if (mLastPowerCheckUptime == 0) { 16090 doCpuKills = false; 16091 } 16092 if (stats.isScreenOn()) { 16093 doWakeKills = false; 16094 } 16095 final long curRealtime = SystemClock.elapsedRealtime(); 16096 final long realtimeSince = curRealtime - mLastPowerCheckRealtime; 16097 final long curUptime = SystemClock.uptimeMillis(); 16098 final long uptimeSince = curUptime - mLastPowerCheckUptime; 16099 mLastPowerCheckRealtime = curRealtime; 16100 mLastPowerCheckUptime = curUptime; 16101 if (realtimeSince < WAKE_LOCK_MIN_CHECK_DURATION) { 16102 doWakeKills = false; 16103 } 16104 if (uptimeSince < CPU_MIN_CHECK_DURATION) { 16105 doCpuKills = false; 16106 } 16107 int i = mLruProcesses.size(); 16108 while (i > 0) { 16109 i--; 16110 ProcessRecord app = mLruProcesses.get(i); 16111 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 16112 long wtime; 16113 synchronized (stats) { 16114 wtime = stats.getProcessWakeTime(app.info.uid, 16115 app.pid, curRealtime); 16116 } 16117 long wtimeUsed = wtime - app.lastWakeTime; 16118 long cputimeUsed = app.curCpuTime - app.lastCpuTime; 16119 if (DEBUG_POWER) { 16120 StringBuilder sb = new StringBuilder(128); 16121 sb.append("Wake for "); 16122 app.toShortString(sb); 16123 sb.append(": over "); 16124 TimeUtils.formatDuration(realtimeSince, sb); 16125 sb.append(" used "); 16126 TimeUtils.formatDuration(wtimeUsed, sb); 16127 sb.append(" ("); 16128 sb.append((wtimeUsed*100)/realtimeSince); 16129 sb.append("%)"); 16130 Slog.i(TAG, sb.toString()); 16131 sb.setLength(0); 16132 sb.append("CPU for "); 16133 app.toShortString(sb); 16134 sb.append(": over "); 16135 TimeUtils.formatDuration(uptimeSince, sb); 16136 sb.append(" used "); 16137 TimeUtils.formatDuration(cputimeUsed, sb); 16138 sb.append(" ("); 16139 sb.append((cputimeUsed*100)/uptimeSince); 16140 sb.append("%)"); 16141 Slog.i(TAG, sb.toString()); 16142 } 16143 // If a process has held a wake lock for more 16144 // than 50% of the time during this period, 16145 // that sounds bad. Kill! 16146 if (doWakeKills && realtimeSince > 0 16147 && ((wtimeUsed*100)/realtimeSince) >= 50) { 16148 synchronized (stats) { 16149 stats.reportExcessiveWakeLocked(app.info.uid, app.processName, 16150 realtimeSince, wtimeUsed); 16151 } 16152 killUnneededProcessLocked(app, "excessive wake held " + wtimeUsed 16153 + " during " + realtimeSince); 16154 app.baseProcessTracker.reportExcessiveWake(app.pkgList); 16155 } else if (doCpuKills && uptimeSince > 0 16156 && ((cputimeUsed*100)/uptimeSince) >= 25) { 16157 synchronized (stats) { 16158 stats.reportExcessiveCpuLocked(app.info.uid, app.processName, 16159 uptimeSince, cputimeUsed); 16160 } 16161 killUnneededProcessLocked(app, "excessive cpu " + cputimeUsed 16162 + " during " + uptimeSince); 16163 app.baseProcessTracker.reportExcessiveCpu(app.pkgList); 16164 } else { 16165 app.lastWakeTime = wtime; 16166 app.lastCpuTime = app.curCpuTime; 16167 } 16168 } 16169 } 16170 } 16171 16172 private final boolean applyOomAdjLocked(ProcessRecord app, 16173 ProcessRecord TOP_APP, boolean doingAll, long now) { 16174 boolean success = true; 16175 16176 if (app.curRawAdj != app.setRawAdj) { 16177 app.setRawAdj = app.curRawAdj; 16178 } 16179 16180 int changes = 0; 16181 16182 if (app.curAdj != app.setAdj) { 16183 ProcessList.setOomAdj(app.pid, app.info.uid, app.curAdj); 16184 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v( 16185 TAG, "Set " + app.pid + " " + app.processName + 16186 " adj " + app.curAdj + ": " + app.adjType); 16187 app.setAdj = app.curAdj; 16188 } 16189 16190 if (app.setSchedGroup != app.curSchedGroup) { 16191 app.setSchedGroup = app.curSchedGroup; 16192 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16193 "Setting process group of " + app.processName 16194 + " to " + app.curSchedGroup); 16195 if (app.waitingToKill != null && 16196 app.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 16197 killUnneededProcessLocked(app, app.waitingToKill); 16198 success = false; 16199 } else { 16200 if (true) { 16201 long oldId = Binder.clearCallingIdentity(); 16202 try { 16203 Process.setProcessGroup(app.pid, app.curSchedGroup); 16204 } catch (Exception e) { 16205 Slog.w(TAG, "Failed setting process group of " + app.pid 16206 + " to " + app.curSchedGroup); 16207 e.printStackTrace(); 16208 } finally { 16209 Binder.restoreCallingIdentity(oldId); 16210 } 16211 } else { 16212 if (app.thread != null) { 16213 try { 16214 app.thread.setSchedulingGroup(app.curSchedGroup); 16215 } catch (RemoteException e) { 16216 } 16217 } 16218 } 16219 Process.setSwappiness(app.pid, 16220 app.curSchedGroup <= Process.THREAD_GROUP_BG_NONINTERACTIVE); 16221 } 16222 } 16223 if (app.repForegroundActivities != app.foregroundActivities) { 16224 app.repForegroundActivities = app.foregroundActivities; 16225 changes |= ProcessChangeItem.CHANGE_ACTIVITIES; 16226 } 16227 if (app.repProcState != app.curProcState) { 16228 app.repProcState = app.curProcState; 16229 changes |= ProcessChangeItem.CHANGE_PROCESS_STATE; 16230 if (app.thread != null) { 16231 try { 16232 if (false) { 16233 //RuntimeException h = new RuntimeException("here"); 16234 Slog.i(TAG, "Sending new process state " + app.repProcState 16235 + " to " + app /*, h*/); 16236 } 16237 app.thread.setProcessState(app.repProcState); 16238 } catch (RemoteException e) { 16239 } 16240 } 16241 } 16242 if (app.setProcState < 0 || ProcessList.procStatesDifferForMem(app.curProcState, 16243 app.setProcState)) { 16244 app.lastStateTime = now; 16245 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 16246 isSleeping(), now); 16247 if (DEBUG_PSS) Slog.d(TAG, "Process state change from " 16248 + ProcessList.makeProcStateString(app.setProcState) + " to " 16249 + ProcessList.makeProcStateString(app.curProcState) + " next pss in " 16250 + (app.nextPssTime-now) + ": " + app); 16251 } else { 16252 if (now > app.nextPssTime || (now > (app.lastPssTime+ProcessList.PSS_MAX_INTERVAL) 16253 && now > (app.lastStateTime+ProcessList.PSS_MIN_TIME_FROM_STATE_CHANGE))) { 16254 requestPssLocked(app, app.setProcState); 16255 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, false, 16256 isSleeping(), now); 16257 } else if (false && DEBUG_PSS) { 16258 Slog.d(TAG, "Not requesting PSS of " + app + ": next=" + (app.nextPssTime-now)); 16259 } 16260 } 16261 if (app.setProcState != app.curProcState) { 16262 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16263 "Proc state change of " + app.processName 16264 + " to " + app.curProcState); 16265 boolean setImportant = app.setProcState < ActivityManager.PROCESS_STATE_SERVICE; 16266 boolean curImportant = app.curProcState < ActivityManager.PROCESS_STATE_SERVICE; 16267 if (setImportant && !curImportant) { 16268 // This app is no longer something we consider important enough to allow to 16269 // use arbitrary amounts of battery power. Note 16270 // its current wake lock time to later know to kill it if 16271 // it is not behaving well. 16272 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 16273 synchronized (stats) { 16274 app.lastWakeTime = stats.getProcessWakeTime(app.info.uid, 16275 app.pid, SystemClock.elapsedRealtime()); 16276 } 16277 app.lastCpuTime = app.curCpuTime; 16278 16279 } 16280 app.setProcState = app.curProcState; 16281 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 16282 app.notCachedSinceIdle = false; 16283 } 16284 if (!doingAll) { 16285 setProcessTrackerStateLocked(app, mProcessStats.getMemFactorLocked(), now); 16286 } else { 16287 app.procStateChanged = true; 16288 } 16289 } 16290 16291 if (changes != 0) { 16292 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Changes in " + app + ": " + changes); 16293 int i = mPendingProcessChanges.size()-1; 16294 ProcessChangeItem item = null; 16295 while (i >= 0) { 16296 item = mPendingProcessChanges.get(i); 16297 if (item.pid == app.pid) { 16298 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Re-using existing item: " + item); 16299 break; 16300 } 16301 i--; 16302 } 16303 if (i < 0) { 16304 // No existing item in pending changes; need a new one. 16305 final int NA = mAvailProcessChanges.size(); 16306 if (NA > 0) { 16307 item = mAvailProcessChanges.remove(NA-1); 16308 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Retreiving available item: " + item); 16309 } else { 16310 item = new ProcessChangeItem(); 16311 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Allocating new item: " + item); 16312 } 16313 item.changes = 0; 16314 item.pid = app.pid; 16315 item.uid = app.info.uid; 16316 if (mPendingProcessChanges.size() == 0) { 16317 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, 16318 "*** Enqueueing dispatch processes changed!"); 16319 mHandler.obtainMessage(DISPATCH_PROCESSES_CHANGED).sendToTarget(); 16320 } 16321 mPendingProcessChanges.add(item); 16322 } 16323 item.changes |= changes; 16324 item.processState = app.repProcState; 16325 item.foregroundActivities = app.repForegroundActivities; 16326 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Item " 16327 + Integer.toHexString(System.identityHashCode(item)) 16328 + " " + app.toShortString() + ": changes=" + item.changes 16329 + " procState=" + item.processState 16330 + " foreground=" + item.foregroundActivities 16331 + " type=" + app.adjType + " source=" + app.adjSource 16332 + " target=" + app.adjTarget); 16333 } 16334 16335 return success; 16336 } 16337 16338 private final void setProcessTrackerStateLocked(ProcessRecord proc, int memFactor, long now) { 16339 if (proc.thread != null) { 16340 if (proc.baseProcessTracker != null) { 16341 proc.baseProcessTracker.setState(proc.repProcState, memFactor, now, proc.pkgList); 16342 } 16343 if (proc.repProcState >= 0) { 16344 mBatteryStatsService.noteProcessState(proc.processName, proc.info.uid, 16345 proc.repProcState); 16346 } 16347 } 16348 } 16349 16350 private final boolean updateOomAdjLocked(ProcessRecord app, int cachedAdj, 16351 ProcessRecord TOP_APP, boolean doingAll, long now) { 16352 if (app.thread == null) { 16353 return false; 16354 } 16355 16356 computeOomAdjLocked(app, cachedAdj, TOP_APP, doingAll, now); 16357 16358 return applyOomAdjLocked(app, TOP_APP, doingAll, now); 16359 } 16360 16361 final void updateProcessForegroundLocked(ProcessRecord proc, boolean isForeground, 16362 boolean oomAdj) { 16363 if (isForeground != proc.foregroundServices) { 16364 proc.foregroundServices = isForeground; 16365 ArrayList<ProcessRecord> curProcs = mForegroundPackages.get(proc.info.packageName, 16366 proc.info.uid); 16367 if (isForeground) { 16368 if (curProcs == null) { 16369 curProcs = new ArrayList<ProcessRecord>(); 16370 mForegroundPackages.put(proc.info.packageName, proc.info.uid, curProcs); 16371 } 16372 if (!curProcs.contains(proc)) { 16373 curProcs.add(proc); 16374 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_FOREGROUND_START, 16375 proc.info.packageName, proc.info.uid); 16376 } 16377 } else { 16378 if (curProcs != null) { 16379 if (curProcs.remove(proc)) { 16380 mBatteryStatsService.noteEvent( 16381 BatteryStats.HistoryItem.EVENT_FOREGROUND_FINISH, 16382 proc.info.packageName, proc.info.uid); 16383 if (curProcs.size() <= 0) { 16384 mForegroundPackages.remove(proc.info.packageName, proc.info.uid); 16385 } 16386 } 16387 } 16388 } 16389 if (oomAdj) { 16390 updateOomAdjLocked(); 16391 } 16392 } 16393 } 16394 16395 private final ActivityRecord resumedAppLocked() { 16396 ActivityRecord act = mStackSupervisor.resumedAppLocked(); 16397 String pkg; 16398 int uid; 16399 if (act != null) { 16400 pkg = act.packageName; 16401 uid = act.info.applicationInfo.uid; 16402 } else { 16403 pkg = null; 16404 uid = -1; 16405 } 16406 // Has the UID or resumed package name changed? 16407 if (uid != mCurResumedUid || (pkg != mCurResumedPackage 16408 && (pkg == null || !pkg.equals(mCurResumedPackage)))) { 16409 if (mCurResumedPackage != null) { 16410 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_FINISH, 16411 mCurResumedPackage, mCurResumedUid); 16412 } 16413 mCurResumedPackage = pkg; 16414 mCurResumedUid = uid; 16415 if (mCurResumedPackage != null) { 16416 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_START, 16417 mCurResumedPackage, mCurResumedUid); 16418 } 16419 } 16420 return act; 16421 } 16422 16423 final boolean updateOomAdjLocked(ProcessRecord app) { 16424 final ActivityRecord TOP_ACT = resumedAppLocked(); 16425 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 16426 final boolean wasCached = app.cached; 16427 16428 mAdjSeq++; 16429 16430 // This is the desired cached adjusment we want to tell it to use. 16431 // If our app is currently cached, we know it, and that is it. Otherwise, 16432 // we don't know it yet, and it needs to now be cached we will then 16433 // need to do a complete oom adj. 16434 final int cachedAdj = app.curRawAdj >= ProcessList.CACHED_APP_MIN_ADJ 16435 ? app.curRawAdj : ProcessList.UNKNOWN_ADJ; 16436 boolean success = updateOomAdjLocked(app, cachedAdj, TOP_APP, false, 16437 SystemClock.uptimeMillis()); 16438 if (wasCached != app.cached || app.curRawAdj == ProcessList.UNKNOWN_ADJ) { 16439 // Changed to/from cached state, so apps after it in the LRU 16440 // list may also be changed. 16441 updateOomAdjLocked(); 16442 } 16443 return success; 16444 } 16445 16446 final void updateOomAdjLocked() { 16447 final ActivityRecord TOP_ACT = resumedAppLocked(); 16448 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 16449 final long now = SystemClock.uptimeMillis(); 16450 final long oldTime = now - ProcessList.MAX_EMPTY_TIME; 16451 final int N = mLruProcesses.size(); 16452 16453 if (false) { 16454 RuntimeException e = new RuntimeException(); 16455 e.fillInStackTrace(); 16456 Slog.i(TAG, "updateOomAdj: top=" + TOP_ACT, e); 16457 } 16458 16459 mAdjSeq++; 16460 mNewNumServiceProcs = 0; 16461 mNewNumAServiceProcs = 0; 16462 16463 final int emptyProcessLimit; 16464 final int cachedProcessLimit; 16465 if (mProcessLimit <= 0) { 16466 emptyProcessLimit = cachedProcessLimit = 0; 16467 } else if (mProcessLimit == 1) { 16468 emptyProcessLimit = 1; 16469 cachedProcessLimit = 0; 16470 } else { 16471 emptyProcessLimit = ProcessList.computeEmptyProcessLimit(mProcessLimit); 16472 cachedProcessLimit = mProcessLimit - emptyProcessLimit; 16473 } 16474 16475 // Let's determine how many processes we have running vs. 16476 // how many slots we have for background processes; we may want 16477 // to put multiple processes in a slot of there are enough of 16478 // them. 16479 int numSlots = (ProcessList.CACHED_APP_MAX_ADJ 16480 - ProcessList.CACHED_APP_MIN_ADJ + 1) / 2; 16481 int numEmptyProcs = N - mNumNonCachedProcs - mNumCachedHiddenProcs; 16482 if (numEmptyProcs > cachedProcessLimit) { 16483 // If there are more empty processes than our limit on cached 16484 // processes, then use the cached process limit for the factor. 16485 // This ensures that the really old empty processes get pushed 16486 // down to the bottom, so if we are running low on memory we will 16487 // have a better chance at keeping around more cached processes 16488 // instead of a gazillion empty processes. 16489 numEmptyProcs = cachedProcessLimit; 16490 } 16491 int emptyFactor = numEmptyProcs/numSlots; 16492 if (emptyFactor < 1) emptyFactor = 1; 16493 int cachedFactor = (mNumCachedHiddenProcs > 0 ? mNumCachedHiddenProcs : 1)/numSlots; 16494 if (cachedFactor < 1) cachedFactor = 1; 16495 int stepCached = 0; 16496 int stepEmpty = 0; 16497 int numCached = 0; 16498 int numEmpty = 0; 16499 int numTrimming = 0; 16500 16501 mNumNonCachedProcs = 0; 16502 mNumCachedHiddenProcs = 0; 16503 16504 // First update the OOM adjustment for each of the 16505 // application processes based on their current state. 16506 int curCachedAdj = ProcessList.CACHED_APP_MIN_ADJ; 16507 int nextCachedAdj = curCachedAdj+1; 16508 int curEmptyAdj = ProcessList.CACHED_APP_MIN_ADJ; 16509 int nextEmptyAdj = curEmptyAdj+2; 16510 for (int i=N-1; i>=0; i--) { 16511 ProcessRecord app = mLruProcesses.get(i); 16512 if (!app.killedByAm && app.thread != null) { 16513 app.procStateChanged = false; 16514 computeOomAdjLocked(app, ProcessList.UNKNOWN_ADJ, TOP_APP, true, now); 16515 16516 // If we haven't yet assigned the final cached adj 16517 // to the process, do that now. 16518 if (app.curAdj >= ProcessList.UNKNOWN_ADJ) { 16519 switch (app.curProcState) { 16520 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 16521 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 16522 // This process is a cached process holding activities... 16523 // assign it the next cached value for that type, and then 16524 // step that cached level. 16525 app.curRawAdj = curCachedAdj; 16526 app.curAdj = app.modifyRawOomAdj(curCachedAdj); 16527 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning activity LRU #" + i 16528 + " adj: " + app.curAdj + " (curCachedAdj=" + curCachedAdj 16529 + ")"); 16530 if (curCachedAdj != nextCachedAdj) { 16531 stepCached++; 16532 if (stepCached >= cachedFactor) { 16533 stepCached = 0; 16534 curCachedAdj = nextCachedAdj; 16535 nextCachedAdj += 2; 16536 if (nextCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) { 16537 nextCachedAdj = ProcessList.CACHED_APP_MAX_ADJ; 16538 } 16539 } 16540 } 16541 break; 16542 default: 16543 // For everything else, assign next empty cached process 16544 // level and bump that up. Note that this means that 16545 // long-running services that have dropped down to the 16546 // cached level will be treated as empty (since their process 16547 // state is still as a service), which is what we want. 16548 app.curRawAdj = curEmptyAdj; 16549 app.curAdj = app.modifyRawOomAdj(curEmptyAdj); 16550 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning empty LRU #" + i 16551 + " adj: " + app.curAdj + " (curEmptyAdj=" + curEmptyAdj 16552 + ")"); 16553 if (curEmptyAdj != nextEmptyAdj) { 16554 stepEmpty++; 16555 if (stepEmpty >= emptyFactor) { 16556 stepEmpty = 0; 16557 curEmptyAdj = nextEmptyAdj; 16558 nextEmptyAdj += 2; 16559 if (nextEmptyAdj > ProcessList.CACHED_APP_MAX_ADJ) { 16560 nextEmptyAdj = ProcessList.CACHED_APP_MAX_ADJ; 16561 } 16562 } 16563 } 16564 break; 16565 } 16566 } 16567 16568 applyOomAdjLocked(app, TOP_APP, true, now); 16569 16570 // Count the number of process types. 16571 switch (app.curProcState) { 16572 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 16573 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 16574 mNumCachedHiddenProcs++; 16575 numCached++; 16576 if (numCached > cachedProcessLimit) { 16577 killUnneededProcessLocked(app, "cached #" + numCached); 16578 } 16579 break; 16580 case ActivityManager.PROCESS_STATE_CACHED_EMPTY: 16581 if (numEmpty > ProcessList.TRIM_EMPTY_APPS 16582 && app.lastActivityTime < oldTime) { 16583 killUnneededProcessLocked(app, "empty for " 16584 + ((oldTime + ProcessList.MAX_EMPTY_TIME - app.lastActivityTime) 16585 / 1000) + "s"); 16586 } else { 16587 numEmpty++; 16588 if (numEmpty > emptyProcessLimit) { 16589 killUnneededProcessLocked(app, "empty #" + numEmpty); 16590 } 16591 } 16592 break; 16593 default: 16594 mNumNonCachedProcs++; 16595 break; 16596 } 16597 16598 if (app.isolated && app.services.size() <= 0) { 16599 // If this is an isolated process, and there are no 16600 // services running in it, then the process is no longer 16601 // needed. We agressively kill these because we can by 16602 // definition not re-use the same process again, and it is 16603 // good to avoid having whatever code was running in them 16604 // left sitting around after no longer needed. 16605 killUnneededProcessLocked(app, "isolated not needed"); 16606 } 16607 16608 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 16609 && !app.killedByAm) { 16610 numTrimming++; 16611 } 16612 } 16613 } 16614 16615 mNumServiceProcs = mNewNumServiceProcs; 16616 16617 // Now determine the memory trimming level of background processes. 16618 // Unfortunately we need to start at the back of the list to do this 16619 // properly. We only do this if the number of background apps we 16620 // are managing to keep around is less than half the maximum we desire; 16621 // if we are keeping a good number around, we'll let them use whatever 16622 // memory they want. 16623 final int numCachedAndEmpty = numCached + numEmpty; 16624 int memFactor; 16625 if (numCached <= ProcessList.TRIM_CACHED_APPS 16626 && numEmpty <= ProcessList.TRIM_EMPTY_APPS) { 16627 if (numCachedAndEmpty <= ProcessList.TRIM_CRITICAL_THRESHOLD) { 16628 memFactor = ProcessStats.ADJ_MEM_FACTOR_CRITICAL; 16629 } else if (numCachedAndEmpty <= ProcessList.TRIM_LOW_THRESHOLD) { 16630 memFactor = ProcessStats.ADJ_MEM_FACTOR_LOW; 16631 } else { 16632 memFactor = ProcessStats.ADJ_MEM_FACTOR_MODERATE; 16633 } 16634 } else { 16635 memFactor = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 16636 } 16637 // We always allow the memory level to go up (better). We only allow it to go 16638 // down if we are in a state where that is allowed, *and* the total number of processes 16639 // has gone down since last time. 16640 if (DEBUG_OOM_ADJ) Slog.d(TAG, "oom: memFactor=" + memFactor + " last=" + mLastMemoryLevel 16641 + " allowLow=" + mAllowLowerMemLevel + " numProcs=" + mLruProcesses.size() 16642 + " last=" + mLastNumProcesses); 16643 if (memFactor > mLastMemoryLevel) { 16644 if (!mAllowLowerMemLevel || mLruProcesses.size() >= mLastNumProcesses) { 16645 memFactor = mLastMemoryLevel; 16646 if (DEBUG_OOM_ADJ) Slog.d(TAG, "Keeping last mem factor!"); 16647 } 16648 } 16649 mLastMemoryLevel = memFactor; 16650 mLastNumProcesses = mLruProcesses.size(); 16651 boolean allChanged = mProcessStats.setMemFactorLocked(memFactor, !isSleeping(), now); 16652 final int trackerMemFactor = mProcessStats.getMemFactorLocked(); 16653 if (memFactor != ProcessStats.ADJ_MEM_FACTOR_NORMAL) { 16654 if (mLowRamStartTime == 0) { 16655 mLowRamStartTime = now; 16656 } 16657 int step = 0; 16658 int fgTrimLevel; 16659 switch (memFactor) { 16660 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 16661 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_CRITICAL; 16662 break; 16663 case ProcessStats.ADJ_MEM_FACTOR_LOW: 16664 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_LOW; 16665 break; 16666 default: 16667 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_MODERATE; 16668 break; 16669 } 16670 int factor = numTrimming/3; 16671 int minFactor = 2; 16672 if (mHomeProcess != null) minFactor++; 16673 if (mPreviousProcess != null) minFactor++; 16674 if (factor < minFactor) factor = minFactor; 16675 int curLevel = ComponentCallbacks2.TRIM_MEMORY_COMPLETE; 16676 for (int i=N-1; i>=0; i--) { 16677 ProcessRecord app = mLruProcesses.get(i); 16678 if (allChanged || app.procStateChanged) { 16679 setProcessTrackerStateLocked(app, trackerMemFactor, now); 16680 app.procStateChanged = false; 16681 } 16682 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 16683 && !app.killedByAm) { 16684 if (app.trimMemoryLevel < curLevel && app.thread != null) { 16685 try { 16686 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16687 "Trimming memory of " + app.processName 16688 + " to " + curLevel); 16689 app.thread.scheduleTrimMemory(curLevel); 16690 } catch (RemoteException e) { 16691 } 16692 if (false) { 16693 // For now we won't do this; our memory trimming seems 16694 // to be good enough at this point that destroying 16695 // activities causes more harm than good. 16696 if (curLevel >= ComponentCallbacks2.TRIM_MEMORY_COMPLETE 16697 && app != mHomeProcess && app != mPreviousProcess) { 16698 // Need to do this on its own message because the stack may not 16699 // be in a consistent state at this point. 16700 // For these apps we will also finish their activities 16701 // to help them free memory. 16702 mStackSupervisor.scheduleDestroyAllActivities(app, "trim"); 16703 } 16704 } 16705 } 16706 app.trimMemoryLevel = curLevel; 16707 step++; 16708 if (step >= factor) { 16709 step = 0; 16710 switch (curLevel) { 16711 case ComponentCallbacks2.TRIM_MEMORY_COMPLETE: 16712 curLevel = ComponentCallbacks2.TRIM_MEMORY_MODERATE; 16713 break; 16714 case ComponentCallbacks2.TRIM_MEMORY_MODERATE: 16715 curLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 16716 break; 16717 } 16718 } 16719 } else if (app.curProcState == ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 16720 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_BACKGROUND 16721 && app.thread != null) { 16722 try { 16723 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16724 "Trimming memory of heavy-weight " + app.processName 16725 + " to " + ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 16726 app.thread.scheduleTrimMemory( 16727 ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 16728 } catch (RemoteException e) { 16729 } 16730 } 16731 app.trimMemoryLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 16732 } else { 16733 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 16734 || app.systemNoUi) && app.pendingUiClean) { 16735 // If this application is now in the background and it 16736 // had done UI, then give it the special trim level to 16737 // have it free UI resources. 16738 final int level = ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN; 16739 if (app.trimMemoryLevel < level && app.thread != null) { 16740 try { 16741 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16742 "Trimming memory of bg-ui " + app.processName 16743 + " to " + level); 16744 app.thread.scheduleTrimMemory(level); 16745 } catch (RemoteException e) { 16746 } 16747 } 16748 app.pendingUiClean = false; 16749 } 16750 if (app.trimMemoryLevel < fgTrimLevel && app.thread != null) { 16751 try { 16752 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16753 "Trimming memory of fg " + app.processName 16754 + " to " + fgTrimLevel); 16755 app.thread.scheduleTrimMemory(fgTrimLevel); 16756 } catch (RemoteException e) { 16757 } 16758 } 16759 app.trimMemoryLevel = fgTrimLevel; 16760 } 16761 } 16762 } else { 16763 if (mLowRamStartTime != 0) { 16764 mLowRamTimeSinceLastIdle += now - mLowRamStartTime; 16765 mLowRamStartTime = 0; 16766 } 16767 for (int i=N-1; i>=0; i--) { 16768 ProcessRecord app = mLruProcesses.get(i); 16769 if (allChanged || app.procStateChanged) { 16770 setProcessTrackerStateLocked(app, trackerMemFactor, now); 16771 app.procStateChanged = false; 16772 } 16773 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 16774 || app.systemNoUi) && app.pendingUiClean) { 16775 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN 16776 && app.thread != null) { 16777 try { 16778 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16779 "Trimming memory of ui hidden " + app.processName 16780 + " to " + ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 16781 app.thread.scheduleTrimMemory( 16782 ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 16783 } catch (RemoteException e) { 16784 } 16785 } 16786 app.pendingUiClean = false; 16787 } 16788 app.trimMemoryLevel = 0; 16789 } 16790 } 16791 16792 if (mAlwaysFinishActivities) { 16793 // Need to do this on its own message because the stack may not 16794 // be in a consistent state at this point. 16795 mStackSupervisor.scheduleDestroyAllActivities(null, "always-finish"); 16796 } 16797 16798 if (allChanged) { 16799 requestPssAllProcsLocked(now, false, mProcessStats.isMemFactorLowered()); 16800 } 16801 16802 if (mProcessStats.shouldWriteNowLocked(now)) { 16803 mHandler.post(new Runnable() { 16804 @Override public void run() { 16805 synchronized (ActivityManagerService.this) { 16806 mProcessStats.writeStateAsyncLocked(); 16807 } 16808 } 16809 }); 16810 } 16811 16812 if (DEBUG_OOM_ADJ) { 16813 Slog.d(TAG, "Did OOM ADJ in " + (SystemClock.uptimeMillis()-now) + "ms"); 16814 } 16815 } 16816 16817 final void trimApplications() { 16818 synchronized (this) { 16819 int i; 16820 16821 // First remove any unused application processes whose package 16822 // has been removed. 16823 for (i=mRemovedProcesses.size()-1; i>=0; i--) { 16824 final ProcessRecord app = mRemovedProcesses.get(i); 16825 if (app.activities.size() == 0 16826 && app.curReceiver == null && app.services.size() == 0) { 16827 Slog.i( 16828 TAG, "Exiting empty application process " 16829 + app.processName + " (" 16830 + (app.thread != null ? app.thread.asBinder() : null) 16831 + ")\n"); 16832 if (app.pid > 0 && app.pid != MY_PID) { 16833 EventLog.writeEvent(EventLogTags.AM_KILL, app.userId, app.pid, 16834 app.processName, app.setAdj, "empty"); 16835 app.killedByAm = true; 16836 Process.killProcessQuiet(app.pid); 16837 Process.killProcessGroup(app.info.uid, app.pid); 16838 } else { 16839 try { 16840 app.thread.scheduleExit(); 16841 } catch (Exception e) { 16842 // Ignore exceptions. 16843 } 16844 } 16845 cleanUpApplicationRecordLocked(app, false, true, -1); 16846 mRemovedProcesses.remove(i); 16847 16848 if (app.persistent) { 16849 addAppLocked(app.info, false, null /* ABI override */); 16850 } 16851 } 16852 } 16853 16854 // Now update the oom adj for all processes. 16855 updateOomAdjLocked(); 16856 } 16857 } 16858 16859 /** This method sends the specified signal to each of the persistent apps */ 16860 public void signalPersistentProcesses(int sig) throws RemoteException { 16861 if (sig != Process.SIGNAL_USR1) { 16862 throw new SecurityException("Only SIGNAL_USR1 is allowed"); 16863 } 16864 16865 synchronized (this) { 16866 if (checkCallingPermission(android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES) 16867 != PackageManager.PERMISSION_GRANTED) { 16868 throw new SecurityException("Requires permission " 16869 + android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES); 16870 } 16871 16872 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 16873 ProcessRecord r = mLruProcesses.get(i); 16874 if (r.thread != null && r.persistent) { 16875 Process.sendSignal(r.pid, sig); 16876 } 16877 } 16878 } 16879 } 16880 16881 private void stopProfilerLocked(ProcessRecord proc, String path, int profileType) { 16882 if (proc == null || proc == mProfileProc) { 16883 proc = mProfileProc; 16884 path = mProfileFile; 16885 profileType = mProfileType; 16886 clearProfilerLocked(); 16887 } 16888 if (proc == null) { 16889 return; 16890 } 16891 try { 16892 proc.thread.profilerControl(false, path, null, profileType); 16893 } catch (RemoteException e) { 16894 throw new IllegalStateException("Process disappeared"); 16895 } 16896 } 16897 16898 private void clearProfilerLocked() { 16899 if (mProfileFd != null) { 16900 try { 16901 mProfileFd.close(); 16902 } catch (IOException e) { 16903 } 16904 } 16905 mProfileApp = null; 16906 mProfileProc = null; 16907 mProfileFile = null; 16908 mProfileType = 0; 16909 mAutoStopProfiler = false; 16910 } 16911 16912 public boolean profileControl(String process, int userId, boolean start, 16913 String path, ParcelFileDescriptor fd, int profileType) throws RemoteException { 16914 16915 try { 16916 synchronized (this) { 16917 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 16918 // its own permission. 16919 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 16920 != PackageManager.PERMISSION_GRANTED) { 16921 throw new SecurityException("Requires permission " 16922 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 16923 } 16924 16925 if (start && fd == null) { 16926 throw new IllegalArgumentException("null fd"); 16927 } 16928 16929 ProcessRecord proc = null; 16930 if (process != null) { 16931 proc = findProcessLocked(process, userId, "profileControl"); 16932 } 16933 16934 if (start && (proc == null || proc.thread == null)) { 16935 throw new IllegalArgumentException("Unknown process: " + process); 16936 } 16937 16938 if (start) { 16939 stopProfilerLocked(null, null, 0); 16940 setProfileApp(proc.info, proc.processName, path, fd, false); 16941 mProfileProc = proc; 16942 mProfileType = profileType; 16943 try { 16944 fd = fd.dup(); 16945 } catch (IOException e) { 16946 fd = null; 16947 } 16948 proc.thread.profilerControl(start, path, fd, profileType); 16949 fd = null; 16950 mProfileFd = null; 16951 } else { 16952 stopProfilerLocked(proc, path, profileType); 16953 if (fd != null) { 16954 try { 16955 fd.close(); 16956 } catch (IOException e) { 16957 } 16958 } 16959 } 16960 16961 return true; 16962 } 16963 } catch (RemoteException e) { 16964 throw new IllegalStateException("Process disappeared"); 16965 } finally { 16966 if (fd != null) { 16967 try { 16968 fd.close(); 16969 } catch (IOException e) { 16970 } 16971 } 16972 } 16973 } 16974 16975 private ProcessRecord findProcessLocked(String process, int userId, String callName) { 16976 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 16977 userId, true, ALLOW_FULL_ONLY, callName, null); 16978 ProcessRecord proc = null; 16979 try { 16980 int pid = Integer.parseInt(process); 16981 synchronized (mPidsSelfLocked) { 16982 proc = mPidsSelfLocked.get(pid); 16983 } 16984 } catch (NumberFormatException e) { 16985 } 16986 16987 if (proc == null) { 16988 ArrayMap<String, SparseArray<ProcessRecord>> all 16989 = mProcessNames.getMap(); 16990 SparseArray<ProcessRecord> procs = all.get(process); 16991 if (procs != null && procs.size() > 0) { 16992 proc = procs.valueAt(0); 16993 if (userId != UserHandle.USER_ALL && proc.userId != userId) { 16994 for (int i=1; i<procs.size(); i++) { 16995 ProcessRecord thisProc = procs.valueAt(i); 16996 if (thisProc.userId == userId) { 16997 proc = thisProc; 16998 break; 16999 } 17000 } 17001 } 17002 } 17003 } 17004 17005 return proc; 17006 } 17007 17008 public boolean dumpHeap(String process, int userId, boolean managed, 17009 String path, ParcelFileDescriptor fd) throws RemoteException { 17010 17011 try { 17012 synchronized (this) { 17013 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 17014 // its own permission (same as profileControl). 17015 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 17016 != PackageManager.PERMISSION_GRANTED) { 17017 throw new SecurityException("Requires permission " 17018 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 17019 } 17020 17021 if (fd == null) { 17022 throw new IllegalArgumentException("null fd"); 17023 } 17024 17025 ProcessRecord proc = findProcessLocked(process, userId, "dumpHeap"); 17026 if (proc == null || proc.thread == null) { 17027 throw new IllegalArgumentException("Unknown process: " + process); 17028 } 17029 17030 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 17031 if (!isDebuggable) { 17032 if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 17033 throw new SecurityException("Process not debuggable: " + proc); 17034 } 17035 } 17036 17037 proc.thread.dumpHeap(managed, path, fd); 17038 fd = null; 17039 return true; 17040 } 17041 } catch (RemoteException e) { 17042 throw new IllegalStateException("Process disappeared"); 17043 } finally { 17044 if (fd != null) { 17045 try { 17046 fd.close(); 17047 } catch (IOException e) { 17048 } 17049 } 17050 } 17051 } 17052 17053 /** In this method we try to acquire our lock to make sure that we have not deadlocked */ 17054 public void monitor() { 17055 synchronized (this) { } 17056 } 17057 17058 void onCoreSettingsChange(Bundle settings) { 17059 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 17060 ProcessRecord processRecord = mLruProcesses.get(i); 17061 try { 17062 if (processRecord.thread != null) { 17063 processRecord.thread.setCoreSettings(settings); 17064 } 17065 } catch (RemoteException re) { 17066 /* ignore */ 17067 } 17068 } 17069 } 17070 17071 // Multi-user methods 17072 17073 /** 17074 * Start user, if its not already running, but don't bring it to foreground. 17075 */ 17076 @Override 17077 public boolean startUserInBackground(final int userId) { 17078 return startUser(userId, /* foreground */ false); 17079 } 17080 17081 /** 17082 * Refreshes the list of users related to the current user when either a 17083 * user switch happens or when a new related user is started in the 17084 * background. 17085 */ 17086 private void updateCurrentProfileIdsLocked() { 17087 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17088 mCurrentUserId, false /* enabledOnly */); 17089 int[] currentProfileIds = new int[profiles.size()]; // profiles will not be null 17090 for (int i = 0; i < currentProfileIds.length; i++) { 17091 currentProfileIds[i] = profiles.get(i).id; 17092 } 17093 mCurrentProfileIds = currentProfileIds; 17094 17095 synchronized (mUserProfileGroupIdsSelfLocked) { 17096 mUserProfileGroupIdsSelfLocked.clear(); 17097 final List<UserInfo> users = getUserManagerLocked().getUsers(false); 17098 for (int i = 0; i < users.size(); i++) { 17099 UserInfo user = users.get(i); 17100 if (user.profileGroupId != UserInfo.NO_PROFILE_GROUP_ID) { 17101 mUserProfileGroupIdsSelfLocked.put(user.id, user.profileGroupId); 17102 } 17103 } 17104 } 17105 } 17106 17107 private Set getProfileIdsLocked(int userId) { 17108 Set userIds = new HashSet<Integer>(); 17109 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17110 userId, false /* enabledOnly */); 17111 for (UserInfo user : profiles) { 17112 userIds.add(Integer.valueOf(user.id)); 17113 } 17114 return userIds; 17115 } 17116 17117 @Override 17118 public boolean switchUser(final int userId) { 17119 return startUser(userId, /* foregound */ true); 17120 } 17121 17122 private boolean startUser(final int userId, boolean foreground) { 17123 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17124 != PackageManager.PERMISSION_GRANTED) { 17125 String msg = "Permission Denial: switchUser() from pid=" 17126 + Binder.getCallingPid() 17127 + ", uid=" + Binder.getCallingUid() 17128 + " requires " + INTERACT_ACROSS_USERS_FULL; 17129 Slog.w(TAG, msg); 17130 throw new SecurityException(msg); 17131 } 17132 17133 if (DEBUG_MU) Slog.i(TAG_MU, "starting userid:" + userId + " fore:" + foreground); 17134 17135 final long ident = Binder.clearCallingIdentity(); 17136 try { 17137 synchronized (this) { 17138 final int oldUserId = mCurrentUserId; 17139 if (oldUserId == userId) { 17140 return true; 17141 } 17142 17143 mStackSupervisor.setLockTaskModeLocked(null, false); 17144 17145 final UserInfo userInfo = getUserManagerLocked().getUserInfo(userId); 17146 if (userInfo == null) { 17147 Slog.w(TAG, "No user info for user #" + userId); 17148 return false; 17149 } 17150 17151 if (foreground) { 17152 mWindowManager.startFreezingScreen(R.anim.screen_user_exit, 17153 R.anim.screen_user_enter); 17154 } 17155 17156 boolean needStart = false; 17157 17158 // If the user we are switching to is not currently started, then 17159 // we need to start it now. 17160 if (mStartedUsers.get(userId) == null) { 17161 mStartedUsers.put(userId, new UserStartedState(new UserHandle(userId), false)); 17162 updateStartedUserArrayLocked(); 17163 needStart = true; 17164 } 17165 17166 final Integer userIdInt = Integer.valueOf(userId); 17167 mUserLru.remove(userIdInt); 17168 mUserLru.add(userIdInt); 17169 17170 if (foreground) { 17171 mCurrentUserId = userId; 17172 updateCurrentProfileIdsLocked(); 17173 mWindowManager.setCurrentUser(userId, mCurrentProfileIds); 17174 // Once the internal notion of the active user has switched, we lock the device 17175 // with the option to show the user switcher on the keyguard. 17176 mWindowManager.lockNow(null); 17177 } else { 17178 final Integer currentUserIdInt = Integer.valueOf(mCurrentUserId); 17179 updateCurrentProfileIdsLocked(); 17180 mWindowManager.setCurrentProfileIds(mCurrentProfileIds); 17181 mUserLru.remove(currentUserIdInt); 17182 mUserLru.add(currentUserIdInt); 17183 } 17184 17185 final UserStartedState uss = mStartedUsers.get(userId); 17186 17187 // Make sure user is in the started state. If it is currently 17188 // stopping, we need to knock that off. 17189 if (uss.mState == UserStartedState.STATE_STOPPING) { 17190 // If we are stopping, we haven't sent ACTION_SHUTDOWN, 17191 // so we can just fairly silently bring the user back from 17192 // the almost-dead. 17193 uss.mState = UserStartedState.STATE_RUNNING; 17194 updateStartedUserArrayLocked(); 17195 needStart = true; 17196 } else if (uss.mState == UserStartedState.STATE_SHUTDOWN) { 17197 // This means ACTION_SHUTDOWN has been sent, so we will 17198 // need to treat this as a new boot of the user. 17199 uss.mState = UserStartedState.STATE_BOOTING; 17200 updateStartedUserArrayLocked(); 17201 needStart = true; 17202 } 17203 17204 if (uss.mState == UserStartedState.STATE_BOOTING) { 17205 // Booting up a new user, need to tell system services about it. 17206 // Note that this is on the same handler as scheduling of broadcasts, 17207 // which is important because it needs to go first. 17208 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_START_MSG, userId)); 17209 } 17210 17211 if (foreground) { 17212 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_CURRENT_MSG, userId, 17213 oldUserId)); 17214 mHandler.removeMessages(REPORT_USER_SWITCH_MSG); 17215 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 17216 mHandler.sendMessage(mHandler.obtainMessage(REPORT_USER_SWITCH_MSG, 17217 oldUserId, userId, uss)); 17218 mHandler.sendMessageDelayed(mHandler.obtainMessage(USER_SWITCH_TIMEOUT_MSG, 17219 oldUserId, userId, uss), USER_SWITCH_TIMEOUT); 17220 } 17221 17222 if (needStart) { 17223 // Send USER_STARTED broadcast 17224 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 17225 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 17226 | Intent.FLAG_RECEIVER_FOREGROUND); 17227 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17228 broadcastIntentLocked(null, null, intent, 17229 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 17230 false, false, MY_PID, Process.SYSTEM_UID, userId); 17231 } 17232 17233 if ((userInfo.flags&UserInfo.FLAG_INITIALIZED) == 0) { 17234 if (userId != UserHandle.USER_OWNER) { 17235 // Send PRE_BOOT_COMPLETED broadcasts for this new user 17236 final ArrayList<ComponentName> doneReceivers 17237 = new ArrayList<ComponentName>(); 17238 deliverPreBootCompleted(null, doneReceivers, userId); 17239 17240 Intent intent = new Intent(Intent.ACTION_USER_INITIALIZE); 17241 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 17242 broadcastIntentLocked(null, null, intent, null, 17243 new IIntentReceiver.Stub() { 17244 public void performReceive(Intent intent, int resultCode, 17245 String data, Bundle extras, boolean ordered, 17246 boolean sticky, int sendingUser) { 17247 userInitialized(uss, userId); 17248 } 17249 }, 0, null, null, null, AppOpsManager.OP_NONE, 17250 true, false, MY_PID, Process.SYSTEM_UID, 17251 userId); 17252 uss.initializing = true; 17253 } else { 17254 getUserManagerLocked().makeInitialized(userInfo.id); 17255 } 17256 } 17257 17258 if (foreground) { 17259 boolean homeInFront = mStackSupervisor.switchUserLocked(userId, uss); 17260 if (homeInFront) { 17261 startHomeActivityLocked(userId); 17262 } else { 17263 mStackSupervisor.resumeTopActivitiesLocked(); 17264 } 17265 EventLogTags.writeAmSwitchUser(userId); 17266 getUserManagerLocked().userForeground(userId); 17267 sendUserSwitchBroadcastsLocked(oldUserId, userId); 17268 } else { 17269 mStackSupervisor.startBackgroundUserLocked(userId, uss); 17270 } 17271 17272 if (needStart) { 17273 Intent intent = new Intent(Intent.ACTION_USER_STARTING); 17274 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 17275 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17276 broadcastIntentLocked(null, null, intent, 17277 null, new IIntentReceiver.Stub() { 17278 @Override 17279 public void performReceive(Intent intent, int resultCode, String data, 17280 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 17281 throws RemoteException { 17282 } 17283 }, 0, null, null, 17284 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 17285 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 17286 } 17287 } 17288 } finally { 17289 Binder.restoreCallingIdentity(ident); 17290 } 17291 17292 return true; 17293 } 17294 17295 void sendUserSwitchBroadcastsLocked(int oldUserId, int newUserId) { 17296 long ident = Binder.clearCallingIdentity(); 17297 try { 17298 Intent intent; 17299 if (oldUserId >= 0) { 17300 // Send USER_BACKGROUND broadcast to all profiles of the outgoing user 17301 List<UserInfo> profiles = mUserManager.getProfiles(oldUserId, false); 17302 int count = profiles.size(); 17303 for (int i = 0; i < count; i++) { 17304 int profileUserId = profiles.get(i).id; 17305 intent = new Intent(Intent.ACTION_USER_BACKGROUND); 17306 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 17307 | Intent.FLAG_RECEIVER_FOREGROUND); 17308 intent.putExtra(Intent.EXTRA_USER_HANDLE, profileUserId); 17309 broadcastIntentLocked(null, null, intent, 17310 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 17311 false, false, MY_PID, Process.SYSTEM_UID, profileUserId); 17312 } 17313 } 17314 if (newUserId >= 0) { 17315 // Send USER_FOREGROUND broadcast to all profiles of the incoming user 17316 List<UserInfo> profiles = mUserManager.getProfiles(newUserId, false); 17317 int count = profiles.size(); 17318 for (int i = 0; i < count; i++) { 17319 int profileUserId = profiles.get(i).id; 17320 intent = new Intent(Intent.ACTION_USER_FOREGROUND); 17321 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 17322 | Intent.FLAG_RECEIVER_FOREGROUND); 17323 intent.putExtra(Intent.EXTRA_USER_HANDLE, profileUserId); 17324 broadcastIntentLocked(null, null, intent, 17325 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 17326 false, false, MY_PID, Process.SYSTEM_UID, profileUserId); 17327 } 17328 intent = new Intent(Intent.ACTION_USER_SWITCHED); 17329 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 17330 | Intent.FLAG_RECEIVER_FOREGROUND); 17331 intent.putExtra(Intent.EXTRA_USER_HANDLE, newUserId); 17332 broadcastIntentLocked(null, null, intent, 17333 null, null, 0, null, null, 17334 android.Manifest.permission.MANAGE_USERS, AppOpsManager.OP_NONE, 17335 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 17336 } 17337 } finally { 17338 Binder.restoreCallingIdentity(ident); 17339 } 17340 } 17341 17342 void dispatchUserSwitch(final UserStartedState uss, final int oldUserId, 17343 final int newUserId) { 17344 final int N = mUserSwitchObservers.beginBroadcast(); 17345 if (N > 0) { 17346 final IRemoteCallback callback = new IRemoteCallback.Stub() { 17347 int mCount = 0; 17348 @Override 17349 public void sendResult(Bundle data) throws RemoteException { 17350 synchronized (ActivityManagerService.this) { 17351 if (mCurUserSwitchCallback == this) { 17352 mCount++; 17353 if (mCount == N) { 17354 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 17355 } 17356 } 17357 } 17358 } 17359 }; 17360 synchronized (this) { 17361 uss.switching = true; 17362 mCurUserSwitchCallback = callback; 17363 } 17364 for (int i=0; i<N; i++) { 17365 try { 17366 mUserSwitchObservers.getBroadcastItem(i).onUserSwitching( 17367 newUserId, callback); 17368 } catch (RemoteException e) { 17369 } 17370 } 17371 } else { 17372 synchronized (this) { 17373 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 17374 } 17375 } 17376 mUserSwitchObservers.finishBroadcast(); 17377 } 17378 17379 void timeoutUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 17380 synchronized (this) { 17381 Slog.w(TAG, "User switch timeout: from " + oldUserId + " to " + newUserId); 17382 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 17383 } 17384 } 17385 17386 void sendContinueUserSwitchLocked(UserStartedState uss, int oldUserId, int newUserId) { 17387 mCurUserSwitchCallback = null; 17388 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 17389 mHandler.sendMessage(mHandler.obtainMessage(CONTINUE_USER_SWITCH_MSG, 17390 oldUserId, newUserId, uss)); 17391 } 17392 17393 void userInitialized(UserStartedState uss, int newUserId) { 17394 completeSwitchAndInitalize(uss, newUserId, true, false); 17395 } 17396 17397 void continueUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 17398 completeSwitchAndInitalize(uss, newUserId, false, true); 17399 } 17400 17401 void completeSwitchAndInitalize(UserStartedState uss, int newUserId, 17402 boolean clearInitializing, boolean clearSwitching) { 17403 boolean unfrozen = false; 17404 synchronized (this) { 17405 if (clearInitializing) { 17406 uss.initializing = false; 17407 getUserManagerLocked().makeInitialized(uss.mHandle.getIdentifier()); 17408 } 17409 if (clearSwitching) { 17410 uss.switching = false; 17411 } 17412 if (!uss.switching && !uss.initializing) { 17413 mWindowManager.stopFreezingScreen(); 17414 unfrozen = true; 17415 } 17416 } 17417 if (unfrozen) { 17418 final int N = mUserSwitchObservers.beginBroadcast(); 17419 for (int i=0; i<N; i++) { 17420 try { 17421 mUserSwitchObservers.getBroadcastItem(i).onUserSwitchComplete(newUserId); 17422 } catch (RemoteException e) { 17423 } 17424 } 17425 mUserSwitchObservers.finishBroadcast(); 17426 } 17427 } 17428 17429 void scheduleStartProfilesLocked() { 17430 if (!mHandler.hasMessages(START_PROFILES_MSG)) { 17431 mHandler.sendMessageDelayed(mHandler.obtainMessage(START_PROFILES_MSG), 17432 DateUtils.SECOND_IN_MILLIS); 17433 } 17434 } 17435 17436 void startProfilesLocked() { 17437 if (DEBUG_MU) Slog.i(TAG_MU, "startProfilesLocked"); 17438 List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17439 mCurrentUserId, false /* enabledOnly */); 17440 List<UserInfo> toStart = new ArrayList<UserInfo>(profiles.size()); 17441 for (UserInfo user : profiles) { 17442 if ((user.flags & UserInfo.FLAG_INITIALIZED) == UserInfo.FLAG_INITIALIZED 17443 && user.id != mCurrentUserId) { 17444 toStart.add(user); 17445 } 17446 } 17447 final int n = toStart.size(); 17448 int i = 0; 17449 for (; i < n && i < (MAX_RUNNING_USERS - 1); ++i) { 17450 startUserInBackground(toStart.get(i).id); 17451 } 17452 if (i < n) { 17453 Slog.w(TAG_MU, "More profiles than MAX_RUNNING_USERS"); 17454 } 17455 } 17456 17457 void finishUserBoot(UserStartedState uss) { 17458 synchronized (this) { 17459 if (uss.mState == UserStartedState.STATE_BOOTING 17460 && mStartedUsers.get(uss.mHandle.getIdentifier()) == uss) { 17461 uss.mState = UserStartedState.STATE_RUNNING; 17462 final int userId = uss.mHandle.getIdentifier(); 17463 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 17464 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17465 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 17466 broadcastIntentLocked(null, null, intent, 17467 null, null, 0, null, null, 17468 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, AppOpsManager.OP_NONE, 17469 true, false, MY_PID, Process.SYSTEM_UID, userId); 17470 } 17471 } 17472 } 17473 17474 void finishUserSwitch(UserStartedState uss) { 17475 synchronized (this) { 17476 finishUserBoot(uss); 17477 17478 startProfilesLocked(); 17479 17480 int num = mUserLru.size(); 17481 int i = 0; 17482 while (num > MAX_RUNNING_USERS && i < mUserLru.size()) { 17483 Integer oldUserId = mUserLru.get(i); 17484 UserStartedState oldUss = mStartedUsers.get(oldUserId); 17485 if (oldUss == null) { 17486 // Shouldn't happen, but be sane if it does. 17487 mUserLru.remove(i); 17488 num--; 17489 continue; 17490 } 17491 if (oldUss.mState == UserStartedState.STATE_STOPPING 17492 || oldUss.mState == UserStartedState.STATE_SHUTDOWN) { 17493 // This user is already stopping, doesn't count. 17494 num--; 17495 i++; 17496 continue; 17497 } 17498 if (oldUserId == UserHandle.USER_OWNER || oldUserId == mCurrentUserId) { 17499 // Owner and current can't be stopped, but count as running. 17500 i++; 17501 continue; 17502 } 17503 // This is a user to be stopped. 17504 stopUserLocked(oldUserId, null); 17505 num--; 17506 i++; 17507 } 17508 } 17509 } 17510 17511 @Override 17512 public int stopUser(final int userId, final IStopUserCallback callback) { 17513 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17514 != PackageManager.PERMISSION_GRANTED) { 17515 String msg = "Permission Denial: switchUser() from pid=" 17516 + Binder.getCallingPid() 17517 + ", uid=" + Binder.getCallingUid() 17518 + " requires " + INTERACT_ACROSS_USERS_FULL; 17519 Slog.w(TAG, msg); 17520 throw new SecurityException(msg); 17521 } 17522 if (userId <= 0) { 17523 throw new IllegalArgumentException("Can't stop primary user " + userId); 17524 } 17525 synchronized (this) { 17526 return stopUserLocked(userId, callback); 17527 } 17528 } 17529 17530 private int stopUserLocked(final int userId, final IStopUserCallback callback) { 17531 if (DEBUG_MU) Slog.i(TAG_MU, "stopUserLocked userId=" + userId); 17532 if (mCurrentUserId == userId) { 17533 return ActivityManager.USER_OP_IS_CURRENT; 17534 } 17535 17536 final UserStartedState uss = mStartedUsers.get(userId); 17537 if (uss == null) { 17538 // User is not started, nothing to do... but we do need to 17539 // callback if requested. 17540 if (callback != null) { 17541 mHandler.post(new Runnable() { 17542 @Override 17543 public void run() { 17544 try { 17545 callback.userStopped(userId); 17546 } catch (RemoteException e) { 17547 } 17548 } 17549 }); 17550 } 17551 return ActivityManager.USER_OP_SUCCESS; 17552 } 17553 17554 if (callback != null) { 17555 uss.mStopCallbacks.add(callback); 17556 } 17557 17558 if (uss.mState != UserStartedState.STATE_STOPPING 17559 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17560 uss.mState = UserStartedState.STATE_STOPPING; 17561 updateStartedUserArrayLocked(); 17562 17563 long ident = Binder.clearCallingIdentity(); 17564 try { 17565 // We are going to broadcast ACTION_USER_STOPPING and then 17566 // once that is done send a final ACTION_SHUTDOWN and then 17567 // stop the user. 17568 final Intent stoppingIntent = new Intent(Intent.ACTION_USER_STOPPING); 17569 stoppingIntent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 17570 stoppingIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17571 stoppingIntent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 17572 final Intent shutdownIntent = new Intent(Intent.ACTION_SHUTDOWN); 17573 // This is the result receiver for the final shutdown broadcast. 17574 final IIntentReceiver shutdownReceiver = new IIntentReceiver.Stub() { 17575 @Override 17576 public void performReceive(Intent intent, int resultCode, String data, 17577 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 17578 finishUserStop(uss); 17579 } 17580 }; 17581 // This is the result receiver for the initial stopping broadcast. 17582 final IIntentReceiver stoppingReceiver = new IIntentReceiver.Stub() { 17583 @Override 17584 public void performReceive(Intent intent, int resultCode, String data, 17585 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 17586 // On to the next. 17587 synchronized (ActivityManagerService.this) { 17588 if (uss.mState != UserStartedState.STATE_STOPPING) { 17589 // Whoops, we are being started back up. Abort, abort! 17590 return; 17591 } 17592 uss.mState = UserStartedState.STATE_SHUTDOWN; 17593 } 17594 mBatteryStatsService.noteEvent( 17595 BatteryStats.HistoryItem.EVENT_USER_RUNNING_FINISH, 17596 Integer.toString(userId), userId); 17597 mSystemServiceManager.stopUser(userId); 17598 broadcastIntentLocked(null, null, shutdownIntent, 17599 null, shutdownReceiver, 0, null, null, null, AppOpsManager.OP_NONE, 17600 true, false, MY_PID, Process.SYSTEM_UID, userId); 17601 } 17602 }; 17603 // Kick things off. 17604 broadcastIntentLocked(null, null, stoppingIntent, 17605 null, stoppingReceiver, 0, null, null, 17606 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 17607 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 17608 } finally { 17609 Binder.restoreCallingIdentity(ident); 17610 } 17611 } 17612 17613 return ActivityManager.USER_OP_SUCCESS; 17614 } 17615 17616 void finishUserStop(UserStartedState uss) { 17617 final int userId = uss.mHandle.getIdentifier(); 17618 boolean stopped; 17619 ArrayList<IStopUserCallback> callbacks; 17620 synchronized (this) { 17621 callbacks = new ArrayList<IStopUserCallback>(uss.mStopCallbacks); 17622 if (mStartedUsers.get(userId) != uss) { 17623 stopped = false; 17624 } else if (uss.mState != UserStartedState.STATE_SHUTDOWN) { 17625 stopped = false; 17626 } else { 17627 stopped = true; 17628 // User can no longer run. 17629 mStartedUsers.remove(userId); 17630 mUserLru.remove(Integer.valueOf(userId)); 17631 updateStartedUserArrayLocked(); 17632 17633 // Clean up all state and processes associated with the user. 17634 // Kill all the processes for the user. 17635 forceStopUserLocked(userId, "finish user"); 17636 } 17637 } 17638 17639 for (int i=0; i<callbacks.size(); i++) { 17640 try { 17641 if (stopped) callbacks.get(i).userStopped(userId); 17642 else callbacks.get(i).userStopAborted(userId); 17643 } catch (RemoteException e) { 17644 } 17645 } 17646 17647 if (stopped) { 17648 mSystemServiceManager.cleanupUser(userId); 17649 synchronized (this) { 17650 mStackSupervisor.removeUserLocked(userId); 17651 } 17652 } 17653 } 17654 17655 @Override 17656 public UserInfo getCurrentUser() { 17657 if ((checkCallingPermission(INTERACT_ACROSS_USERS) 17658 != PackageManager.PERMISSION_GRANTED) && ( 17659 checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17660 != PackageManager.PERMISSION_GRANTED)) { 17661 String msg = "Permission Denial: getCurrentUser() from pid=" 17662 + Binder.getCallingPid() 17663 + ", uid=" + Binder.getCallingUid() 17664 + " requires " + INTERACT_ACROSS_USERS; 17665 Slog.w(TAG, msg); 17666 throw new SecurityException(msg); 17667 } 17668 synchronized (this) { 17669 return getUserManagerLocked().getUserInfo(mCurrentUserId); 17670 } 17671 } 17672 17673 int getCurrentUserIdLocked() { 17674 return mCurrentUserId; 17675 } 17676 17677 @Override 17678 public boolean isUserRunning(int userId, boolean orStopped) { 17679 if (checkCallingPermission(INTERACT_ACROSS_USERS) 17680 != PackageManager.PERMISSION_GRANTED) { 17681 String msg = "Permission Denial: isUserRunning() from pid=" 17682 + Binder.getCallingPid() 17683 + ", uid=" + Binder.getCallingUid() 17684 + " requires " + INTERACT_ACROSS_USERS; 17685 Slog.w(TAG, msg); 17686 throw new SecurityException(msg); 17687 } 17688 synchronized (this) { 17689 return isUserRunningLocked(userId, orStopped); 17690 } 17691 } 17692 17693 boolean isUserRunningLocked(int userId, boolean orStopped) { 17694 UserStartedState state = mStartedUsers.get(userId); 17695 if (state == null) { 17696 return false; 17697 } 17698 if (orStopped) { 17699 return true; 17700 } 17701 return state.mState != UserStartedState.STATE_STOPPING 17702 && state.mState != UserStartedState.STATE_SHUTDOWN; 17703 } 17704 17705 @Override 17706 public int[] getRunningUserIds() { 17707 if (checkCallingPermission(INTERACT_ACROSS_USERS) 17708 != PackageManager.PERMISSION_GRANTED) { 17709 String msg = "Permission Denial: isUserRunning() from pid=" 17710 + Binder.getCallingPid() 17711 + ", uid=" + Binder.getCallingUid() 17712 + " requires " + INTERACT_ACROSS_USERS; 17713 Slog.w(TAG, msg); 17714 throw new SecurityException(msg); 17715 } 17716 synchronized (this) { 17717 return mStartedUserArray; 17718 } 17719 } 17720 17721 private void updateStartedUserArrayLocked() { 17722 int num = 0; 17723 for (int i=0; i<mStartedUsers.size(); i++) { 17724 UserStartedState uss = mStartedUsers.valueAt(i); 17725 // This list does not include stopping users. 17726 if (uss.mState != UserStartedState.STATE_STOPPING 17727 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17728 num++; 17729 } 17730 } 17731 mStartedUserArray = new int[num]; 17732 num = 0; 17733 for (int i=0; i<mStartedUsers.size(); i++) { 17734 UserStartedState uss = mStartedUsers.valueAt(i); 17735 if (uss.mState != UserStartedState.STATE_STOPPING 17736 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17737 mStartedUserArray[num] = mStartedUsers.keyAt(i); 17738 num++; 17739 } 17740 } 17741 } 17742 17743 @Override 17744 public void registerUserSwitchObserver(IUserSwitchObserver observer) { 17745 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17746 != PackageManager.PERMISSION_GRANTED) { 17747 String msg = "Permission Denial: registerUserSwitchObserver() from pid=" 17748 + Binder.getCallingPid() 17749 + ", uid=" + Binder.getCallingUid() 17750 + " requires " + INTERACT_ACROSS_USERS_FULL; 17751 Slog.w(TAG, msg); 17752 throw new SecurityException(msg); 17753 } 17754 17755 mUserSwitchObservers.register(observer); 17756 } 17757 17758 @Override 17759 public void unregisterUserSwitchObserver(IUserSwitchObserver observer) { 17760 mUserSwitchObservers.unregister(observer); 17761 } 17762 17763 private boolean userExists(int userId) { 17764 if (userId == 0) { 17765 return true; 17766 } 17767 UserManagerService ums = getUserManagerLocked(); 17768 return ums != null ? (ums.getUserInfo(userId) != null) : false; 17769 } 17770 17771 int[] getUsersLocked() { 17772 UserManagerService ums = getUserManagerLocked(); 17773 return ums != null ? ums.getUserIds() : new int[] { 0 }; 17774 } 17775 17776 UserManagerService getUserManagerLocked() { 17777 if (mUserManager == null) { 17778 IBinder b = ServiceManager.getService(Context.USER_SERVICE); 17779 mUserManager = (UserManagerService)IUserManager.Stub.asInterface(b); 17780 } 17781 return mUserManager; 17782 } 17783 17784 private int applyUserId(int uid, int userId) { 17785 return UserHandle.getUid(userId, uid); 17786 } 17787 17788 ApplicationInfo getAppInfoForUser(ApplicationInfo info, int userId) { 17789 if (info == null) return null; 17790 ApplicationInfo newInfo = new ApplicationInfo(info); 17791 newInfo.uid = applyUserId(info.uid, userId); 17792 newInfo.dataDir = USER_DATA_DIR + userId + "/" 17793 + info.packageName; 17794 return newInfo; 17795 } 17796 17797 ActivityInfo getActivityInfoForUser(ActivityInfo aInfo, int userId) { 17798 if (aInfo == null 17799 || (userId < 1 && aInfo.applicationInfo.uid < UserHandle.PER_USER_RANGE)) { 17800 return aInfo; 17801 } 17802 17803 ActivityInfo info = new ActivityInfo(aInfo); 17804 info.applicationInfo = getAppInfoForUser(info.applicationInfo, userId); 17805 return info; 17806 } 17807 17808 private final class LocalService extends ActivityManagerInternal { 17809 @Override 17810 public void goingToSleep() { 17811 ActivityManagerService.this.goingToSleep(); 17812 } 17813 17814 @Override 17815 public void wakingUp() { 17816 ActivityManagerService.this.wakingUp(); 17817 } 17818 } 17819 17820 /** 17821 * An implementation of IAppTask, that allows an app to manage its own tasks via 17822 * {@link android.app.ActivityManager.AppTask}. We keep track of the callingUid to ensure that 17823 * only the process that calls getAppTasks() can call the AppTask methods. 17824 */ 17825 class AppTaskImpl extends IAppTask.Stub { 17826 private int mTaskId; 17827 private int mCallingUid; 17828 17829 public AppTaskImpl(int taskId, int callingUid) { 17830 mTaskId = taskId; 17831 mCallingUid = callingUid; 17832 } 17833 17834 @Override 17835 public void finishAndRemoveTask() { 17836 // Ensure that we are called from the same process that created this AppTask 17837 if (mCallingUid != Binder.getCallingUid()) { 17838 Slog.w(TAG, "finishAndRemoveTask: caller " + mCallingUid 17839 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 17840 return; 17841 } 17842 17843 synchronized (ActivityManagerService.this) { 17844 long origId = Binder.clearCallingIdentity(); 17845 try { 17846 TaskRecord tr = recentTaskForIdLocked(mTaskId); 17847 if (tr != null) { 17848 // Only kill the process if we are not a new document 17849 int flags = tr.getBaseIntent().getFlags(); 17850 boolean isDocument = (flags & Intent.FLAG_ACTIVITY_NEW_DOCUMENT) == 17851 Intent.FLAG_ACTIVITY_NEW_DOCUMENT; 17852 removeTaskByIdLocked(mTaskId, 17853 !isDocument ? ActivityManager.REMOVE_TASK_KILL_PROCESS : 0); 17854 } 17855 } finally { 17856 Binder.restoreCallingIdentity(origId); 17857 } 17858 } 17859 } 17860 17861 @Override 17862 public ActivityManager.RecentTaskInfo getTaskInfo() { 17863 // Ensure that we are called from the same process that created this AppTask 17864 if (mCallingUid != Binder.getCallingUid()) { 17865 Slog.w(TAG, "finishAndRemoveTask: caller " + mCallingUid 17866 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 17867 return null; 17868 } 17869 17870 synchronized (ActivityManagerService.this) { 17871 long origId = Binder.clearCallingIdentity(); 17872 try { 17873 TaskRecord tr = recentTaskForIdLocked(mTaskId); 17874 if (tr != null) { 17875 return createRecentTaskInfoFromTaskRecord(tr); 17876 } 17877 } finally { 17878 Binder.restoreCallingIdentity(origId); 17879 } 17880 return null; 17881 } 17882 } 17883 } 17884} 17885