ActivityManagerService.java revision 7f2d5162fd19345945d54cc864b3cc82bea35a2e
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_FULL; 20import static android.content.pm.PackageManager.PERMISSION_GRANTED; 21import static com.android.internal.util.XmlUtils.readBooleanAttribute; 22import static com.android.internal.util.XmlUtils.readIntAttribute; 23import static com.android.internal.util.XmlUtils.readLongAttribute; 24import static com.android.internal.util.XmlUtils.writeBooleanAttribute; 25import static com.android.internal.util.XmlUtils.writeIntAttribute; 26import static com.android.internal.util.XmlUtils.writeLongAttribute; 27import static com.android.server.Watchdog.NATIVE_STACKS_OF_INTEREST; 28import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT; 29import static org.xmlpull.v1.XmlPullParser.START_TAG; 30import static com.android.server.am.ActivityStackSupervisor.HOME_STACK_ID; 31 32import android.Manifest; 33import android.app.AppOpsManager; 34import android.app.IActivityContainer; 35import android.app.IActivityContainerCallback; 36import android.app.IAppTask; 37import android.app.admin.DevicePolicyManager; 38import android.appwidget.AppWidgetManager; 39import android.graphics.Rect; 40import android.os.BatteryStats; 41import android.os.PersistableBundle; 42import android.service.voice.IVoiceInteractionSession; 43import android.util.ArrayMap; 44 45import com.android.internal.R; 46import com.android.internal.annotations.GuardedBy; 47import com.android.internal.app.IAppOpsService; 48import com.android.internal.app.IVoiceInteractor; 49import com.android.internal.app.ProcessMap; 50import com.android.internal.app.ProcessStats; 51import com.android.internal.content.PackageMonitor; 52import com.android.internal.os.BackgroundThread; 53import com.android.internal.os.BatteryStatsImpl; 54import com.android.internal.os.ProcessCpuTracker; 55import com.android.internal.os.TransferPipe; 56import com.android.internal.os.Zygote; 57import com.android.internal.util.FastPrintWriter; 58import com.android.internal.util.FastXmlSerializer; 59import com.android.internal.util.MemInfoReader; 60import com.android.internal.util.Preconditions; 61import com.android.server.AppOpsService; 62import com.android.server.AttributeCache; 63import com.android.server.IntentResolver; 64import com.android.server.LocalServices; 65import com.android.server.ServiceThread; 66import com.android.server.SystemService; 67import com.android.server.SystemServiceManager; 68import com.android.server.Watchdog; 69import com.android.server.am.ActivityStack.ActivityState; 70import com.android.server.firewall.IntentFirewall; 71import com.android.server.pm.UserManagerService; 72import com.android.server.wm.AppTransition; 73import com.android.server.wm.WindowManagerService; 74import com.google.android.collect.Lists; 75import com.google.android.collect.Maps; 76 77import libcore.io.IoUtils; 78 79import org.xmlpull.v1.XmlPullParser; 80import org.xmlpull.v1.XmlPullParserException; 81import org.xmlpull.v1.XmlSerializer; 82 83import android.app.Activity; 84import android.app.ActivityManager; 85import android.app.ActivityManager.RunningTaskInfo; 86import android.app.ActivityManager.StackInfo; 87import android.app.ActivityManagerInternal; 88import android.app.ActivityManagerNative; 89import android.app.ActivityOptions; 90import android.app.ActivityThread; 91import android.app.AlertDialog; 92import android.app.AppGlobals; 93import android.app.ApplicationErrorReport; 94import android.app.Dialog; 95import android.app.IActivityController; 96import android.app.IApplicationThread; 97import android.app.IInstrumentationWatcher; 98import android.app.INotificationManager; 99import android.app.IProcessObserver; 100import android.app.IServiceConnection; 101import android.app.IStopUserCallback; 102import android.app.IUiAutomationConnection; 103import android.app.IUserSwitchObserver; 104import android.app.Instrumentation; 105import android.app.Notification; 106import android.app.NotificationManager; 107import android.app.PendingIntent; 108import android.app.backup.IBackupManager; 109import android.content.ActivityNotFoundException; 110import android.content.BroadcastReceiver; 111import android.content.ClipData; 112import android.content.ComponentCallbacks2; 113import android.content.ComponentName; 114import android.content.ContentProvider; 115import android.content.ContentResolver; 116import android.content.Context; 117import android.content.DialogInterface; 118import android.content.IContentProvider; 119import android.content.IIntentReceiver; 120import android.content.IIntentSender; 121import android.content.Intent; 122import android.content.IntentFilter; 123import android.content.IntentSender; 124import android.content.pm.ActivityInfo; 125import android.content.pm.ApplicationInfo; 126import android.content.pm.ConfigurationInfo; 127import android.content.pm.IPackageDataObserver; 128import android.content.pm.IPackageManager; 129import android.content.pm.InstrumentationInfo; 130import android.content.pm.PackageInfo; 131import android.content.pm.PackageManager; 132import android.content.pm.ParceledListSlice; 133import android.content.pm.UserInfo; 134import android.content.pm.PackageManager.NameNotFoundException; 135import android.content.pm.PathPermission; 136import android.content.pm.ProviderInfo; 137import android.content.pm.ResolveInfo; 138import android.content.pm.ServiceInfo; 139import android.content.res.CompatibilityInfo; 140import android.content.res.Configuration; 141import android.graphics.Bitmap; 142import android.net.Proxy; 143import android.net.ProxyInfo; 144import android.net.Uri; 145import android.os.Binder; 146import android.os.Build; 147import android.os.Bundle; 148import android.os.Debug; 149import android.os.DropBoxManager; 150import android.os.Environment; 151import android.os.FactoryTest; 152import android.os.FileObserver; 153import android.os.FileUtils; 154import android.os.Handler; 155import android.os.IBinder; 156import android.os.IPermissionController; 157import android.os.IRemoteCallback; 158import android.os.IUserManager; 159import android.os.Looper; 160import android.os.Message; 161import android.os.Parcel; 162import android.os.ParcelFileDescriptor; 163import android.os.Process; 164import android.os.RemoteCallbackList; 165import android.os.RemoteException; 166import android.os.SELinux; 167import android.os.ServiceManager; 168import android.os.StrictMode; 169import android.os.SystemClock; 170import android.os.SystemProperties; 171import android.os.UpdateLock; 172import android.os.UserHandle; 173import android.provider.Settings; 174import android.text.format.DateUtils; 175import android.text.format.Time; 176import android.util.AtomicFile; 177import android.util.EventLog; 178import android.util.Log; 179import android.util.Pair; 180import android.util.PrintWriterPrinter; 181import android.util.Slog; 182import android.util.SparseArray; 183import android.util.TimeUtils; 184import android.util.Xml; 185import android.view.Gravity; 186import android.view.LayoutInflater; 187import android.view.View; 188import android.view.WindowManager; 189 190import java.io.BufferedInputStream; 191import java.io.BufferedOutputStream; 192import java.io.DataInputStream; 193import java.io.DataOutputStream; 194import java.io.File; 195import java.io.FileDescriptor; 196import java.io.FileInputStream; 197import java.io.FileNotFoundException; 198import java.io.FileOutputStream; 199import java.io.IOException; 200import java.io.InputStreamReader; 201import java.io.PrintWriter; 202import java.io.StringWriter; 203import java.lang.ref.WeakReference; 204import java.util.ArrayList; 205import java.util.Arrays; 206import java.util.Collections; 207import java.util.Comparator; 208import java.util.HashMap; 209import java.util.HashSet; 210import java.util.Iterator; 211import java.util.List; 212import java.util.Locale; 213import java.util.Map; 214import java.util.Set; 215import java.util.concurrent.atomic.AtomicBoolean; 216import java.util.concurrent.atomic.AtomicLong; 217 218public final class ActivityManagerService extends ActivityManagerNative 219 implements Watchdog.Monitor, BatteryStatsImpl.BatteryCallback { 220 private static final String USER_DATA_DIR = "/data/user/"; 221 static final String TAG = "ActivityManager"; 222 static final String TAG_MU = "ActivityManagerServiceMU"; 223 static final boolean DEBUG = false; 224 static final boolean localLOGV = DEBUG; 225 static final boolean DEBUG_BACKUP = localLOGV || false; 226 static final boolean DEBUG_BROADCAST = localLOGV || false; 227 static final boolean DEBUG_BROADCAST_LIGHT = DEBUG_BROADCAST || false; 228 static final boolean DEBUG_BACKGROUND_BROADCAST = DEBUG_BROADCAST || false; 229 static final boolean DEBUG_CLEANUP = localLOGV || false; 230 static final boolean DEBUG_CONFIGURATION = localLOGV || false; 231 static final boolean DEBUG_FOCUS = false; 232 static final boolean DEBUG_IMMERSIVE = localLOGV || false; 233 static final boolean DEBUG_MU = localLOGV || false; 234 static final boolean DEBUG_OOM_ADJ = localLOGV || false; 235 static final boolean DEBUG_LRU = localLOGV || false; 236 static final boolean DEBUG_PAUSE = localLOGV || false; 237 static final boolean DEBUG_POWER = localLOGV || false; 238 static final boolean DEBUG_POWER_QUICK = DEBUG_POWER || false; 239 static final boolean DEBUG_PROCESS_OBSERVERS = localLOGV || false; 240 static final boolean DEBUG_PROCESSES = localLOGV || false; 241 static final boolean DEBUG_PROVIDER = localLOGV || false; 242 static final boolean DEBUG_RESULTS = localLOGV || false; 243 static final boolean DEBUG_SERVICE = localLOGV || false; 244 static final boolean DEBUG_SERVICE_EXECUTING = localLOGV || false; 245 static final boolean DEBUG_STACK = localLOGV || false; 246 static final boolean DEBUG_SWITCH = localLOGV || false; 247 static final boolean DEBUG_TASKS = localLOGV || false; 248 static final boolean DEBUG_THUMBNAILS = localLOGV || false; 249 static final boolean DEBUG_TRANSITION = localLOGV || false; 250 static final boolean DEBUG_URI_PERMISSION = localLOGV || false; 251 static final boolean DEBUG_USER_LEAVING = localLOGV || false; 252 static final boolean DEBUG_VISBILITY = localLOGV || false; 253 static final boolean DEBUG_PSS = localLOGV || false; 254 static final boolean DEBUG_LOCKSCREEN = localLOGV || false; 255 static final boolean VALIDATE_TOKENS = false; 256 static final boolean SHOW_ACTIVITY_START_TIME = true; 257 258 // Control over CPU and battery monitoring. 259 static final long BATTERY_STATS_TIME = 30*60*1000; // write battery stats every 30 minutes. 260 static final boolean MONITOR_CPU_USAGE = true; 261 static final long MONITOR_CPU_MIN_TIME = 5*1000; // don't sample cpu less than every 5 seconds. 262 static final long MONITOR_CPU_MAX_TIME = 0x0fffffff; // wait possibly forever for next cpu sample. 263 static final boolean MONITOR_THREAD_CPU_USAGE = false; 264 265 // The flags that are set for all calls we make to the package manager. 266 static final int STOCK_PM_FLAGS = PackageManager.GET_SHARED_LIBRARY_FILES; 267 268 private static final String SYSTEM_DEBUGGABLE = "ro.debuggable"; 269 270 static final boolean IS_USER_BUILD = "user".equals(Build.TYPE); 271 272 // Maximum number of recent tasks that we can remember. 273 static final int MAX_RECENT_TASKS = ActivityManager.isLowRamDeviceStatic() ? 10 : 20; 274 275 // Amount of time after a call to stopAppSwitches() during which we will 276 // prevent further untrusted switches from happening. 277 static final long APP_SWITCH_DELAY_TIME = 5*1000; 278 279 // How long we wait for a launched process to attach to the activity manager 280 // before we decide it's never going to come up for real. 281 static final int PROC_START_TIMEOUT = 10*1000; 282 283 // How long we wait for a launched process to attach to the activity manager 284 // before we decide it's never going to come up for real, when the process was 285 // started with a wrapper for instrumentation (such as Valgrind) because it 286 // could take much longer than usual. 287 static final int PROC_START_TIMEOUT_WITH_WRAPPER = 1200*1000; 288 289 // How long to wait after going idle before forcing apps to GC. 290 static final int GC_TIMEOUT = 5*1000; 291 292 // The minimum amount of time between successive GC requests for a process. 293 static final int GC_MIN_INTERVAL = 60*1000; 294 295 // The minimum amount of time between successive PSS requests for a process. 296 static final int FULL_PSS_MIN_INTERVAL = 10*60*1000; 297 298 // The minimum amount of time between successive PSS requests for a process 299 // when the request is due to the memory state being lowered. 300 static final int FULL_PSS_LOWERED_INTERVAL = 2*60*1000; 301 302 // The rate at which we check for apps using excessive power -- 15 mins. 303 static final int POWER_CHECK_DELAY = (DEBUG_POWER_QUICK ? 2 : 15) * 60*1000; 304 305 // The minimum sample duration we will allow before deciding we have 306 // enough data on wake locks to start killing things. 307 static final int WAKE_LOCK_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 308 309 // The minimum sample duration we will allow before deciding we have 310 // enough data on CPU usage to start killing things. 311 static final int CPU_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 312 313 // How long we allow a receiver to run before giving up on it. 314 static final int BROADCAST_FG_TIMEOUT = 10*1000; 315 static final int BROADCAST_BG_TIMEOUT = 60*1000; 316 317 // How long we wait until we timeout on key dispatching. 318 static final int KEY_DISPATCHING_TIMEOUT = 5*1000; 319 320 // How long we wait until we timeout on key dispatching during instrumentation. 321 static final int INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT = 60*1000; 322 323 // Amount of time we wait for observers to handle a user switch before 324 // giving up on them and unfreezing the screen. 325 static final int USER_SWITCH_TIMEOUT = 2*1000; 326 327 // Maximum number of users we allow to be running at a time. 328 static final int MAX_RUNNING_USERS = 3; 329 330 // How long to wait in getAssistContextExtras for the activity and foreground services 331 // to respond with the result. 332 static final int PENDING_ASSIST_EXTRAS_TIMEOUT = 500; 333 334 // Maximum number of persisted Uri grants a package is allowed 335 static final int MAX_PERSISTED_URI_GRANTS = 128; 336 337 static final int MY_PID = Process.myPid(); 338 339 static final String[] EMPTY_STRING_ARRAY = new String[0]; 340 341 // How many bytes to write into the dropbox log before truncating 342 static final int DROPBOX_MAX_SIZE = 256 * 1024; 343 344 /** All system services */ 345 SystemServiceManager mSystemServiceManager; 346 347 /** Run all ActivityStacks through this */ 348 ActivityStackSupervisor mStackSupervisor; 349 350 public IntentFirewall mIntentFirewall; 351 352 // Whether we should show our dialogs (ANR, crash, etc) or just perform their 353 // default actuion automatically. Important for devices without direct input 354 // devices. 355 private boolean mShowDialogs = true; 356 357 /** 358 * Description of a request to start a new activity, which has been held 359 * due to app switches being disabled. 360 */ 361 static class PendingActivityLaunch { 362 final ActivityRecord r; 363 final ActivityRecord sourceRecord; 364 final int startFlags; 365 final ActivityStack stack; 366 367 PendingActivityLaunch(ActivityRecord _r, ActivityRecord _sourceRecord, 368 int _startFlags, ActivityStack _stack) { 369 r = _r; 370 sourceRecord = _sourceRecord; 371 startFlags = _startFlags; 372 stack = _stack; 373 } 374 } 375 376 final ArrayList<PendingActivityLaunch> mPendingActivityLaunches 377 = new ArrayList<PendingActivityLaunch>(); 378 379 BroadcastQueue mFgBroadcastQueue; 380 BroadcastQueue mBgBroadcastQueue; 381 // Convenient for easy iteration over the queues. Foreground is first 382 // so that dispatch of foreground broadcasts gets precedence. 383 final BroadcastQueue[] mBroadcastQueues = new BroadcastQueue[2]; 384 385 BroadcastQueue broadcastQueueForIntent(Intent intent) { 386 final boolean isFg = (intent.getFlags() & Intent.FLAG_RECEIVER_FOREGROUND) != 0; 387 if (DEBUG_BACKGROUND_BROADCAST) { 388 Slog.i(TAG, "Broadcast intent " + intent + " on " 389 + (isFg ? "foreground" : "background") 390 + " queue"); 391 } 392 return (isFg) ? mFgBroadcastQueue : mBgBroadcastQueue; 393 } 394 395 BroadcastRecord broadcastRecordForReceiverLocked(IBinder receiver) { 396 for (BroadcastQueue queue : mBroadcastQueues) { 397 BroadcastRecord r = queue.getMatchingOrderedReceiver(receiver); 398 if (r != null) { 399 return r; 400 } 401 } 402 return null; 403 } 404 405 /** 406 * Activity we have told the window manager to have key focus. 407 */ 408 ActivityRecord mFocusedActivity = null; 409 410 /** 411 * List of intents that were used to start the most recent tasks. 412 */ 413 ArrayList<TaskRecord> mRecentTasks; 414 415 public class PendingAssistExtras extends Binder implements Runnable { 416 public final ActivityRecord activity; 417 public boolean haveResult = false; 418 public Bundle result = null; 419 public PendingAssistExtras(ActivityRecord _activity) { 420 activity = _activity; 421 } 422 @Override 423 public void run() { 424 Slog.w(TAG, "getAssistContextExtras failed: timeout retrieving from " + activity); 425 synchronized (this) { 426 haveResult = true; 427 notifyAll(); 428 } 429 } 430 } 431 432 final ArrayList<PendingAssistExtras> mPendingAssistExtras 433 = new ArrayList<PendingAssistExtras>(); 434 435 /** 436 * Process management. 437 */ 438 final ProcessList mProcessList = new ProcessList(); 439 440 /** 441 * All of the applications we currently have running organized by name. 442 * The keys are strings of the application package name (as 443 * returned by the package manager), and the keys are ApplicationRecord 444 * objects. 445 */ 446 final ProcessMap<ProcessRecord> mProcessNames = new ProcessMap<ProcessRecord>(); 447 448 /** 449 * Tracking long-term execution of processes to look for abuse and other 450 * bad app behavior. 451 */ 452 final ProcessStatsService mProcessStats; 453 454 /** 455 * The currently running isolated processes. 456 */ 457 final SparseArray<ProcessRecord> mIsolatedProcesses = new SparseArray<ProcessRecord>(); 458 459 /** 460 * Counter for assigning isolated process uids, to avoid frequently reusing the 461 * same ones. 462 */ 463 int mNextIsolatedProcessUid = 0; 464 465 /** 466 * The currently running heavy-weight process, if any. 467 */ 468 ProcessRecord mHeavyWeightProcess = null; 469 470 /** 471 * The last time that various processes have crashed. 472 */ 473 final ProcessMap<Long> mProcessCrashTimes = new ProcessMap<Long>(); 474 475 /** 476 * Information about a process that is currently marked as bad. 477 */ 478 static final class BadProcessInfo { 479 BadProcessInfo(long time, String shortMsg, String longMsg, String stack) { 480 this.time = time; 481 this.shortMsg = shortMsg; 482 this.longMsg = longMsg; 483 this.stack = stack; 484 } 485 486 final long time; 487 final String shortMsg; 488 final String longMsg; 489 final String stack; 490 } 491 492 /** 493 * Set of applications that we consider to be bad, and will reject 494 * incoming broadcasts from (which the user has no control over). 495 * Processes are added to this set when they have crashed twice within 496 * a minimum amount of time; they are removed from it when they are 497 * later restarted (hopefully due to some user action). The value is the 498 * time it was added to the list. 499 */ 500 final ProcessMap<BadProcessInfo> mBadProcesses = new ProcessMap<BadProcessInfo>(); 501 502 /** 503 * All of the processes we currently have running organized by pid. 504 * The keys are the pid running the application. 505 * 506 * <p>NOTE: This object is protected by its own lock, NOT the global 507 * activity manager lock! 508 */ 509 final SparseArray<ProcessRecord> mPidsSelfLocked = new SparseArray<ProcessRecord>(); 510 511 /** 512 * All of the processes that have been forced to be foreground. The key 513 * is the pid of the caller who requested it (we hold a death 514 * link on it). 515 */ 516 abstract class ForegroundToken implements IBinder.DeathRecipient { 517 int pid; 518 IBinder token; 519 } 520 final SparseArray<ForegroundToken> mForegroundProcesses = new SparseArray<ForegroundToken>(); 521 522 /** 523 * List of records for processes that someone had tried to start before the 524 * system was ready. We don't start them at that point, but ensure they 525 * are started by the time booting is complete. 526 */ 527 final ArrayList<ProcessRecord> mProcessesOnHold = new ArrayList<ProcessRecord>(); 528 529 /** 530 * List of persistent applications that are in the process 531 * of being started. 532 */ 533 final ArrayList<ProcessRecord> mPersistentStartingProcesses = new ArrayList<ProcessRecord>(); 534 535 /** 536 * Processes that are being forcibly torn down. 537 */ 538 final ArrayList<ProcessRecord> mRemovedProcesses = new ArrayList<ProcessRecord>(); 539 540 /** 541 * List of running applications, sorted by recent usage. 542 * The first entry in the list is the least recently used. 543 */ 544 final ArrayList<ProcessRecord> mLruProcesses = new ArrayList<ProcessRecord>(); 545 546 /** 547 * Where in mLruProcesses that the processes hosting activities start. 548 */ 549 int mLruProcessActivityStart = 0; 550 551 /** 552 * Where in mLruProcesses that the processes hosting services start. 553 * This is after (lower index) than mLruProcessesActivityStart. 554 */ 555 int mLruProcessServiceStart = 0; 556 557 /** 558 * List of processes that should gc as soon as things are idle. 559 */ 560 final ArrayList<ProcessRecord> mProcessesToGc = new ArrayList<ProcessRecord>(); 561 562 /** 563 * Processes we want to collect PSS data from. 564 */ 565 final ArrayList<ProcessRecord> mPendingPssProcesses = new ArrayList<ProcessRecord>(); 566 567 /** 568 * Last time we requested PSS data of all processes. 569 */ 570 long mLastFullPssTime = SystemClock.uptimeMillis(); 571 572 /** 573 * This is the process holding what we currently consider to be 574 * the "home" activity. 575 */ 576 ProcessRecord mHomeProcess; 577 578 /** 579 * This is the process holding the activity the user last visited that 580 * is in a different process from the one they are currently in. 581 */ 582 ProcessRecord mPreviousProcess; 583 584 /** 585 * The time at which the previous process was last visible. 586 */ 587 long mPreviousProcessVisibleTime; 588 589 /** 590 * Which uses have been started, so are allowed to run code. 591 */ 592 final SparseArray<UserStartedState> mStartedUsers = new SparseArray<UserStartedState>(); 593 594 /** 595 * LRU list of history of current users. Most recently current is at the end. 596 */ 597 final ArrayList<Integer> mUserLru = new ArrayList<Integer>(); 598 599 /** 600 * Constant array of the users that are currently started. 601 */ 602 int[] mStartedUserArray = new int[] { 0 }; 603 604 /** 605 * Registered observers of the user switching mechanics. 606 */ 607 final RemoteCallbackList<IUserSwitchObserver> mUserSwitchObservers 608 = new RemoteCallbackList<IUserSwitchObserver>(); 609 610 /** 611 * Currently active user switch. 612 */ 613 Object mCurUserSwitchCallback; 614 615 /** 616 * Packages that the user has asked to have run in screen size 617 * compatibility mode instead of filling the screen. 618 */ 619 final CompatModePackages mCompatModePackages; 620 621 /** 622 * Set of IntentSenderRecord objects that are currently active. 623 */ 624 final HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>> mIntentSenderRecords 625 = new HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>>(); 626 627 /** 628 * Fingerprints (hashCode()) of stack traces that we've 629 * already logged DropBox entries for. Guarded by itself. If 630 * something (rogue user app) forces this over 631 * MAX_DUP_SUPPRESSED_STACKS entries, the contents are cleared. 632 */ 633 private final HashSet<Integer> mAlreadyLoggedViolatedStacks = new HashSet<Integer>(); 634 private static final int MAX_DUP_SUPPRESSED_STACKS = 5000; 635 636 /** 637 * Strict Mode background batched logging state. 638 * 639 * The string buffer is guarded by itself, and its lock is also 640 * used to determine if another batched write is already 641 * in-flight. 642 */ 643 private final StringBuilder mStrictModeBuffer = new StringBuilder(); 644 645 /** 646 * Keeps track of all IIntentReceivers that have been registered for 647 * broadcasts. Hash keys are the receiver IBinder, hash value is 648 * a ReceiverList. 649 */ 650 final HashMap<IBinder, ReceiverList> mRegisteredReceivers = 651 new HashMap<IBinder, ReceiverList>(); 652 653 /** 654 * Resolver for broadcast intents to registered receivers. 655 * Holds BroadcastFilter (subclass of IntentFilter). 656 */ 657 final IntentResolver<BroadcastFilter, BroadcastFilter> mReceiverResolver 658 = new IntentResolver<BroadcastFilter, BroadcastFilter>() { 659 @Override 660 protected boolean allowFilterResult( 661 BroadcastFilter filter, List<BroadcastFilter> dest) { 662 IBinder target = filter.receiverList.receiver.asBinder(); 663 for (int i=dest.size()-1; i>=0; i--) { 664 if (dest.get(i).receiverList.receiver.asBinder() == target) { 665 return false; 666 } 667 } 668 return true; 669 } 670 671 @Override 672 protected BroadcastFilter newResult(BroadcastFilter filter, int match, int userId) { 673 if (userId == UserHandle.USER_ALL || filter.owningUserId == UserHandle.USER_ALL 674 || userId == filter.owningUserId) { 675 return super.newResult(filter, match, userId); 676 } 677 return null; 678 } 679 680 @Override 681 protected BroadcastFilter[] newArray(int size) { 682 return new BroadcastFilter[size]; 683 } 684 685 @Override 686 protected boolean isPackageForFilter(String packageName, BroadcastFilter filter) { 687 return packageName.equals(filter.packageName); 688 } 689 }; 690 691 /** 692 * State of all active sticky broadcasts per user. Keys are the action of the 693 * sticky Intent, values are an ArrayList of all broadcasted intents with 694 * that action (which should usually be one). The SparseArray is keyed 695 * by the user ID the sticky is for, and can include UserHandle.USER_ALL 696 * for stickies that are sent to all users. 697 */ 698 final SparseArray<ArrayMap<String, ArrayList<Intent>>> mStickyBroadcasts = 699 new SparseArray<ArrayMap<String, ArrayList<Intent>>>(); 700 701 final ActiveServices mServices; 702 703 /** 704 * Backup/restore process management 705 */ 706 String mBackupAppName = null; 707 BackupRecord mBackupTarget = null; 708 709 final ProviderMap mProviderMap; 710 711 /** 712 * List of content providers who have clients waiting for them. The 713 * application is currently being launched and the provider will be 714 * removed from this list once it is published. 715 */ 716 final ArrayList<ContentProviderRecord> mLaunchingProviders 717 = new ArrayList<ContentProviderRecord>(); 718 719 /** 720 * File storing persisted {@link #mGrantedUriPermissions}. 721 */ 722 private final AtomicFile mGrantFile; 723 724 /** XML constants used in {@link #mGrantFile} */ 725 private static final String TAG_URI_GRANTS = "uri-grants"; 726 private static final String TAG_URI_GRANT = "uri-grant"; 727 private static final String ATTR_USER_HANDLE = "userHandle"; 728 private static final String ATTR_SOURCE_USER_ID = "sourceUserId"; 729 private static final String ATTR_TARGET_USER_ID = "targetUserId"; 730 private static final String ATTR_SOURCE_PKG = "sourcePkg"; 731 private static final String ATTR_TARGET_PKG = "targetPkg"; 732 private static final String ATTR_URI = "uri"; 733 private static final String ATTR_MODE_FLAGS = "modeFlags"; 734 private static final String ATTR_CREATED_TIME = "createdTime"; 735 private static final String ATTR_PREFIX = "prefix"; 736 737 /** 738 * Global set of specific {@link Uri} permissions that have been granted. 739 * This optimized lookup structure maps from {@link UriPermission#targetUid} 740 * to {@link UriPermission#uri} to {@link UriPermission}. 741 */ 742 @GuardedBy("this") 743 private final SparseArray<ArrayMap<GrantUri, UriPermission>> 744 mGrantedUriPermissions = new SparseArray<ArrayMap<GrantUri, UriPermission>>(); 745 746 public static class GrantUri { 747 public final int sourceUserId; 748 public final Uri uri; 749 public boolean prefix; 750 751 public GrantUri(int sourceUserId, Uri uri, boolean prefix) { 752 this.sourceUserId = sourceUserId; 753 this.uri = uri; 754 this.prefix = prefix; 755 } 756 757 @Override 758 public int hashCode() { 759 return toString().hashCode(); 760 } 761 762 @Override 763 public boolean equals(Object o) { 764 if (o instanceof GrantUri) { 765 GrantUri other = (GrantUri) o; 766 return uri.equals(other.uri) && (sourceUserId == other.sourceUserId) 767 && prefix == other.prefix; 768 } 769 return false; 770 } 771 772 @Override 773 public String toString() { 774 String result = Integer.toString(sourceUserId) + " @ " + uri.toString(); 775 if (prefix) result += " [prefix]"; 776 return result; 777 } 778 779 public String toSafeString() { 780 String result = Integer.toString(sourceUserId) + " @ " + uri.toSafeString(); 781 if (prefix) result += " [prefix]"; 782 return result; 783 } 784 785 public static GrantUri resolve(int defaultSourceUserHandle, Uri uri) { 786 return new GrantUri(ContentProvider.getUserIdFromUri(uri, defaultSourceUserHandle), 787 ContentProvider.getUriWithoutUserId(uri), false); 788 } 789 } 790 791 CoreSettingsObserver mCoreSettingsObserver; 792 793 /** 794 * Thread-local storage used to carry caller permissions over through 795 * indirect content-provider access. 796 */ 797 private class Identity { 798 public int pid; 799 public int uid; 800 801 Identity(int _pid, int _uid) { 802 pid = _pid; 803 uid = _uid; 804 } 805 } 806 807 private static final ThreadLocal<Identity> sCallerIdentity = new ThreadLocal<Identity>(); 808 809 /** 810 * All information we have collected about the runtime performance of 811 * any user id that can impact battery performance. 812 */ 813 final BatteryStatsService mBatteryStatsService; 814 815 /** 816 * Information about component usage 817 */ 818 final UsageStatsService mUsageStatsService; 819 820 /** 821 * Information about and control over application operations 822 */ 823 final AppOpsService mAppOpsService; 824 825 /** 826 * Save recent tasks information across reboots. 827 */ 828 final TaskPersister mTaskPersister; 829 830 /** 831 * Current configuration information. HistoryRecord objects are given 832 * a reference to this object to indicate which configuration they are 833 * currently running in, so this object must be kept immutable. 834 */ 835 Configuration mConfiguration = new Configuration(); 836 837 /** 838 * Current sequencing integer of the configuration, for skipping old 839 * configurations. 840 */ 841 int mConfigurationSeq = 0; 842 843 /** 844 * Hardware-reported OpenGLES version. 845 */ 846 final int GL_ES_VERSION; 847 848 /** 849 * List of initialization arguments to pass to all processes when binding applications to them. 850 * For example, references to the commonly used services. 851 */ 852 HashMap<String, IBinder> mAppBindArgs; 853 854 /** 855 * Temporary to avoid allocations. Protected by main lock. 856 */ 857 final StringBuilder mStringBuilder = new StringBuilder(256); 858 859 /** 860 * Used to control how we initialize the service. 861 */ 862 ComponentName mTopComponent; 863 String mTopAction = Intent.ACTION_MAIN; 864 String mTopData; 865 boolean mProcessesReady = false; 866 boolean mSystemReady = false; 867 boolean mBooting = false; 868 boolean mWaitingUpdate = false; 869 boolean mDidUpdate = false; 870 boolean mOnBattery = false; 871 boolean mLaunchWarningShown = false; 872 873 Context mContext; 874 875 int mFactoryTest; 876 877 boolean mCheckedForSetup; 878 879 /** 880 * The time at which we will allow normal application switches again, 881 * after a call to {@link #stopAppSwitches()}. 882 */ 883 long mAppSwitchesAllowedTime; 884 885 /** 886 * This is set to true after the first switch after mAppSwitchesAllowedTime 887 * is set; any switches after that will clear the time. 888 */ 889 boolean mDidAppSwitch; 890 891 /** 892 * Last time (in realtime) at which we checked for power usage. 893 */ 894 long mLastPowerCheckRealtime; 895 896 /** 897 * Last time (in uptime) at which we checked for power usage. 898 */ 899 long mLastPowerCheckUptime; 900 901 /** 902 * Set while we are wanting to sleep, to prevent any 903 * activities from being started/resumed. 904 */ 905 private boolean mSleeping = false; 906 907 /** 908 * Set while we are running a voice interaction. This overrides 909 * sleeping while it is active. 910 */ 911 private boolean mRunningVoice = false; 912 913 /** 914 * State of external calls telling us if the device is asleep. 915 */ 916 private boolean mWentToSleep = false; 917 918 /** 919 * State of external call telling us if the lock screen is shown. 920 */ 921 private boolean mLockScreenShown = false; 922 923 /** 924 * Set if we are shutting down the system, similar to sleeping. 925 */ 926 boolean mShuttingDown = false; 927 928 /** 929 * Current sequence id for oom_adj computation traversal. 930 */ 931 int mAdjSeq = 0; 932 933 /** 934 * Current sequence id for process LRU updating. 935 */ 936 int mLruSeq = 0; 937 938 /** 939 * Keep track of the non-cached/empty process we last found, to help 940 * determine how to distribute cached/empty processes next time. 941 */ 942 int mNumNonCachedProcs = 0; 943 944 /** 945 * Keep track of the number of cached hidden procs, to balance oom adj 946 * distribution between those and empty procs. 947 */ 948 int mNumCachedHiddenProcs = 0; 949 950 /** 951 * Keep track of the number of service processes we last found, to 952 * determine on the next iteration which should be B services. 953 */ 954 int mNumServiceProcs = 0; 955 int mNewNumAServiceProcs = 0; 956 int mNewNumServiceProcs = 0; 957 958 /** 959 * Allow the current computed overall memory level of the system to go down? 960 * This is set to false when we are killing processes for reasons other than 961 * memory management, so that the now smaller process list will not be taken as 962 * an indication that memory is tighter. 963 */ 964 boolean mAllowLowerMemLevel = false; 965 966 /** 967 * The last computed memory level, for holding when we are in a state that 968 * processes are going away for other reasons. 969 */ 970 int mLastMemoryLevel = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 971 972 /** 973 * The last total number of process we have, to determine if changes actually look 974 * like a shrinking number of process due to lower RAM. 975 */ 976 int mLastNumProcesses; 977 978 /** 979 * The uptime of the last time we performed idle maintenance. 980 */ 981 long mLastIdleTime = SystemClock.uptimeMillis(); 982 983 /** 984 * Total time spent with RAM that has been added in the past since the last idle time. 985 */ 986 long mLowRamTimeSinceLastIdle = 0; 987 988 /** 989 * If RAM is currently low, when that horrible situation started. 990 */ 991 long mLowRamStartTime = 0; 992 993 /** 994 * For reporting to battery stats the current top application. 995 */ 996 private String mCurResumedPackage = null; 997 private int mCurResumedUid = -1; 998 999 /** 1000 * For reporting to battery stats the apps currently running foreground 1001 * service. The ProcessMap is package/uid tuples; each of these contain 1002 * an array of the currently foreground processes. 1003 */ 1004 final ProcessMap<ArrayList<ProcessRecord>> mForegroundPackages 1005 = new ProcessMap<ArrayList<ProcessRecord>>(); 1006 1007 /** 1008 * This is set if we had to do a delayed dexopt of an app before launching 1009 * it, to increase the ANR timeouts in that case. 1010 */ 1011 boolean mDidDexOpt; 1012 1013 /** 1014 * Set if the systemServer made a call to enterSafeMode. 1015 */ 1016 boolean mSafeMode; 1017 1018 String mDebugApp = null; 1019 boolean mWaitForDebugger = false; 1020 boolean mDebugTransient = false; 1021 String mOrigDebugApp = null; 1022 boolean mOrigWaitForDebugger = false; 1023 boolean mAlwaysFinishActivities = false; 1024 IActivityController mController = null; 1025 String mProfileApp = null; 1026 ProcessRecord mProfileProc = null; 1027 String mProfileFile; 1028 ParcelFileDescriptor mProfileFd; 1029 int mProfileType = 0; 1030 boolean mAutoStopProfiler = false; 1031 String mOpenGlTraceApp = null; 1032 1033 static class ProcessChangeItem { 1034 static final int CHANGE_ACTIVITIES = 1<<0; 1035 static final int CHANGE_PROCESS_STATE = 1<<1; 1036 int changes; 1037 int uid; 1038 int pid; 1039 int processState; 1040 boolean foregroundActivities; 1041 } 1042 1043 final RemoteCallbackList<IProcessObserver> mProcessObservers 1044 = new RemoteCallbackList<IProcessObserver>(); 1045 ProcessChangeItem[] mActiveProcessChanges = new ProcessChangeItem[5]; 1046 1047 final ArrayList<ProcessChangeItem> mPendingProcessChanges 1048 = new ArrayList<ProcessChangeItem>(); 1049 final ArrayList<ProcessChangeItem> mAvailProcessChanges 1050 = new ArrayList<ProcessChangeItem>(); 1051 1052 /** 1053 * Runtime CPU use collection thread. This object's lock is used to 1054 * protect all related state. 1055 */ 1056 final Thread mProcessCpuThread; 1057 1058 /** 1059 * Used to collect process stats when showing not responding dialog. 1060 * Protected by mProcessCpuThread. 1061 */ 1062 final ProcessCpuTracker mProcessCpuTracker = new ProcessCpuTracker( 1063 MONITOR_THREAD_CPU_USAGE); 1064 final AtomicLong mLastCpuTime = new AtomicLong(0); 1065 final AtomicBoolean mProcessCpuMutexFree = new AtomicBoolean(true); 1066 1067 long mLastWriteTime = 0; 1068 1069 /** 1070 * Used to retain an update lock when the foreground activity is in 1071 * immersive mode. 1072 */ 1073 final UpdateLock mUpdateLock = new UpdateLock("immersive"); 1074 1075 /** 1076 * Set to true after the system has finished booting. 1077 */ 1078 boolean mBooted = false; 1079 1080 int mProcessLimit = ProcessList.MAX_CACHED_APPS; 1081 int mProcessLimitOverride = -1; 1082 1083 WindowManagerService mWindowManager; 1084 1085 final ActivityThread mSystemThread; 1086 1087 int mCurrentUserId = 0; 1088 int[] mCurrentProfileIds = new int[] {UserHandle.USER_OWNER}; // Accessed by ActivityStack 1089 private UserManagerService mUserManager; 1090 1091 private final class AppDeathRecipient implements IBinder.DeathRecipient { 1092 final ProcessRecord mApp; 1093 final int mPid; 1094 final IApplicationThread mAppThread; 1095 1096 AppDeathRecipient(ProcessRecord app, int pid, 1097 IApplicationThread thread) { 1098 if (localLOGV) Slog.v( 1099 TAG, "New death recipient " + this 1100 + " for thread " + thread.asBinder()); 1101 mApp = app; 1102 mPid = pid; 1103 mAppThread = thread; 1104 } 1105 1106 @Override 1107 public void binderDied() { 1108 if (localLOGV) Slog.v( 1109 TAG, "Death received in " + this 1110 + " for thread " + mAppThread.asBinder()); 1111 synchronized(ActivityManagerService.this) { 1112 appDiedLocked(mApp, mPid, mAppThread); 1113 } 1114 } 1115 } 1116 1117 static final int SHOW_ERROR_MSG = 1; 1118 static final int SHOW_NOT_RESPONDING_MSG = 2; 1119 static final int SHOW_FACTORY_ERROR_MSG = 3; 1120 static final int UPDATE_CONFIGURATION_MSG = 4; 1121 static final int GC_BACKGROUND_PROCESSES_MSG = 5; 1122 static final int WAIT_FOR_DEBUGGER_MSG = 6; 1123 static final int SERVICE_TIMEOUT_MSG = 12; 1124 static final int UPDATE_TIME_ZONE = 13; 1125 static final int SHOW_UID_ERROR_MSG = 14; 1126 static final int IM_FEELING_LUCKY_MSG = 15; 1127 static final int PROC_START_TIMEOUT_MSG = 20; 1128 static final int DO_PENDING_ACTIVITY_LAUNCHES_MSG = 21; 1129 static final int KILL_APPLICATION_MSG = 22; 1130 static final int FINALIZE_PENDING_INTENT_MSG = 23; 1131 static final int POST_HEAVY_NOTIFICATION_MSG = 24; 1132 static final int CANCEL_HEAVY_NOTIFICATION_MSG = 25; 1133 static final int SHOW_STRICT_MODE_VIOLATION_MSG = 26; 1134 static final int CHECK_EXCESSIVE_WAKE_LOCKS_MSG = 27; 1135 static final int CLEAR_DNS_CACHE_MSG = 28; 1136 static final int UPDATE_HTTP_PROXY_MSG = 29; 1137 static final int SHOW_COMPAT_MODE_DIALOG_MSG = 30; 1138 static final int DISPATCH_PROCESSES_CHANGED = 31; 1139 static final int DISPATCH_PROCESS_DIED = 32; 1140 static final int REPORT_MEM_USAGE_MSG = 33; 1141 static final int REPORT_USER_SWITCH_MSG = 34; 1142 static final int CONTINUE_USER_SWITCH_MSG = 35; 1143 static final int USER_SWITCH_TIMEOUT_MSG = 36; 1144 static final int IMMERSIVE_MODE_LOCK_MSG = 37; 1145 static final int PERSIST_URI_GRANTS_MSG = 38; 1146 static final int REQUEST_ALL_PSS_MSG = 39; 1147 static final int START_PROFILES_MSG = 40; 1148 static final int UPDATE_TIME = 41; 1149 static final int SYSTEM_USER_START_MSG = 42; 1150 static final int SYSTEM_USER_CURRENT_MSG = 43; 1151 1152 static final int FIRST_ACTIVITY_STACK_MSG = 100; 1153 static final int FIRST_BROADCAST_QUEUE_MSG = 200; 1154 static final int FIRST_COMPAT_MODE_MSG = 300; 1155 static final int FIRST_SUPERVISOR_STACK_MSG = 100; 1156 1157 AlertDialog mUidAlert; 1158 CompatModeDialog mCompatModeDialog; 1159 long mLastMemUsageReportTime = 0; 1160 1161 /** 1162 * Flag whether the current user is a "monkey", i.e. whether 1163 * the UI is driven by a UI automation tool. 1164 */ 1165 private boolean mUserIsMonkey; 1166 1167 final ServiceThread mHandlerThread; 1168 final MainHandler mHandler; 1169 1170 final class MainHandler extends Handler { 1171 public MainHandler(Looper looper) { 1172 super(looper, null, true); 1173 } 1174 1175 @Override 1176 public void handleMessage(Message msg) { 1177 switch (msg.what) { 1178 case SHOW_ERROR_MSG: { 1179 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1180 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 1181 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 1182 synchronized (ActivityManagerService.this) { 1183 ProcessRecord proc = (ProcessRecord)data.get("app"); 1184 AppErrorResult res = (AppErrorResult) data.get("result"); 1185 if (proc != null && proc.crashDialog != null) { 1186 Slog.e(TAG, "App already has crash dialog: " + proc); 1187 if (res != null) { 1188 res.set(0); 1189 } 1190 return; 1191 } 1192 if (!showBackground && UserHandle.getAppId(proc.uid) 1193 >= Process.FIRST_APPLICATION_UID && proc.userId != mCurrentUserId 1194 && proc.pid != MY_PID) { 1195 Slog.w(TAG, "Skipping crash dialog of " + proc + ": background"); 1196 if (res != null) { 1197 res.set(0); 1198 } 1199 return; 1200 } 1201 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1202 Dialog d = new AppErrorDialog(mContext, 1203 ActivityManagerService.this, res, proc); 1204 d.show(); 1205 proc.crashDialog = d; 1206 } else { 1207 // The device is asleep, so just pretend that the user 1208 // saw a crash dialog and hit "force quit". 1209 if (res != null) { 1210 res.set(0); 1211 } 1212 } 1213 } 1214 1215 ensureBootCompleted(); 1216 } break; 1217 case SHOW_NOT_RESPONDING_MSG: { 1218 synchronized (ActivityManagerService.this) { 1219 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1220 ProcessRecord proc = (ProcessRecord)data.get("app"); 1221 if (proc != null && proc.anrDialog != null) { 1222 Slog.e(TAG, "App already has anr dialog: " + proc); 1223 return; 1224 } 1225 1226 Intent intent = new Intent("android.intent.action.ANR"); 1227 if (!mProcessesReady) { 1228 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 1229 | Intent.FLAG_RECEIVER_FOREGROUND); 1230 } 1231 broadcastIntentLocked(null, null, intent, 1232 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 1233 false, false, MY_PID, Process.SYSTEM_UID, 0 /* TODO: Verify */); 1234 1235 if (mShowDialogs) { 1236 Dialog d = new AppNotRespondingDialog(ActivityManagerService.this, 1237 mContext, proc, (ActivityRecord)data.get("activity"), 1238 msg.arg1 != 0); 1239 d.show(); 1240 proc.anrDialog = d; 1241 } else { 1242 // Just kill the app if there is no dialog to be shown. 1243 killAppAtUsersRequest(proc, null); 1244 } 1245 } 1246 1247 ensureBootCompleted(); 1248 } break; 1249 case SHOW_STRICT_MODE_VIOLATION_MSG: { 1250 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1251 synchronized (ActivityManagerService.this) { 1252 ProcessRecord proc = (ProcessRecord) data.get("app"); 1253 if (proc == null) { 1254 Slog.e(TAG, "App not found when showing strict mode dialog."); 1255 break; 1256 } 1257 if (proc.crashDialog != null) { 1258 Slog.e(TAG, "App already has strict mode dialog: " + proc); 1259 return; 1260 } 1261 AppErrorResult res = (AppErrorResult) data.get("result"); 1262 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1263 Dialog d = new StrictModeViolationDialog(mContext, 1264 ActivityManagerService.this, res, proc); 1265 d.show(); 1266 proc.crashDialog = d; 1267 } else { 1268 // The device is asleep, so just pretend that the user 1269 // saw a crash dialog and hit "force quit". 1270 res.set(0); 1271 } 1272 } 1273 ensureBootCompleted(); 1274 } break; 1275 case SHOW_FACTORY_ERROR_MSG: { 1276 Dialog d = new FactoryErrorDialog( 1277 mContext, msg.getData().getCharSequence("msg")); 1278 d.show(); 1279 ensureBootCompleted(); 1280 } break; 1281 case UPDATE_CONFIGURATION_MSG: { 1282 final ContentResolver resolver = mContext.getContentResolver(); 1283 Settings.System.putConfiguration(resolver, (Configuration)msg.obj); 1284 } break; 1285 case GC_BACKGROUND_PROCESSES_MSG: { 1286 synchronized (ActivityManagerService.this) { 1287 performAppGcsIfAppropriateLocked(); 1288 } 1289 } break; 1290 case WAIT_FOR_DEBUGGER_MSG: { 1291 synchronized (ActivityManagerService.this) { 1292 ProcessRecord app = (ProcessRecord)msg.obj; 1293 if (msg.arg1 != 0) { 1294 if (!app.waitedForDebugger) { 1295 Dialog d = new AppWaitingForDebuggerDialog( 1296 ActivityManagerService.this, 1297 mContext, app); 1298 app.waitDialog = d; 1299 app.waitedForDebugger = true; 1300 d.show(); 1301 } 1302 } else { 1303 if (app.waitDialog != null) { 1304 app.waitDialog.dismiss(); 1305 app.waitDialog = null; 1306 } 1307 } 1308 } 1309 } break; 1310 case SERVICE_TIMEOUT_MSG: { 1311 if (mDidDexOpt) { 1312 mDidDexOpt = false; 1313 Message nmsg = mHandler.obtainMessage(SERVICE_TIMEOUT_MSG); 1314 nmsg.obj = msg.obj; 1315 mHandler.sendMessageDelayed(nmsg, ActiveServices.SERVICE_TIMEOUT); 1316 return; 1317 } 1318 mServices.serviceTimeout((ProcessRecord)msg.obj); 1319 } break; 1320 case UPDATE_TIME_ZONE: { 1321 synchronized (ActivityManagerService.this) { 1322 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1323 ProcessRecord r = mLruProcesses.get(i); 1324 if (r.thread != null) { 1325 try { 1326 r.thread.updateTimeZone(); 1327 } catch (RemoteException ex) { 1328 Slog.w(TAG, "Failed to update time zone for: " + r.info.processName); 1329 } 1330 } 1331 } 1332 } 1333 } break; 1334 case CLEAR_DNS_CACHE_MSG: { 1335 synchronized (ActivityManagerService.this) { 1336 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1337 ProcessRecord r = mLruProcesses.get(i); 1338 if (r.thread != null) { 1339 try { 1340 r.thread.clearDnsCache(); 1341 } catch (RemoteException ex) { 1342 Slog.w(TAG, "Failed to clear dns cache for: " + r.info.processName); 1343 } 1344 } 1345 } 1346 } 1347 } break; 1348 case UPDATE_HTTP_PROXY_MSG: { 1349 ProxyInfo proxy = (ProxyInfo)msg.obj; 1350 String host = ""; 1351 String port = ""; 1352 String exclList = ""; 1353 Uri pacFileUrl = Uri.EMPTY; 1354 if (proxy != null) { 1355 host = proxy.getHost(); 1356 port = Integer.toString(proxy.getPort()); 1357 exclList = proxy.getExclusionListAsString(); 1358 pacFileUrl = proxy.getPacFileUrl(); 1359 } 1360 synchronized (ActivityManagerService.this) { 1361 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1362 ProcessRecord r = mLruProcesses.get(i); 1363 if (r.thread != null) { 1364 try { 1365 r.thread.setHttpProxy(host, port, exclList, pacFileUrl); 1366 } catch (RemoteException ex) { 1367 Slog.w(TAG, "Failed to update http proxy for: " + 1368 r.info.processName); 1369 } 1370 } 1371 } 1372 } 1373 } break; 1374 case SHOW_UID_ERROR_MSG: { 1375 String title = "System UIDs Inconsistent"; 1376 String text = "UIDs on the system are inconsistent, you need to wipe your" 1377 + " data partition or your device will be unstable."; 1378 Log.e(TAG, title + ": " + text); 1379 if (mShowDialogs) { 1380 // XXX This is a temporary dialog, no need to localize. 1381 AlertDialog d = new BaseErrorDialog(mContext); 1382 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 1383 d.setCancelable(false); 1384 d.setTitle(title); 1385 d.setMessage(text); 1386 d.setButton(DialogInterface.BUTTON_POSITIVE, "I'm Feeling Lucky", 1387 mHandler.obtainMessage(IM_FEELING_LUCKY_MSG)); 1388 mUidAlert = d; 1389 d.show(); 1390 } 1391 } break; 1392 case IM_FEELING_LUCKY_MSG: { 1393 if (mUidAlert != null) { 1394 mUidAlert.dismiss(); 1395 mUidAlert = null; 1396 } 1397 } break; 1398 case PROC_START_TIMEOUT_MSG: { 1399 if (mDidDexOpt) { 1400 mDidDexOpt = false; 1401 Message nmsg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 1402 nmsg.obj = msg.obj; 1403 mHandler.sendMessageDelayed(nmsg, PROC_START_TIMEOUT); 1404 return; 1405 } 1406 ProcessRecord app = (ProcessRecord)msg.obj; 1407 synchronized (ActivityManagerService.this) { 1408 processStartTimedOutLocked(app); 1409 } 1410 } break; 1411 case DO_PENDING_ACTIVITY_LAUNCHES_MSG: { 1412 synchronized (ActivityManagerService.this) { 1413 doPendingActivityLaunchesLocked(true); 1414 } 1415 } break; 1416 case KILL_APPLICATION_MSG: { 1417 synchronized (ActivityManagerService.this) { 1418 int appid = msg.arg1; 1419 boolean restart = (msg.arg2 == 1); 1420 Bundle bundle = (Bundle)msg.obj; 1421 String pkg = bundle.getString("pkg"); 1422 String reason = bundle.getString("reason"); 1423 forceStopPackageLocked(pkg, appid, restart, false, true, false, 1424 false, UserHandle.USER_ALL, reason); 1425 } 1426 } break; 1427 case FINALIZE_PENDING_INTENT_MSG: { 1428 ((PendingIntentRecord)msg.obj).completeFinalize(); 1429 } break; 1430 case POST_HEAVY_NOTIFICATION_MSG: { 1431 INotificationManager inm = NotificationManager.getService(); 1432 if (inm == null) { 1433 return; 1434 } 1435 1436 ActivityRecord root = (ActivityRecord)msg.obj; 1437 ProcessRecord process = root.app; 1438 if (process == null) { 1439 return; 1440 } 1441 1442 try { 1443 Context context = mContext.createPackageContext(process.info.packageName, 0); 1444 String text = mContext.getString(R.string.heavy_weight_notification, 1445 context.getApplicationInfo().loadLabel(context.getPackageManager())); 1446 Notification notification = new Notification(); 1447 notification.icon = com.android.internal.R.drawable.stat_sys_adb; //context.getApplicationInfo().icon; 1448 notification.when = 0; 1449 notification.flags = Notification.FLAG_ONGOING_EVENT; 1450 notification.tickerText = text; 1451 notification.defaults = 0; // please be quiet 1452 notification.sound = null; 1453 notification.vibrate = null; 1454 notification.setLatestEventInfo(context, text, 1455 mContext.getText(R.string.heavy_weight_notification_detail), 1456 PendingIntent.getActivityAsUser(mContext, 0, root.intent, 1457 PendingIntent.FLAG_CANCEL_CURRENT, null, 1458 new UserHandle(root.userId))); 1459 1460 try { 1461 int[] outId = new int[1]; 1462 inm.enqueueNotificationWithTag("android", "android", null, 1463 R.string.heavy_weight_notification, 1464 notification, outId, root.userId); 1465 } catch (RuntimeException e) { 1466 Slog.w(ActivityManagerService.TAG, 1467 "Error showing notification for heavy-weight app", e); 1468 } catch (RemoteException e) { 1469 } 1470 } catch (NameNotFoundException e) { 1471 Slog.w(TAG, "Unable to create context for heavy notification", e); 1472 } 1473 } break; 1474 case CANCEL_HEAVY_NOTIFICATION_MSG: { 1475 INotificationManager inm = NotificationManager.getService(); 1476 if (inm == null) { 1477 return; 1478 } 1479 try { 1480 inm.cancelNotificationWithTag("android", null, 1481 R.string.heavy_weight_notification, msg.arg1); 1482 } catch (RuntimeException e) { 1483 Slog.w(ActivityManagerService.TAG, 1484 "Error canceling notification for service", e); 1485 } catch (RemoteException e) { 1486 } 1487 } break; 1488 case CHECK_EXCESSIVE_WAKE_LOCKS_MSG: { 1489 synchronized (ActivityManagerService.this) { 1490 checkExcessivePowerUsageLocked(true); 1491 removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1492 Message nmsg = obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1493 sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 1494 } 1495 } break; 1496 case SHOW_COMPAT_MODE_DIALOG_MSG: { 1497 synchronized (ActivityManagerService.this) { 1498 ActivityRecord ar = (ActivityRecord)msg.obj; 1499 if (mCompatModeDialog != null) { 1500 if (mCompatModeDialog.mAppInfo.packageName.equals( 1501 ar.info.applicationInfo.packageName)) { 1502 return; 1503 } 1504 mCompatModeDialog.dismiss(); 1505 mCompatModeDialog = null; 1506 } 1507 if (ar != null && false) { 1508 if (mCompatModePackages.getPackageAskCompatModeLocked( 1509 ar.packageName)) { 1510 int mode = mCompatModePackages.computeCompatModeLocked( 1511 ar.info.applicationInfo); 1512 if (mode == ActivityManager.COMPAT_MODE_DISABLED 1513 || mode == ActivityManager.COMPAT_MODE_ENABLED) { 1514 mCompatModeDialog = new CompatModeDialog( 1515 ActivityManagerService.this, mContext, 1516 ar.info.applicationInfo); 1517 mCompatModeDialog.show(); 1518 } 1519 } 1520 } 1521 } 1522 break; 1523 } 1524 case DISPATCH_PROCESSES_CHANGED: { 1525 dispatchProcessesChanged(); 1526 break; 1527 } 1528 case DISPATCH_PROCESS_DIED: { 1529 final int pid = msg.arg1; 1530 final int uid = msg.arg2; 1531 dispatchProcessDied(pid, uid); 1532 break; 1533 } 1534 case REPORT_MEM_USAGE_MSG: { 1535 final ArrayList<ProcessMemInfo> memInfos = (ArrayList<ProcessMemInfo>)msg.obj; 1536 Thread thread = new Thread() { 1537 @Override public void run() { 1538 final SparseArray<ProcessMemInfo> infoMap 1539 = new SparseArray<ProcessMemInfo>(memInfos.size()); 1540 for (int i=0, N=memInfos.size(); i<N; i++) { 1541 ProcessMemInfo mi = memInfos.get(i); 1542 infoMap.put(mi.pid, mi); 1543 } 1544 updateCpuStatsNow(); 1545 synchronized (mProcessCpuThread) { 1546 final int N = mProcessCpuTracker.countStats(); 1547 for (int i=0; i<N; i++) { 1548 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 1549 if (st.vsize > 0) { 1550 long pss = Debug.getPss(st.pid, null); 1551 if (pss > 0) { 1552 if (infoMap.indexOfKey(st.pid) < 0) { 1553 ProcessMemInfo mi = new ProcessMemInfo(st.name, st.pid, 1554 ProcessList.NATIVE_ADJ, -1, "native", null); 1555 mi.pss = pss; 1556 memInfos.add(mi); 1557 } 1558 } 1559 } 1560 } 1561 } 1562 1563 long totalPss = 0; 1564 for (int i=0, N=memInfos.size(); i<N; i++) { 1565 ProcessMemInfo mi = memInfos.get(i); 1566 if (mi.pss == 0) { 1567 mi.pss = Debug.getPss(mi.pid, null); 1568 } 1569 totalPss += mi.pss; 1570 } 1571 Collections.sort(memInfos, new Comparator<ProcessMemInfo>() { 1572 @Override public int compare(ProcessMemInfo lhs, ProcessMemInfo rhs) { 1573 if (lhs.oomAdj != rhs.oomAdj) { 1574 return lhs.oomAdj < rhs.oomAdj ? -1 : 1; 1575 } 1576 if (lhs.pss != rhs.pss) { 1577 return lhs.pss < rhs.pss ? 1 : -1; 1578 } 1579 return 0; 1580 } 1581 }); 1582 1583 StringBuilder tag = new StringBuilder(128); 1584 StringBuilder stack = new StringBuilder(128); 1585 tag.append("Low on memory -- "); 1586 appendMemBucket(tag, totalPss, "total", false); 1587 appendMemBucket(stack, totalPss, "total", true); 1588 1589 StringBuilder logBuilder = new StringBuilder(1024); 1590 logBuilder.append("Low on memory:\n"); 1591 1592 boolean firstLine = true; 1593 int lastOomAdj = Integer.MIN_VALUE; 1594 for (int i=0, N=memInfos.size(); i<N; i++) { 1595 ProcessMemInfo mi = memInfos.get(i); 1596 1597 if (mi.oomAdj != ProcessList.NATIVE_ADJ 1598 && (mi.oomAdj < ProcessList.SERVICE_ADJ 1599 || mi.oomAdj == ProcessList.HOME_APP_ADJ 1600 || mi.oomAdj == ProcessList.PREVIOUS_APP_ADJ)) { 1601 if (lastOomAdj != mi.oomAdj) { 1602 lastOomAdj = mi.oomAdj; 1603 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1604 tag.append(" / "); 1605 } 1606 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ) { 1607 if (firstLine) { 1608 stack.append(":"); 1609 firstLine = false; 1610 } 1611 stack.append("\n\t at "); 1612 } else { 1613 stack.append("$"); 1614 } 1615 } else { 1616 tag.append(" "); 1617 stack.append("$"); 1618 } 1619 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1620 appendMemBucket(tag, mi.pss, mi.name, false); 1621 } 1622 appendMemBucket(stack, mi.pss, mi.name, true); 1623 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ 1624 && ((i+1) >= N || memInfos.get(i+1).oomAdj != lastOomAdj)) { 1625 stack.append("("); 1626 for (int k=0; k<DUMP_MEM_OOM_ADJ.length; k++) { 1627 if (DUMP_MEM_OOM_ADJ[k] == mi.oomAdj) { 1628 stack.append(DUMP_MEM_OOM_LABEL[k]); 1629 stack.append(":"); 1630 stack.append(DUMP_MEM_OOM_ADJ[k]); 1631 } 1632 } 1633 stack.append(")"); 1634 } 1635 } 1636 1637 logBuilder.append(" "); 1638 logBuilder.append(ProcessList.makeOomAdjString(mi.oomAdj)); 1639 logBuilder.append(' '); 1640 logBuilder.append(ProcessList.makeProcStateString(mi.procState)); 1641 logBuilder.append(' '); 1642 ProcessList.appendRamKb(logBuilder, mi.pss); 1643 logBuilder.append(" kB: "); 1644 logBuilder.append(mi.name); 1645 logBuilder.append(" ("); 1646 logBuilder.append(mi.pid); 1647 logBuilder.append(") "); 1648 logBuilder.append(mi.adjType); 1649 logBuilder.append('\n'); 1650 if (mi.adjReason != null) { 1651 logBuilder.append(" "); 1652 logBuilder.append(mi.adjReason); 1653 logBuilder.append('\n'); 1654 } 1655 } 1656 1657 logBuilder.append(" "); 1658 ProcessList.appendRamKb(logBuilder, totalPss); 1659 logBuilder.append(" kB: TOTAL\n"); 1660 1661 long[] infos = new long[Debug.MEMINFO_COUNT]; 1662 Debug.getMemInfo(infos); 1663 logBuilder.append(" MemInfo: "); 1664 logBuilder.append(infos[Debug.MEMINFO_SLAB]).append(" kB slab, "); 1665 logBuilder.append(infos[Debug.MEMINFO_SHMEM]).append(" kB shmem, "); 1666 logBuilder.append(infos[Debug.MEMINFO_BUFFERS]).append(" kB buffers, "); 1667 logBuilder.append(infos[Debug.MEMINFO_CACHED]).append(" kB cached, "); 1668 logBuilder.append(infos[Debug.MEMINFO_FREE]).append(" kB free\n"); 1669 if (infos[Debug.MEMINFO_ZRAM_TOTAL] != 0) { 1670 logBuilder.append(" ZRAM: "); 1671 logBuilder.append(infos[Debug.MEMINFO_ZRAM_TOTAL]); 1672 logBuilder.append(" kB RAM, "); 1673 logBuilder.append(infos[Debug.MEMINFO_SWAP_TOTAL]); 1674 logBuilder.append(" kB swap total, "); 1675 logBuilder.append(infos[Debug.MEMINFO_SWAP_FREE]); 1676 logBuilder.append(" kB swap free\n"); 1677 } 1678 Slog.i(TAG, logBuilder.toString()); 1679 1680 StringBuilder dropBuilder = new StringBuilder(1024); 1681 /* 1682 StringWriter oomSw = new StringWriter(); 1683 PrintWriter oomPw = new FastPrintWriter(oomSw, false, 256); 1684 StringWriter catSw = new StringWriter(); 1685 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1686 String[] emptyArgs = new String[] { }; 1687 dumpApplicationMemoryUsage(null, oomPw, " ", emptyArgs, true, catPw); 1688 oomPw.flush(); 1689 String oomString = oomSw.toString(); 1690 */ 1691 dropBuilder.append(stack); 1692 dropBuilder.append('\n'); 1693 dropBuilder.append('\n'); 1694 dropBuilder.append(logBuilder); 1695 dropBuilder.append('\n'); 1696 /* 1697 dropBuilder.append(oomString); 1698 dropBuilder.append('\n'); 1699 */ 1700 StringWriter catSw = new StringWriter(); 1701 synchronized (ActivityManagerService.this) { 1702 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1703 String[] emptyArgs = new String[] { }; 1704 catPw.println(); 1705 dumpProcessesLocked(null, catPw, emptyArgs, 0, false, null); 1706 catPw.println(); 1707 mServices.dumpServicesLocked(null, catPw, emptyArgs, 0, 1708 false, false, null); 1709 catPw.println(); 1710 dumpActivitiesLocked(null, catPw, emptyArgs, 0, false, false, null); 1711 catPw.flush(); 1712 } 1713 dropBuilder.append(catSw.toString()); 1714 addErrorToDropBox("lowmem", null, "system_server", null, 1715 null, tag.toString(), dropBuilder.toString(), null, null); 1716 //Slog.i(TAG, "Sent to dropbox:"); 1717 //Slog.i(TAG, dropBuilder.toString()); 1718 synchronized (ActivityManagerService.this) { 1719 long now = SystemClock.uptimeMillis(); 1720 if (mLastMemUsageReportTime < now) { 1721 mLastMemUsageReportTime = now; 1722 } 1723 } 1724 } 1725 }; 1726 thread.start(); 1727 break; 1728 } 1729 case REPORT_USER_SWITCH_MSG: { 1730 dispatchUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1731 break; 1732 } 1733 case CONTINUE_USER_SWITCH_MSG: { 1734 continueUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1735 break; 1736 } 1737 case USER_SWITCH_TIMEOUT_MSG: { 1738 timeoutUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1739 break; 1740 } 1741 case IMMERSIVE_MODE_LOCK_MSG: { 1742 final boolean nextState = (msg.arg1 != 0); 1743 if (mUpdateLock.isHeld() != nextState) { 1744 if (DEBUG_IMMERSIVE) { 1745 final ActivityRecord r = (ActivityRecord) msg.obj; 1746 Slog.d(TAG, "Applying new update lock state '" + nextState + "' for " + r); 1747 } 1748 if (nextState) { 1749 mUpdateLock.acquire(); 1750 } else { 1751 mUpdateLock.release(); 1752 } 1753 } 1754 break; 1755 } 1756 case PERSIST_URI_GRANTS_MSG: { 1757 writeGrantedUriPermissions(); 1758 break; 1759 } 1760 case REQUEST_ALL_PSS_MSG: { 1761 requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, false); 1762 break; 1763 } 1764 case START_PROFILES_MSG: { 1765 synchronized (ActivityManagerService.this) { 1766 startProfilesLocked(); 1767 } 1768 break; 1769 } 1770 case UPDATE_TIME: { 1771 synchronized (ActivityManagerService.this) { 1772 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1773 ProcessRecord r = mLruProcesses.get(i); 1774 if (r.thread != null) { 1775 try { 1776 r.thread.updateTimePrefs(msg.arg1 == 0 ? false : true); 1777 } catch (RemoteException ex) { 1778 Slog.w(TAG, "Failed to update preferences for: " + r.info.processName); 1779 } 1780 } 1781 } 1782 } 1783 break; 1784 } 1785 case SYSTEM_USER_START_MSG: { 1786 mSystemServiceManager.startUser(msg.arg1); 1787 break; 1788 } 1789 case SYSTEM_USER_CURRENT_MSG: { 1790 mSystemServiceManager.switchUser(msg.arg1); 1791 break; 1792 } 1793 } 1794 } 1795 }; 1796 1797 static final int COLLECT_PSS_BG_MSG = 1; 1798 1799 final Handler mBgHandler = new Handler(BackgroundThread.getHandler().getLooper()) { 1800 @Override 1801 public void handleMessage(Message msg) { 1802 switch (msg.what) { 1803 case COLLECT_PSS_BG_MSG: { 1804 int i=0, num=0; 1805 long start = SystemClock.uptimeMillis(); 1806 long[] tmp = new long[1]; 1807 do { 1808 ProcessRecord proc; 1809 int procState; 1810 int pid; 1811 synchronized (ActivityManagerService.this) { 1812 if (i >= mPendingPssProcesses.size()) { 1813 if (DEBUG_PSS) Slog.d(TAG, "Collected PSS of " + num + " of " + i 1814 + " processes in " + (SystemClock.uptimeMillis()-start) + "ms"); 1815 mPendingPssProcesses.clear(); 1816 return; 1817 } 1818 proc = mPendingPssProcesses.get(i); 1819 procState = proc.pssProcState; 1820 if (proc.thread != null && procState == proc.setProcState) { 1821 pid = proc.pid; 1822 } else { 1823 proc = null; 1824 pid = 0; 1825 } 1826 i++; 1827 } 1828 if (proc != null) { 1829 long pss = Debug.getPss(pid, tmp); 1830 synchronized (ActivityManagerService.this) { 1831 if (proc.thread != null && proc.setProcState == procState 1832 && proc.pid == pid) { 1833 num++; 1834 proc.lastPssTime = SystemClock.uptimeMillis(); 1835 proc.baseProcessTracker.addPss(pss, tmp[0], true, proc.pkgList); 1836 if (DEBUG_PSS) Slog.d(TAG, "PSS of " + proc.toShortString() 1837 + ": " + pss + " lastPss=" + proc.lastPss 1838 + " state=" + ProcessList.makeProcStateString(procState)); 1839 if (proc.initialIdlePss == 0) { 1840 proc.initialIdlePss = pss; 1841 } 1842 proc.lastPss = pss; 1843 if (procState >= ActivityManager.PROCESS_STATE_HOME) { 1844 proc.lastCachedPss = pss; 1845 } 1846 } 1847 } 1848 } 1849 } while (true); 1850 } 1851 } 1852 } 1853 }; 1854 1855 /** 1856 * Monitor for package changes and update our internal state. 1857 */ 1858 private final PackageMonitor mPackageMonitor = new PackageMonitor() { 1859 @Override 1860 public void onPackageRemoved(String packageName, int uid) { 1861 // Remove all tasks with activities in the specified package from the list of recent tasks 1862 synchronized (ActivityManagerService.this) { 1863 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 1864 TaskRecord tr = mRecentTasks.get(i); 1865 ComponentName cn = tr.intent.getComponent(); 1866 if (cn != null && cn.getPackageName().equals(packageName)) { 1867 // If the package name matches, remove the task and kill the process 1868 removeTaskByIdLocked(tr.taskId, ActivityManager.REMOVE_TASK_KILL_PROCESS); 1869 } 1870 } 1871 } 1872 } 1873 1874 @Override 1875 public boolean onPackageChanged(String packageName, int uid, String[] components) { 1876 onPackageModified(packageName); 1877 return true; 1878 } 1879 1880 @Override 1881 public void onPackageModified(String packageName) { 1882 final PackageManager pm = mContext.getPackageManager(); 1883 final ArrayList<Pair<Intent, Integer>> recentTaskIntents = 1884 new ArrayList<Pair<Intent, Integer>>(); 1885 final ArrayList<Integer> tasksToRemove = new ArrayList<Integer>(); 1886 // Copy the list of recent tasks so that we don't hold onto the lock on 1887 // ActivityManagerService for long periods while checking if components exist. 1888 synchronized (ActivityManagerService.this) { 1889 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 1890 TaskRecord tr = mRecentTasks.get(i); 1891 recentTaskIntents.add(new Pair<Intent, Integer>(tr.intent, tr.taskId)); 1892 } 1893 } 1894 // Check the recent tasks and filter out all tasks with components that no longer exist. 1895 Intent tmpI = new Intent(); 1896 for (int i = recentTaskIntents.size() - 1; i >= 0; i--) { 1897 Pair<Intent, Integer> p = recentTaskIntents.get(i); 1898 ComponentName cn = p.first.getComponent(); 1899 if (cn != null && cn.getPackageName().equals(packageName)) { 1900 try { 1901 // Add the task to the list to remove if the component no longer exists 1902 tmpI.setComponent(cn); 1903 if (pm.queryIntentActivities(tmpI, PackageManager.MATCH_DEFAULT_ONLY).isEmpty()) { 1904 tasksToRemove.add(p.second); 1905 } 1906 } catch (Exception e) {} 1907 } 1908 } 1909 // Prune all the tasks with removed components from the list of recent tasks 1910 synchronized (ActivityManagerService.this) { 1911 for (int i = tasksToRemove.size() - 1; i >= 0; i--) { 1912 // Remove the task but don't kill the process (since other components in that 1913 // package may still be running and in the background) 1914 removeTaskByIdLocked(tasksToRemove.get(i), 0); 1915 } 1916 } 1917 } 1918 1919 @Override 1920 public boolean onHandleForceStop(Intent intent, String[] packages, int uid, boolean doit) { 1921 // Force stop the specified packages 1922 if (packages != null) { 1923 for (String pkg : packages) { 1924 synchronized (ActivityManagerService.this) { 1925 if (forceStopPackageLocked(pkg, -1, false, false, false, false, false, 0, 1926 "finished booting")) { 1927 return true; 1928 } 1929 } 1930 } 1931 } 1932 return false; 1933 } 1934 }; 1935 1936 public void setSystemProcess() { 1937 try { 1938 ServiceManager.addService(Context.ACTIVITY_SERVICE, this, true); 1939 ServiceManager.addService(ProcessStats.SERVICE_NAME, mProcessStats); 1940 ServiceManager.addService("meminfo", new MemBinder(this)); 1941 ServiceManager.addService("gfxinfo", new GraphicsBinder(this)); 1942 ServiceManager.addService("dbinfo", new DbBinder(this)); 1943 if (MONITOR_CPU_USAGE) { 1944 ServiceManager.addService("cpuinfo", new CpuBinder(this)); 1945 } 1946 ServiceManager.addService("permission", new PermissionController(this)); 1947 1948 ApplicationInfo info = mContext.getPackageManager().getApplicationInfo( 1949 "android", STOCK_PM_FLAGS); 1950 mSystemThread.installSystemApplicationInfo(info); 1951 1952 synchronized (this) { 1953 ProcessRecord app = newProcessRecordLocked(info, info.processName, false); 1954 app.persistent = true; 1955 app.pid = MY_PID; 1956 app.maxAdj = ProcessList.SYSTEM_ADJ; 1957 app.makeActive(mSystemThread.getApplicationThread(), mProcessStats); 1958 mProcessNames.put(app.processName, app.uid, app); 1959 synchronized (mPidsSelfLocked) { 1960 mPidsSelfLocked.put(app.pid, app); 1961 } 1962 updateLruProcessLocked(app, false, null); 1963 updateOomAdjLocked(); 1964 } 1965 } catch (PackageManager.NameNotFoundException e) { 1966 throw new RuntimeException( 1967 "Unable to find android system package", e); 1968 } 1969 } 1970 1971 public void setWindowManager(WindowManagerService wm) { 1972 mWindowManager = wm; 1973 mStackSupervisor.setWindowManager(wm); 1974 } 1975 1976 public void startObservingNativeCrashes() { 1977 final NativeCrashListener ncl = new NativeCrashListener(this); 1978 ncl.start(); 1979 } 1980 1981 public IAppOpsService getAppOpsService() { 1982 return mAppOpsService; 1983 } 1984 1985 static class MemBinder extends Binder { 1986 ActivityManagerService mActivityManagerService; 1987 MemBinder(ActivityManagerService activityManagerService) { 1988 mActivityManagerService = activityManagerService; 1989 } 1990 1991 @Override 1992 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 1993 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 1994 != PackageManager.PERMISSION_GRANTED) { 1995 pw.println("Permission Denial: can't dump meminfo from from pid=" 1996 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 1997 + " without permission " + android.Manifest.permission.DUMP); 1998 return; 1999 } 2000 2001 mActivityManagerService.dumpApplicationMemoryUsage(fd, pw, " ", args, false, null); 2002 } 2003 } 2004 2005 static class GraphicsBinder extends Binder { 2006 ActivityManagerService mActivityManagerService; 2007 GraphicsBinder(ActivityManagerService activityManagerService) { 2008 mActivityManagerService = activityManagerService; 2009 } 2010 2011 @Override 2012 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2013 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2014 != PackageManager.PERMISSION_GRANTED) { 2015 pw.println("Permission Denial: can't dump gfxinfo from from pid=" 2016 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2017 + " without permission " + android.Manifest.permission.DUMP); 2018 return; 2019 } 2020 2021 mActivityManagerService.dumpGraphicsHardwareUsage(fd, pw, args); 2022 } 2023 } 2024 2025 static class DbBinder extends Binder { 2026 ActivityManagerService mActivityManagerService; 2027 DbBinder(ActivityManagerService activityManagerService) { 2028 mActivityManagerService = activityManagerService; 2029 } 2030 2031 @Override 2032 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2033 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2034 != PackageManager.PERMISSION_GRANTED) { 2035 pw.println("Permission Denial: can't dump dbinfo from from pid=" 2036 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2037 + " without permission " + android.Manifest.permission.DUMP); 2038 return; 2039 } 2040 2041 mActivityManagerService.dumpDbInfo(fd, pw, args); 2042 } 2043 } 2044 2045 static class CpuBinder extends Binder { 2046 ActivityManagerService mActivityManagerService; 2047 CpuBinder(ActivityManagerService activityManagerService) { 2048 mActivityManagerService = activityManagerService; 2049 } 2050 2051 @Override 2052 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2053 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2054 != PackageManager.PERMISSION_GRANTED) { 2055 pw.println("Permission Denial: can't dump cpuinfo from from pid=" 2056 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2057 + " without permission " + android.Manifest.permission.DUMP); 2058 return; 2059 } 2060 2061 synchronized (mActivityManagerService.mProcessCpuThread) { 2062 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentLoad()); 2063 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentState( 2064 SystemClock.uptimeMillis())); 2065 } 2066 } 2067 } 2068 2069 public static final class Lifecycle extends SystemService { 2070 private final ActivityManagerService mService; 2071 2072 public Lifecycle(Context context) { 2073 super(context); 2074 mService = new ActivityManagerService(context); 2075 } 2076 2077 @Override 2078 public void onStart() { 2079 mService.start(); 2080 } 2081 2082 public ActivityManagerService getService() { 2083 return mService; 2084 } 2085 } 2086 2087 // Note: This method is invoked on the main thread but may need to attach various 2088 // handlers to other threads. So take care to be explicit about the looper. 2089 public ActivityManagerService(Context systemContext) { 2090 mContext = systemContext; 2091 mFactoryTest = FactoryTest.getMode(); 2092 mSystemThread = ActivityThread.currentActivityThread(); 2093 2094 Slog.i(TAG, "Memory class: " + ActivityManager.staticGetMemoryClass()); 2095 2096 mHandlerThread = new ServiceThread(TAG, 2097 android.os.Process.THREAD_PRIORITY_FOREGROUND, false /*allowIo*/); 2098 mHandlerThread.start(); 2099 mHandler = new MainHandler(mHandlerThread.getLooper()); 2100 2101 mFgBroadcastQueue = new BroadcastQueue(this, mHandler, 2102 "foreground", BROADCAST_FG_TIMEOUT, false); 2103 mBgBroadcastQueue = new BroadcastQueue(this, mHandler, 2104 "background", BROADCAST_BG_TIMEOUT, true); 2105 mBroadcastQueues[0] = mFgBroadcastQueue; 2106 mBroadcastQueues[1] = mBgBroadcastQueue; 2107 2108 mServices = new ActiveServices(this); 2109 mProviderMap = new ProviderMap(this); 2110 2111 // TODO: Move creation of battery stats service outside of activity manager service. 2112 File dataDir = Environment.getDataDirectory(); 2113 File systemDir = new File(dataDir, "system"); 2114 systemDir.mkdirs(); 2115 mBatteryStatsService = new BatteryStatsService(new File( 2116 systemDir, "batterystats.bin").toString(), mHandler); 2117 mBatteryStatsService.getActiveStatistics().readLocked(); 2118 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2119 mOnBattery = DEBUG_POWER ? true 2120 : mBatteryStatsService.getActiveStatistics().getIsOnBattery(); 2121 mBatteryStatsService.getActiveStatistics().setCallback(this); 2122 2123 mProcessStats = new ProcessStatsService(this, new File(systemDir, "procstats")); 2124 2125 mUsageStatsService = new UsageStatsService(new File(systemDir, "usagestats").toString()); 2126 mAppOpsService = new AppOpsService(new File(systemDir, "appops.xml"), mHandler); 2127 2128 mGrantFile = new AtomicFile(new File(systemDir, "urigrants.xml")); 2129 2130 // User 0 is the first and only user that runs at boot. 2131 mStartedUsers.put(0, new UserStartedState(new UserHandle(0), true)); 2132 mUserLru.add(Integer.valueOf(0)); 2133 updateStartedUserArrayLocked(); 2134 2135 GL_ES_VERSION = SystemProperties.getInt("ro.opengles.version", 2136 ConfigurationInfo.GL_ES_VERSION_UNDEFINED); 2137 2138 mConfiguration.setToDefaults(); 2139 mConfiguration.setLocale(Locale.getDefault()); 2140 2141 mConfigurationSeq = mConfiguration.seq = 1; 2142 mProcessCpuTracker.init(); 2143 2144 mCompatModePackages = new CompatModePackages(this, systemDir, mHandler); 2145 mIntentFirewall = new IntentFirewall(new IntentFirewallInterface(), mHandler); 2146 mStackSupervisor = new ActivityStackSupervisor(this); 2147 mTaskPersister = new TaskPersister(systemDir, mStackSupervisor); 2148 2149 mProcessCpuThread = new Thread("CpuTracker") { 2150 @Override 2151 public void run() { 2152 while (true) { 2153 try { 2154 try { 2155 synchronized(this) { 2156 final long now = SystemClock.uptimeMillis(); 2157 long nextCpuDelay = (mLastCpuTime.get()+MONITOR_CPU_MAX_TIME)-now; 2158 long nextWriteDelay = (mLastWriteTime+BATTERY_STATS_TIME)-now; 2159 //Slog.i(TAG, "Cpu delay=" + nextCpuDelay 2160 // + ", write delay=" + nextWriteDelay); 2161 if (nextWriteDelay < nextCpuDelay) { 2162 nextCpuDelay = nextWriteDelay; 2163 } 2164 if (nextCpuDelay > 0) { 2165 mProcessCpuMutexFree.set(true); 2166 this.wait(nextCpuDelay); 2167 } 2168 } 2169 } catch (InterruptedException e) { 2170 } 2171 updateCpuStatsNow(); 2172 } catch (Exception e) { 2173 Slog.e(TAG, "Unexpected exception collecting process stats", e); 2174 } 2175 } 2176 } 2177 }; 2178 2179 Watchdog.getInstance().addMonitor(this); 2180 Watchdog.getInstance().addThread(mHandler); 2181 } 2182 2183 public void setSystemServiceManager(SystemServiceManager mgr) { 2184 mSystemServiceManager = mgr; 2185 } 2186 2187 private void start() { 2188 mProcessCpuThread.start(); 2189 2190 mBatteryStatsService.publish(mContext); 2191 mUsageStatsService.publish(mContext); 2192 mAppOpsService.publish(mContext); 2193 Slog.d("AppOps", "AppOpsService published"); 2194 LocalServices.addService(ActivityManagerInternal.class, new LocalService()); 2195 } 2196 2197 @Override 2198 public boolean onTransact(int code, Parcel data, Parcel reply, int flags) 2199 throws RemoteException { 2200 if (code == SYSPROPS_TRANSACTION) { 2201 // We need to tell all apps about the system property change. 2202 ArrayList<IBinder> procs = new ArrayList<IBinder>(); 2203 synchronized(this) { 2204 final int NP = mProcessNames.getMap().size(); 2205 for (int ip=0; ip<NP; ip++) { 2206 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 2207 final int NA = apps.size(); 2208 for (int ia=0; ia<NA; ia++) { 2209 ProcessRecord app = apps.valueAt(ia); 2210 if (app.thread != null) { 2211 procs.add(app.thread.asBinder()); 2212 } 2213 } 2214 } 2215 } 2216 2217 int N = procs.size(); 2218 for (int i=0; i<N; i++) { 2219 Parcel data2 = Parcel.obtain(); 2220 try { 2221 procs.get(i).transact(IBinder.SYSPROPS_TRANSACTION, data2, null, 0); 2222 } catch (RemoteException e) { 2223 } 2224 data2.recycle(); 2225 } 2226 } 2227 try { 2228 return super.onTransact(code, data, reply, flags); 2229 } catch (RuntimeException e) { 2230 // The activity manager only throws security exceptions, so let's 2231 // log all others. 2232 if (!(e instanceof SecurityException)) { 2233 Slog.wtf(TAG, "Activity Manager Crash", e); 2234 } 2235 throw e; 2236 } 2237 } 2238 2239 void updateCpuStats() { 2240 final long now = SystemClock.uptimeMillis(); 2241 if (mLastCpuTime.get() >= now - MONITOR_CPU_MIN_TIME) { 2242 return; 2243 } 2244 if (mProcessCpuMutexFree.compareAndSet(true, false)) { 2245 synchronized (mProcessCpuThread) { 2246 mProcessCpuThread.notify(); 2247 } 2248 } 2249 } 2250 2251 void updateCpuStatsNow() { 2252 synchronized (mProcessCpuThread) { 2253 mProcessCpuMutexFree.set(false); 2254 final long now = SystemClock.uptimeMillis(); 2255 boolean haveNewCpuStats = false; 2256 2257 if (MONITOR_CPU_USAGE && 2258 mLastCpuTime.get() < (now-MONITOR_CPU_MIN_TIME)) { 2259 mLastCpuTime.set(now); 2260 haveNewCpuStats = true; 2261 mProcessCpuTracker.update(); 2262 //Slog.i(TAG, mProcessCpu.printCurrentState()); 2263 //Slog.i(TAG, "Total CPU usage: " 2264 // + mProcessCpu.getTotalCpuPercent() + "%"); 2265 2266 // Slog the cpu usage if the property is set. 2267 if ("true".equals(SystemProperties.get("events.cpu"))) { 2268 int user = mProcessCpuTracker.getLastUserTime(); 2269 int system = mProcessCpuTracker.getLastSystemTime(); 2270 int iowait = mProcessCpuTracker.getLastIoWaitTime(); 2271 int irq = mProcessCpuTracker.getLastIrqTime(); 2272 int softIrq = mProcessCpuTracker.getLastSoftIrqTime(); 2273 int idle = mProcessCpuTracker.getLastIdleTime(); 2274 2275 int total = user + system + iowait + irq + softIrq + idle; 2276 if (total == 0) total = 1; 2277 2278 EventLog.writeEvent(EventLogTags.CPU, 2279 ((user+system+iowait+irq+softIrq) * 100) / total, 2280 (user * 100) / total, 2281 (system * 100) / total, 2282 (iowait * 100) / total, 2283 (irq * 100) / total, 2284 (softIrq * 100) / total); 2285 } 2286 } 2287 2288 long[] cpuSpeedTimes = mProcessCpuTracker.getLastCpuSpeedTimes(); 2289 final BatteryStatsImpl bstats = mBatteryStatsService.getActiveStatistics(); 2290 synchronized(bstats) { 2291 synchronized(mPidsSelfLocked) { 2292 if (haveNewCpuStats) { 2293 if (mOnBattery) { 2294 int perc = bstats.startAddingCpuLocked(); 2295 int totalUTime = 0; 2296 int totalSTime = 0; 2297 final int N = mProcessCpuTracker.countStats(); 2298 for (int i=0; i<N; i++) { 2299 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 2300 if (!st.working) { 2301 continue; 2302 } 2303 ProcessRecord pr = mPidsSelfLocked.get(st.pid); 2304 int otherUTime = (st.rel_utime*perc)/100; 2305 int otherSTime = (st.rel_stime*perc)/100; 2306 totalUTime += otherUTime; 2307 totalSTime += otherSTime; 2308 if (pr != null) { 2309 BatteryStatsImpl.Uid.Proc ps = pr.curProcBatteryStats; 2310 if (ps == null || !ps.isActive()) { 2311 pr.curProcBatteryStats = ps = bstats.getProcessStatsLocked( 2312 pr.info.uid, pr.processName); 2313 } 2314 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2315 st.rel_stime-otherSTime); 2316 ps.addSpeedStepTimes(cpuSpeedTimes); 2317 pr.curCpuTime += (st.rel_utime+st.rel_stime) * 10; 2318 } else { 2319 BatteryStatsImpl.Uid.Proc ps = st.batteryStats; 2320 if (ps == null || !ps.isActive()) { 2321 st.batteryStats = ps = bstats.getProcessStatsLocked( 2322 bstats.mapUid(st.uid), st.name); 2323 } 2324 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2325 st.rel_stime-otherSTime); 2326 ps.addSpeedStepTimes(cpuSpeedTimes); 2327 } 2328 } 2329 bstats.finishAddingCpuLocked(perc, totalUTime, 2330 totalSTime, cpuSpeedTimes); 2331 } 2332 } 2333 } 2334 2335 if (mLastWriteTime < (now-BATTERY_STATS_TIME)) { 2336 mLastWriteTime = now; 2337 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2338 } 2339 } 2340 } 2341 } 2342 2343 @Override 2344 public void batteryNeedsCpuUpdate() { 2345 updateCpuStatsNow(); 2346 } 2347 2348 @Override 2349 public void batteryPowerChanged(boolean onBattery) { 2350 // When plugging in, update the CPU stats first before changing 2351 // the plug state. 2352 updateCpuStatsNow(); 2353 synchronized (this) { 2354 synchronized(mPidsSelfLocked) { 2355 mOnBattery = DEBUG_POWER ? true : onBattery; 2356 } 2357 } 2358 } 2359 2360 /** 2361 * Initialize the application bind args. These are passed to each 2362 * process when the bindApplication() IPC is sent to the process. They're 2363 * lazily setup to make sure the services are running when they're asked for. 2364 */ 2365 private HashMap<String, IBinder> getCommonServicesLocked() { 2366 if (mAppBindArgs == null) { 2367 mAppBindArgs = new HashMap<String, IBinder>(); 2368 2369 // Setup the application init args 2370 mAppBindArgs.put("package", ServiceManager.getService("package")); 2371 mAppBindArgs.put("window", ServiceManager.getService("window")); 2372 mAppBindArgs.put(Context.ALARM_SERVICE, 2373 ServiceManager.getService(Context.ALARM_SERVICE)); 2374 } 2375 return mAppBindArgs; 2376 } 2377 2378 final void setFocusedActivityLocked(ActivityRecord r) { 2379 if (mFocusedActivity != r) { 2380 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedActivityLocked: r=" + r); 2381 mFocusedActivity = r; 2382 if (r.task != null && r.task.voiceInteractor != null) { 2383 startRunningVoiceLocked(); 2384 } else { 2385 finishRunningVoiceLocked(); 2386 } 2387 mStackSupervisor.setFocusedStack(r); 2388 if (r != null) { 2389 mWindowManager.setFocusedApp(r.appToken, true); 2390 } 2391 applyUpdateLockStateLocked(r); 2392 } 2393 } 2394 2395 final void clearFocusedActivity(ActivityRecord r) { 2396 if (mFocusedActivity == r) { 2397 mFocusedActivity = null; 2398 } 2399 } 2400 2401 @Override 2402 public void setFocusedStack(int stackId) { 2403 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedStack: stackId=" + stackId); 2404 synchronized (ActivityManagerService.this) { 2405 ActivityStack stack = mStackSupervisor.getStack(stackId); 2406 if (stack != null) { 2407 ActivityRecord r = stack.topRunningActivityLocked(null); 2408 if (r != null) { 2409 setFocusedActivityLocked(r); 2410 } 2411 } 2412 } 2413 } 2414 2415 @Override 2416 public void notifyActivityDrawn(IBinder token) { 2417 if (DEBUG_VISBILITY) Slog.d(TAG, "notifyActivityDrawn: token=" + token); 2418 synchronized (this) { 2419 ActivityRecord r= mStackSupervisor.isInAnyStackLocked(token); 2420 if (r != null) { 2421 r.task.stack.notifyActivityDrawnLocked(r); 2422 } 2423 } 2424 } 2425 2426 final void applyUpdateLockStateLocked(ActivityRecord r) { 2427 // Modifications to the UpdateLock state are done on our handler, outside 2428 // the activity manager's locks. The new state is determined based on the 2429 // state *now* of the relevant activity record. The object is passed to 2430 // the handler solely for logging detail, not to be consulted/modified. 2431 final boolean nextState = r != null && r.immersive; 2432 mHandler.sendMessage( 2433 mHandler.obtainMessage(IMMERSIVE_MODE_LOCK_MSG, (nextState) ? 1 : 0, 0, r)); 2434 } 2435 2436 final void showAskCompatModeDialogLocked(ActivityRecord r) { 2437 Message msg = Message.obtain(); 2438 msg.what = SHOW_COMPAT_MODE_DIALOG_MSG; 2439 msg.obj = r.task.askedCompatMode ? null : r; 2440 mHandler.sendMessage(msg); 2441 } 2442 2443 private final int updateLruProcessInternalLocked(ProcessRecord app, long now, int index, 2444 String what, Object obj, ProcessRecord srcApp) { 2445 app.lastActivityTime = now; 2446 2447 if (app.activities.size() > 0) { 2448 // Don't want to touch dependent processes that are hosting activities. 2449 return index; 2450 } 2451 2452 int lrui = mLruProcesses.lastIndexOf(app); 2453 if (lrui < 0) { 2454 Slog.wtf(TAG, "Adding dependent process " + app + " not on LRU list: " 2455 + what + " " + obj + " from " + srcApp); 2456 return index; 2457 } 2458 2459 if (lrui >= index) { 2460 // Don't want to cause this to move dependent processes *back* in the 2461 // list as if they were less frequently used. 2462 return index; 2463 } 2464 2465 if (lrui >= mLruProcessActivityStart) { 2466 // Don't want to touch dependent processes that are hosting activities. 2467 return index; 2468 } 2469 2470 mLruProcesses.remove(lrui); 2471 if (index > 0) { 2472 index--; 2473 } 2474 if (DEBUG_LRU) Slog.d(TAG, "Moving dep from " + lrui + " to " + index 2475 + " in LRU list: " + app); 2476 mLruProcesses.add(index, app); 2477 return index; 2478 } 2479 2480 final void removeLruProcessLocked(ProcessRecord app) { 2481 int lrui = mLruProcesses.lastIndexOf(app); 2482 if (lrui >= 0) { 2483 if (lrui <= mLruProcessActivityStart) { 2484 mLruProcessActivityStart--; 2485 } 2486 if (lrui <= mLruProcessServiceStart) { 2487 mLruProcessServiceStart--; 2488 } 2489 mLruProcesses.remove(lrui); 2490 } 2491 } 2492 2493 final void updateLruProcessLocked(ProcessRecord app, boolean activityChange, 2494 ProcessRecord client) { 2495 final boolean hasActivity = app.activities.size() > 0 || app.hasClientActivities 2496 || app.treatLikeActivity; 2497 final boolean hasService = false; // not impl yet. app.services.size() > 0; 2498 if (!activityChange && hasActivity) { 2499 // The process has activities, so we are only allowing activity-based adjustments 2500 // to move it. It should be kept in the front of the list with other 2501 // processes that have activities, and we don't want those to change their 2502 // order except due to activity operations. 2503 return; 2504 } 2505 2506 mLruSeq++; 2507 final long now = SystemClock.uptimeMillis(); 2508 app.lastActivityTime = now; 2509 2510 // First a quick reject: if the app is already at the position we will 2511 // put it, then there is nothing to do. 2512 if (hasActivity) { 2513 final int N = mLruProcesses.size(); 2514 if (N > 0 && mLruProcesses.get(N-1) == app) { 2515 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top activity: " + app); 2516 return; 2517 } 2518 } else { 2519 if (mLruProcessServiceStart > 0 2520 && mLruProcesses.get(mLruProcessServiceStart-1) == app) { 2521 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top other: " + app); 2522 return; 2523 } 2524 } 2525 2526 int lrui = mLruProcesses.lastIndexOf(app); 2527 2528 if (app.persistent && lrui >= 0) { 2529 // We don't care about the position of persistent processes, as long as 2530 // they are in the list. 2531 if (DEBUG_LRU) Slog.d(TAG, "Not moving, persistent: " + app); 2532 return; 2533 } 2534 2535 /* In progress: compute new position first, so we can avoid doing work 2536 if the process is not actually going to move. Not yet working. 2537 int addIndex; 2538 int nextIndex; 2539 boolean inActivity = false, inService = false; 2540 if (hasActivity) { 2541 // Process has activities, put it at the very tipsy-top. 2542 addIndex = mLruProcesses.size(); 2543 nextIndex = mLruProcessServiceStart; 2544 inActivity = true; 2545 } else if (hasService) { 2546 // Process has services, put it at the top of the service list. 2547 addIndex = mLruProcessActivityStart; 2548 nextIndex = mLruProcessServiceStart; 2549 inActivity = true; 2550 inService = true; 2551 } else { 2552 // Process not otherwise of interest, it goes to the top of the non-service area. 2553 addIndex = mLruProcessServiceStart; 2554 if (client != null) { 2555 int clientIndex = mLruProcesses.lastIndexOf(client); 2556 if (clientIndex < 0) Slog.d(TAG, "Unknown client " + client + " when updating " 2557 + app); 2558 if (clientIndex >= 0 && addIndex > clientIndex) { 2559 addIndex = clientIndex; 2560 } 2561 } 2562 nextIndex = addIndex > 0 ? addIndex-1 : addIndex; 2563 } 2564 2565 Slog.d(TAG, "Update LRU at " + lrui + " to " + addIndex + " (act=" 2566 + mLruProcessActivityStart + "): " + app); 2567 */ 2568 2569 if (lrui >= 0) { 2570 if (lrui < mLruProcessActivityStart) { 2571 mLruProcessActivityStart--; 2572 } 2573 if (lrui < mLruProcessServiceStart) { 2574 mLruProcessServiceStart--; 2575 } 2576 /* 2577 if (addIndex > lrui) { 2578 addIndex--; 2579 } 2580 if (nextIndex > lrui) { 2581 nextIndex--; 2582 } 2583 */ 2584 mLruProcesses.remove(lrui); 2585 } 2586 2587 /* 2588 mLruProcesses.add(addIndex, app); 2589 if (inActivity) { 2590 mLruProcessActivityStart++; 2591 } 2592 if (inService) { 2593 mLruProcessActivityStart++; 2594 } 2595 */ 2596 2597 int nextIndex; 2598 if (hasActivity) { 2599 final int N = mLruProcesses.size(); 2600 if (app.activities.size() == 0 && mLruProcessActivityStart < (N-1)) { 2601 // Process doesn't have activities, but has clients with 2602 // activities... move it up, but one below the top (the top 2603 // should always have a real activity). 2604 if (DEBUG_LRU) Slog.d(TAG, "Adding to second-top of LRU activity list: " + app); 2605 mLruProcesses.add(N-1, app); 2606 // To keep it from spamming the LRU list (by making a bunch of clients), 2607 // we will push down any other entries owned by the app. 2608 final int uid = app.info.uid; 2609 for (int i=N-2; i>mLruProcessActivityStart; i--) { 2610 ProcessRecord subProc = mLruProcesses.get(i); 2611 if (subProc.info.uid == uid) { 2612 // We want to push this one down the list. If the process after 2613 // it is for the same uid, however, don't do so, because we don't 2614 // want them internally to be re-ordered. 2615 if (mLruProcesses.get(i-1).info.uid != uid) { 2616 if (DEBUG_LRU) Slog.d(TAG, "Pushing uid " + uid + " swapping at " + i 2617 + ": " + mLruProcesses.get(i) + " : " + mLruProcesses.get(i-1)); 2618 ProcessRecord tmp = mLruProcesses.get(i); 2619 mLruProcesses.set(i, mLruProcesses.get(i-1)); 2620 mLruProcesses.set(i-1, tmp); 2621 i--; 2622 } 2623 } else { 2624 // A gap, we can stop here. 2625 break; 2626 } 2627 } 2628 } else { 2629 // Process has activities, put it at the very tipsy-top. 2630 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU activity list: " + app); 2631 mLruProcesses.add(app); 2632 } 2633 nextIndex = mLruProcessServiceStart; 2634 } else if (hasService) { 2635 // Process has services, put it at the top of the service list. 2636 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU service list: " + app); 2637 mLruProcesses.add(mLruProcessActivityStart, app); 2638 nextIndex = mLruProcessServiceStart; 2639 mLruProcessActivityStart++; 2640 } else { 2641 // Process not otherwise of interest, it goes to the top of the non-service area. 2642 int index = mLruProcessServiceStart; 2643 if (client != null) { 2644 // If there is a client, don't allow the process to be moved up higher 2645 // in the list than that client. 2646 int clientIndex = mLruProcesses.lastIndexOf(client); 2647 if (DEBUG_LRU && clientIndex < 0) Slog.d(TAG, "Unknown client " + client 2648 + " when updating " + app); 2649 if (clientIndex <= lrui) { 2650 // Don't allow the client index restriction to push it down farther in the 2651 // list than it already is. 2652 clientIndex = lrui; 2653 } 2654 if (clientIndex >= 0 && index > clientIndex) { 2655 index = clientIndex; 2656 } 2657 } 2658 if (DEBUG_LRU) Slog.d(TAG, "Adding at " + index + " of LRU list: " + app); 2659 mLruProcesses.add(index, app); 2660 nextIndex = index-1; 2661 mLruProcessActivityStart++; 2662 mLruProcessServiceStart++; 2663 } 2664 2665 // If the app is currently using a content provider or service, 2666 // bump those processes as well. 2667 for (int j=app.connections.size()-1; j>=0; j--) { 2668 ConnectionRecord cr = app.connections.valueAt(j); 2669 if (cr.binding != null && !cr.serviceDead && cr.binding.service != null 2670 && cr.binding.service.app != null 2671 && cr.binding.service.app.lruSeq != mLruSeq 2672 && !cr.binding.service.app.persistent) { 2673 nextIndex = updateLruProcessInternalLocked(cr.binding.service.app, now, nextIndex, 2674 "service connection", cr, app); 2675 } 2676 } 2677 for (int j=app.conProviders.size()-1; j>=0; j--) { 2678 ContentProviderRecord cpr = app.conProviders.get(j).provider; 2679 if (cpr.proc != null && cpr.proc.lruSeq != mLruSeq && !cpr.proc.persistent) { 2680 nextIndex = updateLruProcessInternalLocked(cpr.proc, now, nextIndex, 2681 "provider reference", cpr, app); 2682 } 2683 } 2684 } 2685 2686 final ProcessRecord getProcessRecordLocked(String processName, int uid, boolean keepIfLarge) { 2687 if (uid == Process.SYSTEM_UID) { 2688 // The system gets to run in any process. If there are multiple 2689 // processes with the same uid, just pick the first (this 2690 // should never happen). 2691 SparseArray<ProcessRecord> procs = mProcessNames.getMap().get(processName); 2692 if (procs == null) return null; 2693 final int N = procs.size(); 2694 for (int i = 0; i < N; i++) { 2695 if (UserHandle.isSameUser(procs.keyAt(i), uid)) return procs.valueAt(i); 2696 } 2697 } 2698 ProcessRecord proc = mProcessNames.get(processName, uid); 2699 if (false && proc != null && !keepIfLarge 2700 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY 2701 && proc.lastCachedPss >= 4000) { 2702 // Turn this condition on to cause killing to happen regularly, for testing. 2703 if (proc.baseProcessTracker != null) { 2704 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2705 } 2706 killUnneededProcessLocked(proc, Long.toString(proc.lastCachedPss) 2707 + "k from cached"); 2708 } else if (proc != null && !keepIfLarge 2709 && mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 2710 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 2711 if (DEBUG_PSS) Slog.d(TAG, "May not keep " + proc + ": pss=" + proc.lastCachedPss); 2712 if (proc.lastCachedPss >= mProcessList.getCachedRestoreThresholdKb()) { 2713 if (proc.baseProcessTracker != null) { 2714 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2715 } 2716 killUnneededProcessLocked(proc, Long.toString(proc.lastCachedPss) 2717 + "k from cached"); 2718 } 2719 } 2720 return proc; 2721 } 2722 2723 void ensurePackageDexOpt(String packageName) { 2724 IPackageManager pm = AppGlobals.getPackageManager(); 2725 try { 2726 if (pm.performDexOpt(packageName)) { 2727 mDidDexOpt = true; 2728 } 2729 } catch (RemoteException e) { 2730 } 2731 } 2732 2733 boolean isNextTransitionForward() { 2734 int transit = mWindowManager.getPendingAppTransition(); 2735 return transit == AppTransition.TRANSIT_ACTIVITY_OPEN 2736 || transit == AppTransition.TRANSIT_TASK_OPEN 2737 || transit == AppTransition.TRANSIT_TASK_TO_FRONT; 2738 } 2739 2740 final ProcessRecord startProcessLocked(String processName, 2741 ApplicationInfo info, boolean knownToBeDead, int intentFlags, 2742 String hostingType, ComponentName hostingName, boolean allowWhileBooting, 2743 boolean isolated, boolean keepIfLarge) { 2744 ProcessRecord app; 2745 if (!isolated) { 2746 app = getProcessRecordLocked(processName, info.uid, keepIfLarge); 2747 } else { 2748 // If this is an isolated process, it can't re-use an existing process. 2749 app = null; 2750 } 2751 // We don't have to do anything more if: 2752 // (1) There is an existing application record; and 2753 // (2) The caller doesn't think it is dead, OR there is no thread 2754 // object attached to it so we know it couldn't have crashed; and 2755 // (3) There is a pid assigned to it, so it is either starting or 2756 // already running. 2757 if (DEBUG_PROCESSES) Slog.v(TAG, "startProcess: name=" + processName 2758 + " app=" + app + " knownToBeDead=" + knownToBeDead 2759 + " thread=" + (app != null ? app.thread : null) 2760 + " pid=" + (app != null ? app.pid : -1)); 2761 if (app != null && app.pid > 0) { 2762 if (!knownToBeDead || app.thread == null) { 2763 // We already have the app running, or are waiting for it to 2764 // come up (we have a pid but not yet its thread), so keep it. 2765 if (DEBUG_PROCESSES) Slog.v(TAG, "App already running: " + app); 2766 // If this is a new package in the process, add the package to the list 2767 app.addPackage(info.packageName, mProcessStats); 2768 return app; 2769 } 2770 2771 // An application record is attached to a previous process, 2772 // clean it up now. 2773 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, "App died: " + app); 2774 handleAppDiedLocked(app, true, true); 2775 } 2776 2777 String hostingNameStr = hostingName != null 2778 ? hostingName.flattenToShortString() : null; 2779 2780 if (!isolated) { 2781 if ((intentFlags&Intent.FLAG_FROM_BACKGROUND) != 0) { 2782 // If we are in the background, then check to see if this process 2783 // is bad. If so, we will just silently fail. 2784 if (mBadProcesses.get(info.processName, info.uid) != null) { 2785 if (DEBUG_PROCESSES) Slog.v(TAG, "Bad process: " + info.uid 2786 + "/" + info.processName); 2787 return null; 2788 } 2789 } else { 2790 // When the user is explicitly starting a process, then clear its 2791 // crash count so that we won't make it bad until they see at 2792 // least one crash dialog again, and make the process good again 2793 // if it had been bad. 2794 if (DEBUG_PROCESSES) Slog.v(TAG, "Clearing bad process: " + info.uid 2795 + "/" + info.processName); 2796 mProcessCrashTimes.remove(info.processName, info.uid); 2797 if (mBadProcesses.get(info.processName, info.uid) != null) { 2798 EventLog.writeEvent(EventLogTags.AM_PROC_GOOD, 2799 UserHandle.getUserId(info.uid), info.uid, 2800 info.processName); 2801 mBadProcesses.remove(info.processName, info.uid); 2802 if (app != null) { 2803 app.bad = false; 2804 } 2805 } 2806 } 2807 } 2808 2809 if (app == null) { 2810 app = newProcessRecordLocked(info, processName, isolated); 2811 if (app == null) { 2812 Slog.w(TAG, "Failed making new process record for " 2813 + processName + "/" + info.uid + " isolated=" + isolated); 2814 return null; 2815 } 2816 mProcessNames.put(processName, app.uid, app); 2817 if (isolated) { 2818 mIsolatedProcesses.put(app.uid, app); 2819 } 2820 } else { 2821 // If this is a new package in the process, add the package to the list 2822 app.addPackage(info.packageName, mProcessStats); 2823 } 2824 2825 // If the system is not ready yet, then hold off on starting this 2826 // process until it is. 2827 if (!mProcessesReady 2828 && !isAllowedWhileBooting(info) 2829 && !allowWhileBooting) { 2830 if (!mProcessesOnHold.contains(app)) { 2831 mProcessesOnHold.add(app); 2832 } 2833 if (DEBUG_PROCESSES) Slog.v(TAG, "System not ready, putting on hold: " + app); 2834 return app; 2835 } 2836 2837 startProcessLocked(app, hostingType, hostingNameStr, null /* ABI override */); 2838 return (app.pid != 0) ? app : null; 2839 } 2840 2841 boolean isAllowedWhileBooting(ApplicationInfo ai) { 2842 return (ai.flags&ApplicationInfo.FLAG_PERSISTENT) != 0; 2843 } 2844 2845 private final void startProcessLocked(ProcessRecord app, 2846 String hostingType, String hostingNameStr, String abiOverride) { 2847 if (app.pid > 0 && app.pid != MY_PID) { 2848 synchronized (mPidsSelfLocked) { 2849 mPidsSelfLocked.remove(app.pid); 2850 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 2851 } 2852 app.setPid(0); 2853 } 2854 2855 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 2856 "startProcessLocked removing on hold: " + app); 2857 mProcessesOnHold.remove(app); 2858 2859 updateCpuStats(); 2860 2861 try { 2862 int uid = app.uid; 2863 2864 int[] gids = null; 2865 int mountExternal = Zygote.MOUNT_EXTERNAL_NONE; 2866 if (!app.isolated) { 2867 int[] permGids = null; 2868 try { 2869 final PackageManager pm = mContext.getPackageManager(); 2870 permGids = pm.getPackageGids(app.info.packageName); 2871 2872 if (Environment.isExternalStorageEmulated()) { 2873 if (pm.checkPermission( 2874 android.Manifest.permission.ACCESS_ALL_EXTERNAL_STORAGE, 2875 app.info.packageName) == PERMISSION_GRANTED) { 2876 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER_ALL; 2877 } else { 2878 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER; 2879 } 2880 } 2881 } catch (PackageManager.NameNotFoundException e) { 2882 Slog.w(TAG, "Unable to retrieve gids", e); 2883 } 2884 2885 /* 2886 * Add shared application and profile GIDs so applications can share some 2887 * resources like shared libraries and access user-wide resources 2888 */ 2889 if (permGids == null) { 2890 gids = new int[2]; 2891 } else { 2892 gids = new int[permGids.length + 2]; 2893 System.arraycopy(permGids, 0, gids, 2, permGids.length); 2894 } 2895 gids[0] = UserHandle.getSharedAppGid(UserHandle.getAppId(uid)); 2896 gids[1] = UserHandle.getUserGid(UserHandle.getUserId(uid)); 2897 } 2898 if (mFactoryTest != FactoryTest.FACTORY_TEST_OFF) { 2899 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 2900 && mTopComponent != null 2901 && app.processName.equals(mTopComponent.getPackageName())) { 2902 uid = 0; 2903 } 2904 if (mFactoryTest == FactoryTest.FACTORY_TEST_HIGH_LEVEL 2905 && (app.info.flags&ApplicationInfo.FLAG_FACTORY_TEST) != 0) { 2906 uid = 0; 2907 } 2908 } 2909 int debugFlags = 0; 2910 if ((app.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 2911 debugFlags |= Zygote.DEBUG_ENABLE_DEBUGGER; 2912 // Also turn on CheckJNI for debuggable apps. It's quite 2913 // awkward to turn on otherwise. 2914 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 2915 } 2916 // Run the app in safe mode if its manifest requests so or the 2917 // system is booted in safe mode. 2918 if ((app.info.flags & ApplicationInfo.FLAG_VM_SAFE_MODE) != 0 || 2919 mSafeMode == true) { 2920 debugFlags |= Zygote.DEBUG_ENABLE_SAFEMODE; 2921 } 2922 if ("1".equals(SystemProperties.get("debug.checkjni"))) { 2923 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 2924 } 2925 if ("1".equals(SystemProperties.get("debug.jni.logging"))) { 2926 debugFlags |= Zygote.DEBUG_ENABLE_JNI_LOGGING; 2927 } 2928 if ("1".equals(SystemProperties.get("debug.assert"))) { 2929 debugFlags |= Zygote.DEBUG_ENABLE_ASSERT; 2930 } 2931 2932 String requiredAbi = (abiOverride != null) ? abiOverride : app.info.cpuAbi; 2933 if (requiredAbi == null) { 2934 requiredAbi = Build.SUPPORTED_ABIS[0]; 2935 } 2936 2937 // Start the process. It will either succeed and return a result containing 2938 // the PID of the new process, or else throw a RuntimeException. 2939 Process.ProcessStartResult startResult = Process.start("android.app.ActivityThread", 2940 app.processName, uid, uid, gids, debugFlags, mountExternal, 2941 app.info.targetSdkVersion, app.info.seinfo, requiredAbi, null); 2942 2943 BatteryStatsImpl bs = mBatteryStatsService.getActiveStatistics(); 2944 synchronized (bs) { 2945 if (bs.isOnBattery()) { 2946 bs.getProcessStatsLocked(app.uid, app.processName).incStartsLocked(); 2947 } 2948 } 2949 2950 EventLog.writeEvent(EventLogTags.AM_PROC_START, 2951 UserHandle.getUserId(uid), startResult.pid, uid, 2952 app.processName, hostingType, 2953 hostingNameStr != null ? hostingNameStr : ""); 2954 2955 if (app.persistent) { 2956 Watchdog.getInstance().processStarted(app.processName, startResult.pid); 2957 } 2958 2959 StringBuilder buf = mStringBuilder; 2960 buf.setLength(0); 2961 buf.append("Start proc "); 2962 buf.append(app.processName); 2963 buf.append(" for "); 2964 buf.append(hostingType); 2965 if (hostingNameStr != null) { 2966 buf.append(" "); 2967 buf.append(hostingNameStr); 2968 } 2969 buf.append(": pid="); 2970 buf.append(startResult.pid); 2971 buf.append(" uid="); 2972 buf.append(uid); 2973 buf.append(" gids={"); 2974 if (gids != null) { 2975 for (int gi=0; gi<gids.length; gi++) { 2976 if (gi != 0) buf.append(", "); 2977 buf.append(gids[gi]); 2978 2979 } 2980 } 2981 buf.append("}"); 2982 if (requiredAbi != null) { 2983 buf.append(" abi="); 2984 buf.append(requiredAbi); 2985 } 2986 Slog.i(TAG, buf.toString()); 2987 app.setPid(startResult.pid); 2988 app.usingWrapper = startResult.usingWrapper; 2989 app.removed = false; 2990 synchronized (mPidsSelfLocked) { 2991 this.mPidsSelfLocked.put(startResult.pid, app); 2992 Message msg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 2993 msg.obj = app; 2994 mHandler.sendMessageDelayed(msg, startResult.usingWrapper 2995 ? PROC_START_TIMEOUT_WITH_WRAPPER : PROC_START_TIMEOUT); 2996 } 2997 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_PROC_START, 2998 app.processName, app.info.uid); 2999 if (app.isolated) { 3000 mBatteryStatsService.addIsolatedUid(app.uid, app.info.uid); 3001 } 3002 } catch (RuntimeException e) { 3003 // XXX do better error recovery. 3004 app.setPid(0); 3005 Slog.e(TAG, "Failure starting process " + app.processName, e); 3006 } 3007 } 3008 3009 void updateUsageStats(ActivityRecord component, boolean resumed) { 3010 if (DEBUG_SWITCH) Slog.d(TAG, "updateUsageStats: comp=" + component + "res=" + resumed); 3011 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 3012 if (resumed) { 3013 mUsageStatsService.noteResumeComponent(component.realActivity); 3014 synchronized (stats) { 3015 stats.noteActivityResumedLocked(component.app.uid); 3016 } 3017 } else { 3018 mUsageStatsService.notePauseComponent(component.realActivity); 3019 synchronized (stats) { 3020 stats.noteActivityPausedLocked(component.app.uid); 3021 } 3022 } 3023 } 3024 3025 Intent getHomeIntent() { 3026 Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null); 3027 intent.setComponent(mTopComponent); 3028 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 3029 intent.addCategory(Intent.CATEGORY_HOME); 3030 } 3031 return intent; 3032 } 3033 3034 boolean startHomeActivityLocked(int userId) { 3035 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3036 && mTopAction == null) { 3037 // We are running in factory test mode, but unable to find 3038 // the factory test app, so just sit around displaying the 3039 // error message and don't try to start anything. 3040 return false; 3041 } 3042 Intent intent = getHomeIntent(); 3043 ActivityInfo aInfo = 3044 resolveActivityInfo(intent, STOCK_PM_FLAGS, userId); 3045 if (aInfo != null) { 3046 intent.setComponent(new ComponentName( 3047 aInfo.applicationInfo.packageName, aInfo.name)); 3048 // Don't do this if the home app is currently being 3049 // instrumented. 3050 aInfo = new ActivityInfo(aInfo); 3051 aInfo.applicationInfo = getAppInfoForUser(aInfo.applicationInfo, userId); 3052 ProcessRecord app = getProcessRecordLocked(aInfo.processName, 3053 aInfo.applicationInfo.uid, true); 3054 if (app == null || app.instrumentationClass == null) { 3055 intent.setFlags(intent.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK); 3056 mStackSupervisor.startHomeActivity(intent, aInfo); 3057 } 3058 } 3059 3060 return true; 3061 } 3062 3063 private ActivityInfo resolveActivityInfo(Intent intent, int flags, int userId) { 3064 ActivityInfo ai = null; 3065 ComponentName comp = intent.getComponent(); 3066 try { 3067 if (comp != null) { 3068 ai = AppGlobals.getPackageManager().getActivityInfo(comp, flags, userId); 3069 } else { 3070 ResolveInfo info = AppGlobals.getPackageManager().resolveIntent( 3071 intent, 3072 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 3073 flags, userId); 3074 3075 if (info != null) { 3076 ai = info.activityInfo; 3077 } 3078 } 3079 } catch (RemoteException e) { 3080 // ignore 3081 } 3082 3083 return ai; 3084 } 3085 3086 /** 3087 * Starts the "new version setup screen" if appropriate. 3088 */ 3089 void startSetupActivityLocked() { 3090 // Only do this once per boot. 3091 if (mCheckedForSetup) { 3092 return; 3093 } 3094 3095 // We will show this screen if the current one is a different 3096 // version than the last one shown, and we are not running in 3097 // low-level factory test mode. 3098 final ContentResolver resolver = mContext.getContentResolver(); 3099 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL && 3100 Settings.Global.getInt(resolver, 3101 Settings.Global.DEVICE_PROVISIONED, 0) != 0) { 3102 mCheckedForSetup = true; 3103 3104 // See if we should be showing the platform update setup UI. 3105 Intent intent = new Intent(Intent.ACTION_UPGRADE_SETUP); 3106 List<ResolveInfo> ris = mContext.getPackageManager() 3107 .queryIntentActivities(intent, PackageManager.GET_META_DATA); 3108 3109 // We don't allow third party apps to replace this. 3110 ResolveInfo ri = null; 3111 for (int i=0; ris != null && i<ris.size(); i++) { 3112 if ((ris.get(i).activityInfo.applicationInfo.flags 3113 & ApplicationInfo.FLAG_SYSTEM) != 0) { 3114 ri = ris.get(i); 3115 break; 3116 } 3117 } 3118 3119 if (ri != null) { 3120 String vers = ri.activityInfo.metaData != null 3121 ? ri.activityInfo.metaData.getString(Intent.METADATA_SETUP_VERSION) 3122 : null; 3123 if (vers == null && ri.activityInfo.applicationInfo.metaData != null) { 3124 vers = ri.activityInfo.applicationInfo.metaData.getString( 3125 Intent.METADATA_SETUP_VERSION); 3126 } 3127 String lastVers = Settings.Secure.getString( 3128 resolver, Settings.Secure.LAST_SETUP_SHOWN); 3129 if (vers != null && !vers.equals(lastVers)) { 3130 intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 3131 intent.setComponent(new ComponentName( 3132 ri.activityInfo.packageName, ri.activityInfo.name)); 3133 mStackSupervisor.startActivityLocked(null, intent, null, ri.activityInfo, 3134 null, null, null, null, 0, 0, 0, null, 0, null, false, null, null); 3135 } 3136 } 3137 } 3138 } 3139 3140 CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) { 3141 return mCompatModePackages.compatibilityInfoForPackageLocked(ai); 3142 } 3143 3144 void enforceNotIsolatedCaller(String caller) { 3145 if (UserHandle.isIsolated(Binder.getCallingUid())) { 3146 throw new SecurityException("Isolated process not allowed to call " + caller); 3147 } 3148 } 3149 3150 @Override 3151 public int getFrontActivityScreenCompatMode() { 3152 enforceNotIsolatedCaller("getFrontActivityScreenCompatMode"); 3153 synchronized (this) { 3154 return mCompatModePackages.getFrontActivityScreenCompatModeLocked(); 3155 } 3156 } 3157 3158 @Override 3159 public void setFrontActivityScreenCompatMode(int mode) { 3160 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3161 "setFrontActivityScreenCompatMode"); 3162 synchronized (this) { 3163 mCompatModePackages.setFrontActivityScreenCompatModeLocked(mode); 3164 } 3165 } 3166 3167 @Override 3168 public int getPackageScreenCompatMode(String packageName) { 3169 enforceNotIsolatedCaller("getPackageScreenCompatMode"); 3170 synchronized (this) { 3171 return mCompatModePackages.getPackageScreenCompatModeLocked(packageName); 3172 } 3173 } 3174 3175 @Override 3176 public void setPackageScreenCompatMode(String packageName, int mode) { 3177 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3178 "setPackageScreenCompatMode"); 3179 synchronized (this) { 3180 mCompatModePackages.setPackageScreenCompatModeLocked(packageName, mode); 3181 } 3182 } 3183 3184 @Override 3185 public boolean getPackageAskScreenCompat(String packageName) { 3186 enforceNotIsolatedCaller("getPackageAskScreenCompat"); 3187 synchronized (this) { 3188 return mCompatModePackages.getPackageAskCompatModeLocked(packageName); 3189 } 3190 } 3191 3192 @Override 3193 public void setPackageAskScreenCompat(String packageName, boolean ask) { 3194 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3195 "setPackageAskScreenCompat"); 3196 synchronized (this) { 3197 mCompatModePackages.setPackageAskCompatModeLocked(packageName, ask); 3198 } 3199 } 3200 3201 private void dispatchProcessesChanged() { 3202 int N; 3203 synchronized (this) { 3204 N = mPendingProcessChanges.size(); 3205 if (mActiveProcessChanges.length < N) { 3206 mActiveProcessChanges = new ProcessChangeItem[N]; 3207 } 3208 mPendingProcessChanges.toArray(mActiveProcessChanges); 3209 mAvailProcessChanges.addAll(mPendingProcessChanges); 3210 mPendingProcessChanges.clear(); 3211 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "*** Delivering " + N + " process changes"); 3212 } 3213 3214 int i = mProcessObservers.beginBroadcast(); 3215 while (i > 0) { 3216 i--; 3217 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3218 if (observer != null) { 3219 try { 3220 for (int j=0; j<N; j++) { 3221 ProcessChangeItem item = mActiveProcessChanges[j]; 3222 if ((item.changes&ProcessChangeItem.CHANGE_ACTIVITIES) != 0) { 3223 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "ACTIVITIES CHANGED pid=" 3224 + item.pid + " uid=" + item.uid + ": " 3225 + item.foregroundActivities); 3226 observer.onForegroundActivitiesChanged(item.pid, item.uid, 3227 item.foregroundActivities); 3228 } 3229 if ((item.changes&ProcessChangeItem.CHANGE_PROCESS_STATE) != 0) { 3230 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "PROCSTATE CHANGED pid=" 3231 + item.pid + " uid=" + item.uid + ": " + item.processState); 3232 observer.onProcessStateChanged(item.pid, item.uid, item.processState); 3233 } 3234 } 3235 } catch (RemoteException e) { 3236 } 3237 } 3238 } 3239 mProcessObservers.finishBroadcast(); 3240 } 3241 3242 private void dispatchProcessDied(int pid, int uid) { 3243 int i = mProcessObservers.beginBroadcast(); 3244 while (i > 0) { 3245 i--; 3246 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3247 if (observer != null) { 3248 try { 3249 observer.onProcessDied(pid, uid); 3250 } catch (RemoteException e) { 3251 } 3252 } 3253 } 3254 mProcessObservers.finishBroadcast(); 3255 } 3256 3257 final void doPendingActivityLaunchesLocked(boolean doResume) { 3258 final int N = mPendingActivityLaunches.size(); 3259 if (N <= 0) { 3260 return; 3261 } 3262 for (int i=0; i<N; i++) { 3263 PendingActivityLaunch pal = mPendingActivityLaunches.get(i); 3264 mStackSupervisor.startActivityUncheckedLocked(pal.r, pal.sourceRecord, null, null, pal.startFlags, 3265 doResume && i == (N-1), null); 3266 } 3267 mPendingActivityLaunches.clear(); 3268 } 3269 3270 @Override 3271 public final int startActivity(IApplicationThread caller, String callingPackage, 3272 Intent intent, String resolvedType, IBinder resultTo, 3273 String resultWho, int requestCode, int startFlags, 3274 String profileFile, ParcelFileDescriptor profileFd, Bundle options) { 3275 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo, 3276 resultWho, requestCode, 3277 startFlags, profileFile, profileFd, options, UserHandle.getCallingUserId()); 3278 } 3279 3280 @Override 3281 public final int startActivityAsUser(IApplicationThread caller, String callingPackage, 3282 Intent intent, String resolvedType, IBinder resultTo, 3283 String resultWho, int requestCode, int startFlags, 3284 String profileFile, ParcelFileDescriptor profileFd, Bundle options, int userId) { 3285 enforceNotIsolatedCaller("startActivity"); 3286 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3287 false, true, "startActivity", null); 3288 // TODO: Switch to user app stacks here. 3289 return mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 3290 null, null, resultTo, resultWho, requestCode, startFlags, profileFile, profileFd, 3291 null, null, options, userId, null); 3292 } 3293 3294 @Override 3295 public final WaitResult startActivityAndWait(IApplicationThread caller, String callingPackage, 3296 Intent intent, String resolvedType, IBinder resultTo, 3297 String resultWho, int requestCode, int startFlags, String profileFile, 3298 ParcelFileDescriptor profileFd, Bundle options, int userId) { 3299 enforceNotIsolatedCaller("startActivityAndWait"); 3300 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3301 false, true, "startActivityAndWait", null); 3302 WaitResult res = new WaitResult(); 3303 // TODO: Switch to user app stacks here. 3304 mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 3305 null, null, resultTo, resultWho, requestCode, startFlags, profileFile, profileFd, 3306 res, null, options, UserHandle.getCallingUserId(), null); 3307 return res; 3308 } 3309 3310 @Override 3311 public final int startActivityWithConfig(IApplicationThread caller, String callingPackage, 3312 Intent intent, String resolvedType, IBinder resultTo, 3313 String resultWho, int requestCode, int startFlags, Configuration config, 3314 Bundle options, int userId) { 3315 enforceNotIsolatedCaller("startActivityWithConfig"); 3316 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3317 false, true, "startActivityWithConfig", null); 3318 // TODO: Switch to user app stacks here. 3319 int ret = mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, 3320 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3321 null, null, null, config, options, userId, null); 3322 return ret; 3323 } 3324 3325 @Override 3326 public int startActivityIntentSender(IApplicationThread caller, 3327 IntentSender intent, Intent fillInIntent, String resolvedType, 3328 IBinder resultTo, String resultWho, int requestCode, 3329 int flagsMask, int flagsValues, Bundle options) { 3330 enforceNotIsolatedCaller("startActivityIntentSender"); 3331 // Refuse possible leaked file descriptors 3332 if (fillInIntent != null && fillInIntent.hasFileDescriptors()) { 3333 throw new IllegalArgumentException("File descriptors passed in Intent"); 3334 } 3335 3336 IIntentSender sender = intent.getTarget(); 3337 if (!(sender instanceof PendingIntentRecord)) { 3338 throw new IllegalArgumentException("Bad PendingIntent object"); 3339 } 3340 3341 PendingIntentRecord pir = (PendingIntentRecord)sender; 3342 3343 synchronized (this) { 3344 // If this is coming from the currently resumed activity, it is 3345 // effectively saying that app switches are allowed at this point. 3346 final ActivityStack stack = getFocusedStack(); 3347 if (stack.mResumedActivity != null && 3348 stack.mResumedActivity.info.applicationInfo.uid == Binder.getCallingUid()) { 3349 mAppSwitchesAllowedTime = 0; 3350 } 3351 } 3352 int ret = pir.sendInner(0, fillInIntent, resolvedType, null, null, 3353 resultTo, resultWho, requestCode, flagsMask, flagsValues, options, null); 3354 return ret; 3355 } 3356 3357 @Override 3358 public int startVoiceActivity(String callingPackage, int callingPid, int callingUid, 3359 Intent intent, String resolvedType, IVoiceInteractionSession session, 3360 IVoiceInteractor interactor, int startFlags, String profileFile, 3361 ParcelFileDescriptor profileFd, Bundle options, int userId) { 3362 if (checkCallingPermission(Manifest.permission.BIND_VOICE_INTERACTION) 3363 != PackageManager.PERMISSION_GRANTED) { 3364 String msg = "Permission Denial: startVoiceActivity() from pid=" 3365 + Binder.getCallingPid() 3366 + ", uid=" + Binder.getCallingUid() 3367 + " requires " + android.Manifest.permission.BIND_VOICE_INTERACTION; 3368 Slog.w(TAG, msg); 3369 throw new SecurityException(msg); 3370 } 3371 if (session == null || interactor == null) { 3372 throw new NullPointerException("null session or interactor"); 3373 } 3374 userId = handleIncomingUser(callingPid, callingUid, userId, 3375 false, true, "startVoiceActivity", null); 3376 // TODO: Switch to user app stacks here. 3377 return mStackSupervisor.startActivityMayWait(null, callingUid, callingPackage, intent, 3378 resolvedType, session, interactor, null, null, 0, startFlags, 3379 profileFile, profileFd, null, null, options, userId, null); 3380 } 3381 3382 @Override 3383 public boolean startNextMatchingActivity(IBinder callingActivity, 3384 Intent intent, Bundle options) { 3385 // Refuse possible leaked file descriptors 3386 if (intent != null && intent.hasFileDescriptors() == true) { 3387 throw new IllegalArgumentException("File descriptors passed in Intent"); 3388 } 3389 3390 synchronized (this) { 3391 final ActivityRecord r = ActivityRecord.isInStackLocked(callingActivity); 3392 if (r == null) { 3393 ActivityOptions.abort(options); 3394 return false; 3395 } 3396 if (r.app == null || r.app.thread == null) { 3397 // The caller is not running... d'oh! 3398 ActivityOptions.abort(options); 3399 return false; 3400 } 3401 intent = new Intent(intent); 3402 // The caller is not allowed to change the data. 3403 intent.setDataAndType(r.intent.getData(), r.intent.getType()); 3404 // And we are resetting to find the next component... 3405 intent.setComponent(null); 3406 3407 final boolean debug = ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0); 3408 3409 ActivityInfo aInfo = null; 3410 try { 3411 List<ResolveInfo> resolves = 3412 AppGlobals.getPackageManager().queryIntentActivities( 3413 intent, r.resolvedType, 3414 PackageManager.MATCH_DEFAULT_ONLY | STOCK_PM_FLAGS, 3415 UserHandle.getCallingUserId()); 3416 3417 // Look for the original activity in the list... 3418 final int N = resolves != null ? resolves.size() : 0; 3419 for (int i=0; i<N; i++) { 3420 ResolveInfo rInfo = resolves.get(i); 3421 if (rInfo.activityInfo.packageName.equals(r.packageName) 3422 && rInfo.activityInfo.name.equals(r.info.name)) { 3423 // We found the current one... the next matching is 3424 // after it. 3425 i++; 3426 if (i<N) { 3427 aInfo = resolves.get(i).activityInfo; 3428 } 3429 if (debug) { 3430 Slog.v(TAG, "Next matching activity: found current " + r.packageName 3431 + "/" + r.info.name); 3432 Slog.v(TAG, "Next matching activity: next is " + aInfo.packageName 3433 + "/" + aInfo.name); 3434 } 3435 break; 3436 } 3437 } 3438 } catch (RemoteException e) { 3439 } 3440 3441 if (aInfo == null) { 3442 // Nobody who is next! 3443 ActivityOptions.abort(options); 3444 if (debug) Slog.d(TAG, "Next matching activity: nothing found"); 3445 return false; 3446 } 3447 3448 intent.setComponent(new ComponentName( 3449 aInfo.applicationInfo.packageName, aInfo.name)); 3450 intent.setFlags(intent.getFlags()&~( 3451 Intent.FLAG_ACTIVITY_FORWARD_RESULT| 3452 Intent.FLAG_ACTIVITY_CLEAR_TOP| 3453 Intent.FLAG_ACTIVITY_MULTIPLE_TASK| 3454 Intent.FLAG_ACTIVITY_NEW_TASK)); 3455 3456 // Okay now we need to start the new activity, replacing the 3457 // currently running activity. This is a little tricky because 3458 // we want to start the new one as if the current one is finished, 3459 // but not finish the current one first so that there is no flicker. 3460 // And thus... 3461 final boolean wasFinishing = r.finishing; 3462 r.finishing = true; 3463 3464 // Propagate reply information over to the new activity. 3465 final ActivityRecord resultTo = r.resultTo; 3466 final String resultWho = r.resultWho; 3467 final int requestCode = r.requestCode; 3468 r.resultTo = null; 3469 if (resultTo != null) { 3470 resultTo.removeResultsLocked(r, resultWho, requestCode); 3471 } 3472 3473 final long origId = Binder.clearCallingIdentity(); 3474 int res = mStackSupervisor.startActivityLocked(r.app.thread, intent, 3475 r.resolvedType, aInfo, null, null, resultTo != null ? resultTo.appToken : null, 3476 resultWho, requestCode, -1, r.launchedFromUid, r.launchedFromPackage, 0, 3477 options, false, null, null); 3478 Binder.restoreCallingIdentity(origId); 3479 3480 r.finishing = wasFinishing; 3481 if (res != ActivityManager.START_SUCCESS) { 3482 return false; 3483 } 3484 return true; 3485 } 3486 } 3487 3488 final int startActivityInPackage(int uid, String callingPackage, 3489 Intent intent, String resolvedType, IBinder resultTo, 3490 String resultWho, int requestCode, int startFlags, Bundle options, int userId, 3491 IActivityContainer container) { 3492 3493 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3494 false, true, "startActivityInPackage", null); 3495 3496 // TODO: Switch to user app stacks here. 3497 int ret = mStackSupervisor.startActivityMayWait(null, uid, callingPackage, intent, resolvedType, 3498 null, null, resultTo, resultWho, requestCode, startFlags, 3499 null, null, null, null, options, userId, container); 3500 return ret; 3501 } 3502 3503 @Override 3504 public final int startActivities(IApplicationThread caller, String callingPackage, 3505 Intent[] intents, String[] resolvedTypes, IBinder resultTo, Bundle options, 3506 int userId) { 3507 enforceNotIsolatedCaller("startActivities"); 3508 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3509 false, true, "startActivity", null); 3510 // TODO: Switch to user app stacks here. 3511 int ret = mStackSupervisor.startActivities(caller, -1, callingPackage, intents, 3512 resolvedTypes, resultTo, options, userId); 3513 return ret; 3514 } 3515 3516 final int startActivitiesInPackage(int uid, String callingPackage, 3517 Intent[] intents, String[] resolvedTypes, IBinder resultTo, 3518 Bundle options, int userId) { 3519 3520 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3521 false, true, "startActivityInPackage", null); 3522 // TODO: Switch to user app stacks here. 3523 int ret = mStackSupervisor.startActivities(null, uid, callingPackage, intents, resolvedTypes, 3524 resultTo, options, userId); 3525 return ret; 3526 } 3527 3528 final void addRecentTaskLocked(TaskRecord task) { 3529 int N = mRecentTasks.size(); 3530 // Quick case: check if the top-most recent task is the same. 3531 if (N > 0 && mRecentTasks.get(0) == task) { 3532 return; 3533 } 3534 // Another quick case: never add voice sessions. 3535 if (task.voiceSession != null) { 3536 return; 3537 } 3538 // Remove any existing entries that are the same kind of task. 3539 final Intent intent = task.intent; 3540 final boolean document = intent != null && intent.isDocument(); 3541 for (int i=0; i<N; i++) { 3542 TaskRecord tr = mRecentTasks.get(i); 3543 if (task != tr) { 3544 if (task.userId != tr.userId) { 3545 continue; 3546 } 3547 final Intent trIntent = tr.intent; 3548 if ((task.affinity == null || !task.affinity.equals(tr.affinity)) && 3549 (intent == null || !intent.filterEquals(trIntent))) { 3550 continue; 3551 } 3552 if (document || trIntent != null && trIntent.isDocument()) { 3553 // Document tasks do not match other tasks. 3554 continue; 3555 } 3556 } 3557 3558 // Either task and tr are the same or, their affinities match or their intents match 3559 // and neither of them is a document. 3560 tr.disposeThumbnail(); 3561 mRecentTasks.remove(i); 3562 i--; 3563 N--; 3564 if (task.intent == null) { 3565 // If the new recent task we are adding is not fully 3566 // specified, then replace it with the existing recent task. 3567 task = tr; 3568 } 3569 } 3570 if (N >= MAX_RECENT_TASKS) { 3571 mRecentTasks.remove(N-1).disposeThumbnail(); 3572 } 3573 mRecentTasks.add(0, task); 3574 } 3575 3576 @Override 3577 public void reportActivityFullyDrawn(IBinder token) { 3578 synchronized (this) { 3579 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3580 if (r == null) { 3581 return; 3582 } 3583 r.reportFullyDrawnLocked(); 3584 } 3585 } 3586 3587 @Override 3588 public void setRequestedOrientation(IBinder token, int requestedOrientation) { 3589 synchronized (this) { 3590 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3591 if (r == null) { 3592 return; 3593 } 3594 final long origId = Binder.clearCallingIdentity(); 3595 mWindowManager.setAppOrientation(r.appToken, requestedOrientation); 3596 Configuration config = mWindowManager.updateOrientationFromAppTokens( 3597 mConfiguration, r.mayFreezeScreenLocked(r.app) ? r.appToken : null); 3598 if (config != null) { 3599 r.frozenBeforeDestroy = true; 3600 if (!updateConfigurationLocked(config, r, false, false)) { 3601 mStackSupervisor.resumeTopActivitiesLocked(); 3602 } 3603 } 3604 Binder.restoreCallingIdentity(origId); 3605 } 3606 } 3607 3608 @Override 3609 public int getRequestedOrientation(IBinder token) { 3610 synchronized (this) { 3611 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3612 if (r == null) { 3613 return ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED; 3614 } 3615 return mWindowManager.getAppOrientation(r.appToken); 3616 } 3617 } 3618 3619 /** 3620 * This is the internal entry point for handling Activity.finish(). 3621 * 3622 * @param token The Binder token referencing the Activity we want to finish. 3623 * @param resultCode Result code, if any, from this Activity. 3624 * @param resultData Result data (Intent), if any, from this Activity. 3625 * @param finishTask Whether to finish the task associated with this Activity. Only applies to 3626 * the root Activity in the task. 3627 * 3628 * @return Returns true if the activity successfully finished, or false if it is still running. 3629 */ 3630 @Override 3631 public final boolean finishActivity(IBinder token, int resultCode, Intent resultData, 3632 boolean finishTask) { 3633 // Refuse possible leaked file descriptors 3634 if (resultData != null && resultData.hasFileDescriptors() == true) { 3635 throw new IllegalArgumentException("File descriptors passed in Intent"); 3636 } 3637 3638 synchronized(this) { 3639 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3640 if (r == null) { 3641 return true; 3642 } 3643 // Keep track of the root activity of the task before we finish it 3644 TaskRecord tr = r.task; 3645 ActivityRecord rootR = tr.getRootActivity(); 3646 if (mController != null) { 3647 // Find the first activity that is not finishing. 3648 ActivityRecord next = r.task.stack.topRunningActivityLocked(token, 0); 3649 if (next != null) { 3650 // ask watcher if this is allowed 3651 boolean resumeOK = true; 3652 try { 3653 resumeOK = mController.activityResuming(next.packageName); 3654 } catch (RemoteException e) { 3655 mController = null; 3656 Watchdog.getInstance().setActivityController(null); 3657 } 3658 3659 if (!resumeOK) { 3660 return false; 3661 } 3662 } 3663 } 3664 final long origId = Binder.clearCallingIdentity(); 3665 try { 3666 boolean res; 3667 if (finishTask && r == rootR) { 3668 // If requested, remove the task that is associated to this activity only if it 3669 // was the root activity in the task. The result code and data is ignored because 3670 // we don't support returning them across task boundaries. 3671 res = removeTaskByIdLocked(tr.taskId, 0); 3672 } else { 3673 res = tr.stack.requestFinishActivityLocked(token, resultCode, 3674 resultData, "app-request", true); 3675 } 3676 return res; 3677 } finally { 3678 Binder.restoreCallingIdentity(origId); 3679 } 3680 } 3681 } 3682 3683 @Override 3684 public final void finishHeavyWeightApp() { 3685 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 3686 != PackageManager.PERMISSION_GRANTED) { 3687 String msg = "Permission Denial: finishHeavyWeightApp() from pid=" 3688 + Binder.getCallingPid() 3689 + ", uid=" + Binder.getCallingUid() 3690 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 3691 Slog.w(TAG, msg); 3692 throw new SecurityException(msg); 3693 } 3694 3695 synchronized(this) { 3696 if (mHeavyWeightProcess == null) { 3697 return; 3698 } 3699 3700 ArrayList<ActivityRecord> activities = new ArrayList<ActivityRecord>( 3701 mHeavyWeightProcess.activities); 3702 for (int i=0; i<activities.size(); i++) { 3703 ActivityRecord r = activities.get(i); 3704 if (!r.finishing) { 3705 r.task.stack.finishActivityLocked(r, Activity.RESULT_CANCELED, 3706 null, "finish-heavy", true); 3707 } 3708 } 3709 3710 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 3711 mHeavyWeightProcess.userId, 0)); 3712 mHeavyWeightProcess = null; 3713 } 3714 } 3715 3716 @Override 3717 public void crashApplication(int uid, int initialPid, String packageName, 3718 String message) { 3719 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 3720 != PackageManager.PERMISSION_GRANTED) { 3721 String msg = "Permission Denial: crashApplication() from pid=" 3722 + Binder.getCallingPid() 3723 + ", uid=" + Binder.getCallingUid() 3724 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 3725 Slog.w(TAG, msg); 3726 throw new SecurityException(msg); 3727 } 3728 3729 synchronized(this) { 3730 ProcessRecord proc = null; 3731 3732 // Figure out which process to kill. We don't trust that initialPid 3733 // still has any relation to current pids, so must scan through the 3734 // list. 3735 synchronized (mPidsSelfLocked) { 3736 for (int i=0; i<mPidsSelfLocked.size(); i++) { 3737 ProcessRecord p = mPidsSelfLocked.valueAt(i); 3738 if (p.uid != uid) { 3739 continue; 3740 } 3741 if (p.pid == initialPid) { 3742 proc = p; 3743 break; 3744 } 3745 if (p.pkgList.containsKey(packageName)) { 3746 proc = p; 3747 } 3748 } 3749 } 3750 3751 if (proc == null) { 3752 Slog.w(TAG, "crashApplication: nothing for uid=" + uid 3753 + " initialPid=" + initialPid 3754 + " packageName=" + packageName); 3755 return; 3756 } 3757 3758 if (proc.thread != null) { 3759 if (proc.pid == Process.myPid()) { 3760 Log.w(TAG, "crashApplication: trying to crash self!"); 3761 return; 3762 } 3763 long ident = Binder.clearCallingIdentity(); 3764 try { 3765 proc.thread.scheduleCrash(message); 3766 } catch (RemoteException e) { 3767 } 3768 Binder.restoreCallingIdentity(ident); 3769 } 3770 } 3771 } 3772 3773 @Override 3774 public final void finishSubActivity(IBinder token, String resultWho, 3775 int requestCode) { 3776 synchronized(this) { 3777 final long origId = Binder.clearCallingIdentity(); 3778 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3779 if (r != null) { 3780 r.task.stack.finishSubActivityLocked(r, resultWho, requestCode); 3781 } 3782 Binder.restoreCallingIdentity(origId); 3783 } 3784 } 3785 3786 @Override 3787 public boolean finishActivityAffinity(IBinder token) { 3788 synchronized(this) { 3789 final long origId = Binder.clearCallingIdentity(); 3790 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3791 boolean res = false; 3792 if (r != null) { 3793 res = r.task.stack.finishActivityAffinityLocked(r); 3794 } 3795 Binder.restoreCallingIdentity(origId); 3796 return res; 3797 } 3798 } 3799 3800 @Override 3801 public boolean willActivityBeVisible(IBinder token) { 3802 synchronized(this) { 3803 ActivityStack stack = ActivityRecord.getStackLocked(token); 3804 if (stack != null) { 3805 return stack.willActivityBeVisibleLocked(token); 3806 } 3807 return false; 3808 } 3809 } 3810 3811 @Override 3812 public void overridePendingTransition(IBinder token, String packageName, 3813 int enterAnim, int exitAnim) { 3814 synchronized(this) { 3815 ActivityRecord self = ActivityRecord.isInStackLocked(token); 3816 if (self == null) { 3817 return; 3818 } 3819 3820 final long origId = Binder.clearCallingIdentity(); 3821 3822 if (self.state == ActivityState.RESUMED 3823 || self.state == ActivityState.PAUSING) { 3824 mWindowManager.overridePendingAppTransition(packageName, 3825 enterAnim, exitAnim, null); 3826 } 3827 3828 Binder.restoreCallingIdentity(origId); 3829 } 3830 } 3831 3832 /** 3833 * Main function for removing an existing process from the activity manager 3834 * as a result of that process going away. Clears out all connections 3835 * to the process. 3836 */ 3837 private final void handleAppDiedLocked(ProcessRecord app, 3838 boolean restarting, boolean allowRestart) { 3839 int pid = app.pid; 3840 cleanUpApplicationRecordLocked(app, restarting, allowRestart, -1); 3841 if (!restarting) { 3842 removeLruProcessLocked(app); 3843 if (pid > 0) { 3844 ProcessList.remove(pid); 3845 } 3846 } 3847 3848 if (mProfileProc == app) { 3849 clearProfilerLocked(); 3850 } 3851 3852 // Remove this application's activities from active lists. 3853 boolean hasVisibleActivities = mStackSupervisor.handleAppDiedLocked(app); 3854 3855 app.activities.clear(); 3856 3857 if (app.instrumentationClass != null) { 3858 Slog.w(TAG, "Crash of app " + app.processName 3859 + " running instrumentation " + app.instrumentationClass); 3860 Bundle info = new Bundle(); 3861 info.putString("shortMsg", "Process crashed."); 3862 finishInstrumentationLocked(app, Activity.RESULT_CANCELED, info); 3863 } 3864 3865 if (!restarting) { 3866 if (!mStackSupervisor.resumeTopActivitiesLocked()) { 3867 // If there was nothing to resume, and we are not already 3868 // restarting this process, but there is a visible activity that 3869 // is hosted by the process... then make sure all visible 3870 // activities are running, taking care of restarting this 3871 // process. 3872 if (hasVisibleActivities) { 3873 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 3874 } 3875 } 3876 } 3877 } 3878 3879 private final int getLRURecordIndexForAppLocked(IApplicationThread thread) { 3880 IBinder threadBinder = thread.asBinder(); 3881 // Find the application record. 3882 for (int i=mLruProcesses.size()-1; i>=0; i--) { 3883 ProcessRecord rec = mLruProcesses.get(i); 3884 if (rec.thread != null && rec.thread.asBinder() == threadBinder) { 3885 return i; 3886 } 3887 } 3888 return -1; 3889 } 3890 3891 final ProcessRecord getRecordForAppLocked( 3892 IApplicationThread thread) { 3893 if (thread == null) { 3894 return null; 3895 } 3896 3897 int appIndex = getLRURecordIndexForAppLocked(thread); 3898 return appIndex >= 0 ? mLruProcesses.get(appIndex) : null; 3899 } 3900 3901 final void doLowMemReportIfNeededLocked(ProcessRecord dyingProc) { 3902 // If there are no longer any background processes running, 3903 // and the app that died was not running instrumentation, 3904 // then tell everyone we are now low on memory. 3905 boolean haveBg = false; 3906 for (int i=mLruProcesses.size()-1; i>=0; i--) { 3907 ProcessRecord rec = mLruProcesses.get(i); 3908 if (rec.thread != null 3909 && rec.setProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 3910 haveBg = true; 3911 break; 3912 } 3913 } 3914 3915 if (!haveBg) { 3916 boolean doReport = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 3917 if (doReport) { 3918 long now = SystemClock.uptimeMillis(); 3919 if (now < (mLastMemUsageReportTime+5*60*1000)) { 3920 doReport = false; 3921 } else { 3922 mLastMemUsageReportTime = now; 3923 } 3924 } 3925 final ArrayList<ProcessMemInfo> memInfos 3926 = doReport ? new ArrayList<ProcessMemInfo>(mLruProcesses.size()) : null; 3927 EventLog.writeEvent(EventLogTags.AM_LOW_MEMORY, mLruProcesses.size()); 3928 long now = SystemClock.uptimeMillis(); 3929 for (int i=mLruProcesses.size()-1; i>=0; i--) { 3930 ProcessRecord rec = mLruProcesses.get(i); 3931 if (rec == dyingProc || rec.thread == null) { 3932 continue; 3933 } 3934 if (doReport) { 3935 memInfos.add(new ProcessMemInfo(rec.processName, rec.pid, rec.setAdj, 3936 rec.setProcState, rec.adjType, rec.makeAdjReason())); 3937 } 3938 if ((rec.lastLowMemory+GC_MIN_INTERVAL) <= now) { 3939 // The low memory report is overriding any current 3940 // state for a GC request. Make sure to do 3941 // heavy/important/visible/foreground processes first. 3942 if (rec.setAdj <= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 3943 rec.lastRequestedGc = 0; 3944 } else { 3945 rec.lastRequestedGc = rec.lastLowMemory; 3946 } 3947 rec.reportLowMemory = true; 3948 rec.lastLowMemory = now; 3949 mProcessesToGc.remove(rec); 3950 addProcessToGcListLocked(rec); 3951 } 3952 } 3953 if (doReport) { 3954 Message msg = mHandler.obtainMessage(REPORT_MEM_USAGE_MSG, memInfos); 3955 mHandler.sendMessage(msg); 3956 } 3957 scheduleAppGcsLocked(); 3958 } 3959 } 3960 3961 final void appDiedLocked(ProcessRecord app, int pid, 3962 IApplicationThread thread) { 3963 3964 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 3965 synchronized (stats) { 3966 stats.noteProcessDiedLocked(app.info.uid, pid); 3967 } 3968 3969 // Clean up already done if the process has been re-started. 3970 if (app.pid == pid && app.thread != null && 3971 app.thread.asBinder() == thread.asBinder()) { 3972 boolean doLowMem = app.instrumentationClass == null; 3973 boolean doOomAdj = doLowMem; 3974 if (!app.killedByAm) { 3975 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 3976 + ") has died."); 3977 mAllowLowerMemLevel = true; 3978 } else { 3979 // Note that we always want to do oom adj to update our state with the 3980 // new number of procs. 3981 mAllowLowerMemLevel = false; 3982 doLowMem = false; 3983 } 3984 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 3985 if (DEBUG_CLEANUP) Slog.v( 3986 TAG, "Dying app: " + app + ", pid: " + pid 3987 + ", thread: " + thread.asBinder()); 3988 handleAppDiedLocked(app, false, true); 3989 3990 if (doOomAdj) { 3991 updateOomAdjLocked(); 3992 } 3993 if (doLowMem) { 3994 doLowMemReportIfNeededLocked(app); 3995 } 3996 } else if (app.pid != pid) { 3997 // A new process has already been started. 3998 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 3999 + ") has died and restarted (pid " + app.pid + ")."); 4000 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4001 } else if (DEBUG_PROCESSES) { 4002 Slog.d(TAG, "Received spurious death notification for thread " 4003 + thread.asBinder()); 4004 } 4005 } 4006 4007 /** 4008 * If a stack trace dump file is configured, dump process stack traces. 4009 * @param clearTraces causes the dump file to be erased prior to the new 4010 * traces being written, if true; when false, the new traces will be 4011 * appended to any existing file content. 4012 * @param firstPids of dalvik VM processes to dump stack traces for first 4013 * @param lastPids of dalvik VM processes to dump stack traces for last 4014 * @param nativeProcs optional list of native process names to dump stack crawls 4015 * @return file containing stack traces, or null if no dump file is configured 4016 */ 4017 public static File dumpStackTraces(boolean clearTraces, ArrayList<Integer> firstPids, 4018 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4019 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4020 if (tracesPath == null || tracesPath.length() == 0) { 4021 return null; 4022 } 4023 4024 File tracesFile = new File(tracesPath); 4025 try { 4026 File tracesDir = tracesFile.getParentFile(); 4027 if (!tracesDir.exists()) { 4028 tracesFile.mkdirs(); 4029 if (!SELinux.restorecon(tracesDir)) { 4030 return null; 4031 } 4032 } 4033 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4034 4035 if (clearTraces && tracesFile.exists()) tracesFile.delete(); 4036 tracesFile.createNewFile(); 4037 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4038 } catch (IOException e) { 4039 Slog.w(TAG, "Unable to prepare ANR traces file: " + tracesPath, e); 4040 return null; 4041 } 4042 4043 dumpStackTraces(tracesPath, firstPids, processCpuTracker, lastPids, nativeProcs); 4044 return tracesFile; 4045 } 4046 4047 private static void dumpStackTraces(String tracesPath, ArrayList<Integer> firstPids, 4048 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4049 // Use a FileObserver to detect when traces finish writing. 4050 // The order of traces is considered important to maintain for legibility. 4051 FileObserver observer = new FileObserver(tracesPath, FileObserver.CLOSE_WRITE) { 4052 @Override 4053 public synchronized void onEvent(int event, String path) { notify(); } 4054 }; 4055 4056 try { 4057 observer.startWatching(); 4058 4059 // First collect all of the stacks of the most important pids. 4060 if (firstPids != null) { 4061 try { 4062 int num = firstPids.size(); 4063 for (int i = 0; i < num; i++) { 4064 synchronized (observer) { 4065 Process.sendSignal(firstPids.get(i), Process.SIGNAL_QUIT); 4066 observer.wait(200); // Wait for write-close, give up after 200msec 4067 } 4068 } 4069 } catch (InterruptedException e) { 4070 Log.wtf(TAG, e); 4071 } 4072 } 4073 4074 // Next collect the stacks of the native pids 4075 if (nativeProcs != null) { 4076 int[] pids = Process.getPidsForCommands(nativeProcs); 4077 if (pids != null) { 4078 for (int pid : pids) { 4079 Debug.dumpNativeBacktraceToFile(pid, tracesPath); 4080 } 4081 } 4082 } 4083 4084 // Lastly, measure CPU usage. 4085 if (processCpuTracker != null) { 4086 processCpuTracker.init(); 4087 System.gc(); 4088 processCpuTracker.update(); 4089 try { 4090 synchronized (processCpuTracker) { 4091 processCpuTracker.wait(500); // measure over 1/2 second. 4092 } 4093 } catch (InterruptedException e) { 4094 } 4095 processCpuTracker.update(); 4096 4097 // We'll take the stack crawls of just the top apps using CPU. 4098 final int N = processCpuTracker.countWorkingStats(); 4099 int numProcs = 0; 4100 for (int i=0; i<N && numProcs<5; i++) { 4101 ProcessCpuTracker.Stats stats = processCpuTracker.getWorkingStats(i); 4102 if (lastPids.indexOfKey(stats.pid) >= 0) { 4103 numProcs++; 4104 try { 4105 synchronized (observer) { 4106 Process.sendSignal(stats.pid, Process.SIGNAL_QUIT); 4107 observer.wait(200); // Wait for write-close, give up after 200msec 4108 } 4109 } catch (InterruptedException e) { 4110 Log.wtf(TAG, e); 4111 } 4112 4113 } 4114 } 4115 } 4116 } finally { 4117 observer.stopWatching(); 4118 } 4119 } 4120 4121 final void logAppTooSlow(ProcessRecord app, long startTime, String msg) { 4122 if (true || IS_USER_BUILD) { 4123 return; 4124 } 4125 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4126 if (tracesPath == null || tracesPath.length() == 0) { 4127 return; 4128 } 4129 4130 StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads(); 4131 StrictMode.allowThreadDiskWrites(); 4132 try { 4133 final File tracesFile = new File(tracesPath); 4134 final File tracesDir = tracesFile.getParentFile(); 4135 final File tracesTmp = new File(tracesDir, "__tmp__"); 4136 try { 4137 if (!tracesDir.exists()) { 4138 tracesFile.mkdirs(); 4139 if (!SELinux.restorecon(tracesDir.getPath())) { 4140 return; 4141 } 4142 } 4143 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4144 4145 if (tracesFile.exists()) { 4146 tracesTmp.delete(); 4147 tracesFile.renameTo(tracesTmp); 4148 } 4149 StringBuilder sb = new StringBuilder(); 4150 Time tobj = new Time(); 4151 tobj.set(System.currentTimeMillis()); 4152 sb.append(tobj.format("%Y-%m-%d %H:%M:%S")); 4153 sb.append(": "); 4154 TimeUtils.formatDuration(SystemClock.uptimeMillis()-startTime, sb); 4155 sb.append(" since "); 4156 sb.append(msg); 4157 FileOutputStream fos = new FileOutputStream(tracesFile); 4158 fos.write(sb.toString().getBytes()); 4159 if (app == null) { 4160 fos.write("\n*** No application process!".getBytes()); 4161 } 4162 fos.close(); 4163 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4164 } catch (IOException e) { 4165 Slog.w(TAG, "Unable to prepare slow app traces file: " + tracesPath, e); 4166 return; 4167 } 4168 4169 if (app != null) { 4170 ArrayList<Integer> firstPids = new ArrayList<Integer>(); 4171 firstPids.add(app.pid); 4172 dumpStackTraces(tracesPath, firstPids, null, null, null); 4173 } 4174 4175 File lastTracesFile = null; 4176 File curTracesFile = null; 4177 for (int i=9; i>=0; i--) { 4178 String name = String.format(Locale.US, "slow%02d.txt", i); 4179 curTracesFile = new File(tracesDir, name); 4180 if (curTracesFile.exists()) { 4181 if (lastTracesFile != null) { 4182 curTracesFile.renameTo(lastTracesFile); 4183 } else { 4184 curTracesFile.delete(); 4185 } 4186 } 4187 lastTracesFile = curTracesFile; 4188 } 4189 tracesFile.renameTo(curTracesFile); 4190 if (tracesTmp.exists()) { 4191 tracesTmp.renameTo(tracesFile); 4192 } 4193 } finally { 4194 StrictMode.setThreadPolicy(oldPolicy); 4195 } 4196 } 4197 4198 final void appNotResponding(ProcessRecord app, ActivityRecord activity, 4199 ActivityRecord parent, boolean aboveSystem, final String annotation) { 4200 ArrayList<Integer> firstPids = new ArrayList<Integer>(5); 4201 SparseArray<Boolean> lastPids = new SparseArray<Boolean>(20); 4202 4203 if (mController != null) { 4204 try { 4205 // 0 == continue, -1 = kill process immediately 4206 int res = mController.appEarlyNotResponding(app.processName, app.pid, annotation); 4207 if (res < 0 && app.pid != MY_PID) Process.killProcess(app.pid); 4208 } catch (RemoteException e) { 4209 mController = null; 4210 Watchdog.getInstance().setActivityController(null); 4211 } 4212 } 4213 4214 long anrTime = SystemClock.uptimeMillis(); 4215 if (MONITOR_CPU_USAGE) { 4216 updateCpuStatsNow(); 4217 } 4218 4219 synchronized (this) { 4220 // PowerManager.reboot() can block for a long time, so ignore ANRs while shutting down. 4221 if (mShuttingDown) { 4222 Slog.i(TAG, "During shutdown skipping ANR: " + app + " " + annotation); 4223 return; 4224 } else if (app.notResponding) { 4225 Slog.i(TAG, "Skipping duplicate ANR: " + app + " " + annotation); 4226 return; 4227 } else if (app.crashing) { 4228 Slog.i(TAG, "Crashing app skipping ANR: " + app + " " + annotation); 4229 return; 4230 } 4231 4232 // In case we come through here for the same app before completing 4233 // this one, mark as anring now so we will bail out. 4234 app.notResponding = true; 4235 4236 // Log the ANR to the event log. 4237 EventLog.writeEvent(EventLogTags.AM_ANR, app.userId, app.pid, 4238 app.processName, app.info.flags, annotation); 4239 4240 // Dump thread traces as quickly as we can, starting with "interesting" processes. 4241 firstPids.add(app.pid); 4242 4243 int parentPid = app.pid; 4244 if (parent != null && parent.app != null && parent.app.pid > 0) parentPid = parent.app.pid; 4245 if (parentPid != app.pid) firstPids.add(parentPid); 4246 4247 if (MY_PID != app.pid && MY_PID != parentPid) firstPids.add(MY_PID); 4248 4249 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 4250 ProcessRecord r = mLruProcesses.get(i); 4251 if (r != null && r.thread != null) { 4252 int pid = r.pid; 4253 if (pid > 0 && pid != app.pid && pid != parentPid && pid != MY_PID) { 4254 if (r.persistent) { 4255 firstPids.add(pid); 4256 } else { 4257 lastPids.put(pid, Boolean.TRUE); 4258 } 4259 } 4260 } 4261 } 4262 } 4263 4264 // Log the ANR to the main log. 4265 StringBuilder info = new StringBuilder(); 4266 info.setLength(0); 4267 info.append("ANR in ").append(app.processName); 4268 if (activity != null && activity.shortComponentName != null) { 4269 info.append(" (").append(activity.shortComponentName).append(")"); 4270 } 4271 info.append("\n"); 4272 info.append("PID: ").append(app.pid).append("\n"); 4273 if (annotation != null) { 4274 info.append("Reason: ").append(annotation).append("\n"); 4275 } 4276 if (parent != null && parent != activity) { 4277 info.append("Parent: ").append(parent.shortComponentName).append("\n"); 4278 } 4279 4280 final ProcessCpuTracker processCpuTracker = new ProcessCpuTracker(true); 4281 4282 File tracesFile = dumpStackTraces(true, firstPids, processCpuTracker, lastPids, 4283 NATIVE_STACKS_OF_INTEREST); 4284 4285 String cpuInfo = null; 4286 if (MONITOR_CPU_USAGE) { 4287 updateCpuStatsNow(); 4288 synchronized (mProcessCpuThread) { 4289 cpuInfo = mProcessCpuTracker.printCurrentState(anrTime); 4290 } 4291 info.append(processCpuTracker.printCurrentLoad()); 4292 info.append(cpuInfo); 4293 } 4294 4295 info.append(processCpuTracker.printCurrentState(anrTime)); 4296 4297 Slog.e(TAG, info.toString()); 4298 if (tracesFile == null) { 4299 // There is no trace file, so dump (only) the alleged culprit's threads to the log 4300 Process.sendSignal(app.pid, Process.SIGNAL_QUIT); 4301 } 4302 4303 addErrorToDropBox("anr", app, app.processName, activity, parent, annotation, 4304 cpuInfo, tracesFile, null); 4305 4306 if (mController != null) { 4307 try { 4308 // 0 == show dialog, 1 = keep waiting, -1 = kill process immediately 4309 int res = mController.appNotResponding(app.processName, app.pid, info.toString()); 4310 if (res != 0) { 4311 if (res < 0 && app.pid != MY_PID) { 4312 Process.killProcess(app.pid); 4313 } else { 4314 synchronized (this) { 4315 mServices.scheduleServiceTimeoutLocked(app); 4316 } 4317 } 4318 return; 4319 } 4320 } catch (RemoteException e) { 4321 mController = null; 4322 Watchdog.getInstance().setActivityController(null); 4323 } 4324 } 4325 4326 // Unless configured otherwise, swallow ANRs in background processes & kill the process. 4327 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 4328 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 4329 4330 synchronized (this) { 4331 if (!showBackground && !app.isInterestingToUserLocked() && app.pid != MY_PID) { 4332 killUnneededProcessLocked(app, "background ANR"); 4333 return; 4334 } 4335 4336 // Set the app's notResponding state, and look up the errorReportReceiver 4337 makeAppNotRespondingLocked(app, 4338 activity != null ? activity.shortComponentName : null, 4339 annotation != null ? "ANR " + annotation : "ANR", 4340 info.toString()); 4341 4342 // Bring up the infamous App Not Responding dialog 4343 Message msg = Message.obtain(); 4344 HashMap<String, Object> map = new HashMap<String, Object>(); 4345 msg.what = SHOW_NOT_RESPONDING_MSG; 4346 msg.obj = map; 4347 msg.arg1 = aboveSystem ? 1 : 0; 4348 map.put("app", app); 4349 if (activity != null) { 4350 map.put("activity", activity); 4351 } 4352 4353 mHandler.sendMessage(msg); 4354 } 4355 } 4356 4357 final void showLaunchWarningLocked(final ActivityRecord cur, final ActivityRecord next) { 4358 if (!mLaunchWarningShown) { 4359 mLaunchWarningShown = true; 4360 mHandler.post(new Runnable() { 4361 @Override 4362 public void run() { 4363 synchronized (ActivityManagerService.this) { 4364 final Dialog d = new LaunchWarningWindow(mContext, cur, next); 4365 d.show(); 4366 mHandler.postDelayed(new Runnable() { 4367 @Override 4368 public void run() { 4369 synchronized (ActivityManagerService.this) { 4370 d.dismiss(); 4371 mLaunchWarningShown = false; 4372 } 4373 } 4374 }, 4000); 4375 } 4376 } 4377 }); 4378 } 4379 } 4380 4381 @Override 4382 public boolean clearApplicationUserData(final String packageName, 4383 final IPackageDataObserver observer, int userId) { 4384 enforceNotIsolatedCaller("clearApplicationUserData"); 4385 int uid = Binder.getCallingUid(); 4386 int pid = Binder.getCallingPid(); 4387 userId = handleIncomingUser(pid, uid, 4388 userId, false, true, "clearApplicationUserData", null); 4389 long callingId = Binder.clearCallingIdentity(); 4390 try { 4391 IPackageManager pm = AppGlobals.getPackageManager(); 4392 int pkgUid = -1; 4393 synchronized(this) { 4394 try { 4395 pkgUid = pm.getPackageUid(packageName, userId); 4396 } catch (RemoteException e) { 4397 } 4398 if (pkgUid == -1) { 4399 Slog.w(TAG, "Invalid packageName: " + packageName); 4400 if (observer != null) { 4401 try { 4402 observer.onRemoveCompleted(packageName, false); 4403 } catch (RemoteException e) { 4404 Slog.i(TAG, "Observer no longer exists."); 4405 } 4406 } 4407 return false; 4408 } 4409 if (uid == pkgUid || checkComponentPermission( 4410 android.Manifest.permission.CLEAR_APP_USER_DATA, 4411 pid, uid, -1, true) 4412 == PackageManager.PERMISSION_GRANTED) { 4413 forceStopPackageLocked(packageName, pkgUid, "clear data"); 4414 } else { 4415 throw new SecurityException("PID " + pid + " does not have permission " 4416 + android.Manifest.permission.CLEAR_APP_USER_DATA + " to clear data" 4417 + " of package " + packageName); 4418 } 4419 } 4420 4421 try { 4422 // Clear application user data 4423 pm.clearApplicationUserData(packageName, observer, userId); 4424 4425 // Remove all permissions granted from/to this package 4426 removeUriPermissionsForPackageLocked(packageName, userId, true); 4427 4428 Intent intent = new Intent(Intent.ACTION_PACKAGE_DATA_CLEARED, 4429 Uri.fromParts("package", packageName, null)); 4430 intent.putExtra(Intent.EXTRA_UID, pkgUid); 4431 broadcastIntentInPackage("android", Process.SYSTEM_UID, intent, 4432 null, null, 0, null, null, null, false, false, userId); 4433 } catch (RemoteException e) { 4434 } 4435 } finally { 4436 Binder.restoreCallingIdentity(callingId); 4437 } 4438 return true; 4439 } 4440 4441 @Override 4442 public void killBackgroundProcesses(final String packageName, int userId) { 4443 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 4444 != PackageManager.PERMISSION_GRANTED && 4445 checkCallingPermission(android.Manifest.permission.RESTART_PACKAGES) 4446 != PackageManager.PERMISSION_GRANTED) { 4447 String msg = "Permission Denial: killBackgroundProcesses() from pid=" 4448 + Binder.getCallingPid() 4449 + ", uid=" + Binder.getCallingUid() 4450 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 4451 Slog.w(TAG, msg); 4452 throw new SecurityException(msg); 4453 } 4454 4455 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4456 userId, true, true, "killBackgroundProcesses", null); 4457 long callingId = Binder.clearCallingIdentity(); 4458 try { 4459 IPackageManager pm = AppGlobals.getPackageManager(); 4460 synchronized(this) { 4461 int appId = -1; 4462 try { 4463 appId = UserHandle.getAppId(pm.getPackageUid(packageName, 0)); 4464 } catch (RemoteException e) { 4465 } 4466 if (appId == -1) { 4467 Slog.w(TAG, "Invalid packageName: " + packageName); 4468 return; 4469 } 4470 killPackageProcessesLocked(packageName, appId, userId, 4471 ProcessList.SERVICE_ADJ, false, true, true, false, "kill background"); 4472 } 4473 } finally { 4474 Binder.restoreCallingIdentity(callingId); 4475 } 4476 } 4477 4478 @Override 4479 public void killAllBackgroundProcesses() { 4480 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 4481 != PackageManager.PERMISSION_GRANTED) { 4482 String msg = "Permission Denial: killAllBackgroundProcesses() from pid=" 4483 + Binder.getCallingPid() 4484 + ", uid=" + Binder.getCallingUid() 4485 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 4486 Slog.w(TAG, msg); 4487 throw new SecurityException(msg); 4488 } 4489 4490 long callingId = Binder.clearCallingIdentity(); 4491 try { 4492 synchronized(this) { 4493 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 4494 final int NP = mProcessNames.getMap().size(); 4495 for (int ip=0; ip<NP; ip++) { 4496 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 4497 final int NA = apps.size(); 4498 for (int ia=0; ia<NA; ia++) { 4499 ProcessRecord app = apps.valueAt(ia); 4500 if (app.persistent) { 4501 // we don't kill persistent processes 4502 continue; 4503 } 4504 if (app.removed) { 4505 procs.add(app); 4506 } else if (app.setAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 4507 app.removed = true; 4508 procs.add(app); 4509 } 4510 } 4511 } 4512 4513 int N = procs.size(); 4514 for (int i=0; i<N; i++) { 4515 removeProcessLocked(procs.get(i), false, true, "kill all background"); 4516 } 4517 mAllowLowerMemLevel = true; 4518 updateOomAdjLocked(); 4519 doLowMemReportIfNeededLocked(null); 4520 } 4521 } finally { 4522 Binder.restoreCallingIdentity(callingId); 4523 } 4524 } 4525 4526 @Override 4527 public void forceStopPackage(final String packageName, int userId) { 4528 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4529 != PackageManager.PERMISSION_GRANTED) { 4530 String msg = "Permission Denial: forceStopPackage() from pid=" 4531 + Binder.getCallingPid() 4532 + ", uid=" + Binder.getCallingUid() 4533 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4534 Slog.w(TAG, msg); 4535 throw new SecurityException(msg); 4536 } 4537 final int callingPid = Binder.getCallingPid(); 4538 userId = handleIncomingUser(callingPid, Binder.getCallingUid(), 4539 userId, true, true, "forceStopPackage", null); 4540 long callingId = Binder.clearCallingIdentity(); 4541 try { 4542 IPackageManager pm = AppGlobals.getPackageManager(); 4543 synchronized(this) { 4544 int[] users = userId == UserHandle.USER_ALL 4545 ? getUsersLocked() : new int[] { userId }; 4546 for (int user : users) { 4547 int pkgUid = -1; 4548 try { 4549 pkgUid = pm.getPackageUid(packageName, user); 4550 } catch (RemoteException e) { 4551 } 4552 if (pkgUid == -1) { 4553 Slog.w(TAG, "Invalid packageName: " + packageName); 4554 continue; 4555 } 4556 try { 4557 pm.setPackageStoppedState(packageName, true, user); 4558 } catch (RemoteException e) { 4559 } catch (IllegalArgumentException e) { 4560 Slog.w(TAG, "Failed trying to unstop package " 4561 + packageName + ": " + e); 4562 } 4563 if (isUserRunningLocked(user, false)) { 4564 forceStopPackageLocked(packageName, pkgUid, "from pid " + callingPid); 4565 } 4566 } 4567 } 4568 } finally { 4569 Binder.restoreCallingIdentity(callingId); 4570 } 4571 } 4572 4573 /* 4574 * The pkg name and app id have to be specified. 4575 */ 4576 @Override 4577 public void killApplicationWithAppId(String pkg, int appid, String reason) { 4578 if (pkg == null) { 4579 return; 4580 } 4581 // Make sure the uid is valid. 4582 if (appid < 0) { 4583 Slog.w(TAG, "Invalid appid specified for pkg : " + pkg); 4584 return; 4585 } 4586 int callerUid = Binder.getCallingUid(); 4587 // Only the system server can kill an application 4588 if (callerUid == Process.SYSTEM_UID) { 4589 // Post an aysnc message to kill the application 4590 Message msg = mHandler.obtainMessage(KILL_APPLICATION_MSG); 4591 msg.arg1 = appid; 4592 msg.arg2 = 0; 4593 Bundle bundle = new Bundle(); 4594 bundle.putString("pkg", pkg); 4595 bundle.putString("reason", reason); 4596 msg.obj = bundle; 4597 mHandler.sendMessage(msg); 4598 } else { 4599 throw new SecurityException(callerUid + " cannot kill pkg: " + 4600 pkg); 4601 } 4602 } 4603 4604 @Override 4605 public void closeSystemDialogs(String reason) { 4606 enforceNotIsolatedCaller("closeSystemDialogs"); 4607 4608 final int pid = Binder.getCallingPid(); 4609 final int uid = Binder.getCallingUid(); 4610 final long origId = Binder.clearCallingIdentity(); 4611 try { 4612 synchronized (this) { 4613 // Only allow this from foreground processes, so that background 4614 // applications can't abuse it to prevent system UI from being shown. 4615 if (uid >= Process.FIRST_APPLICATION_UID) { 4616 ProcessRecord proc; 4617 synchronized (mPidsSelfLocked) { 4618 proc = mPidsSelfLocked.get(pid); 4619 } 4620 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 4621 Slog.w(TAG, "Ignoring closeSystemDialogs " + reason 4622 + " from background process " + proc); 4623 return; 4624 } 4625 } 4626 closeSystemDialogsLocked(reason); 4627 } 4628 } finally { 4629 Binder.restoreCallingIdentity(origId); 4630 } 4631 } 4632 4633 void closeSystemDialogsLocked(String reason) { 4634 Intent intent = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS); 4635 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4636 | Intent.FLAG_RECEIVER_FOREGROUND); 4637 if (reason != null) { 4638 intent.putExtra("reason", reason); 4639 } 4640 mWindowManager.closeSystemDialogs(reason); 4641 4642 mStackSupervisor.closeSystemDialogsLocked(); 4643 4644 broadcastIntentLocked(null, null, intent, null, 4645 null, 0, null, null, null, AppOpsManager.OP_NONE, false, false, -1, 4646 Process.SYSTEM_UID, UserHandle.USER_ALL); 4647 } 4648 4649 @Override 4650 public Debug.MemoryInfo[] getProcessMemoryInfo(int[] pids) { 4651 enforceNotIsolatedCaller("getProcessMemoryInfo"); 4652 Debug.MemoryInfo[] infos = new Debug.MemoryInfo[pids.length]; 4653 for (int i=pids.length-1; i>=0; i--) { 4654 ProcessRecord proc; 4655 int oomAdj; 4656 synchronized (this) { 4657 synchronized (mPidsSelfLocked) { 4658 proc = mPidsSelfLocked.get(pids[i]); 4659 oomAdj = proc != null ? proc.setAdj : 0; 4660 } 4661 } 4662 infos[i] = new Debug.MemoryInfo(); 4663 Debug.getMemoryInfo(pids[i], infos[i]); 4664 if (proc != null) { 4665 synchronized (this) { 4666 if (proc.thread != null && proc.setAdj == oomAdj) { 4667 // Record this for posterity if the process has been stable. 4668 proc.baseProcessTracker.addPss(infos[i].getTotalPss(), 4669 infos[i].getTotalUss(), false, proc.pkgList); 4670 } 4671 } 4672 } 4673 } 4674 return infos; 4675 } 4676 4677 @Override 4678 public long[] getProcessPss(int[] pids) { 4679 enforceNotIsolatedCaller("getProcessPss"); 4680 long[] pss = new long[pids.length]; 4681 for (int i=pids.length-1; i>=0; i--) { 4682 ProcessRecord proc; 4683 int oomAdj; 4684 synchronized (this) { 4685 synchronized (mPidsSelfLocked) { 4686 proc = mPidsSelfLocked.get(pids[i]); 4687 oomAdj = proc != null ? proc.setAdj : 0; 4688 } 4689 } 4690 long[] tmpUss = new long[1]; 4691 pss[i] = Debug.getPss(pids[i], tmpUss); 4692 if (proc != null) { 4693 synchronized (this) { 4694 if (proc.thread != null && proc.setAdj == oomAdj) { 4695 // Record this for posterity if the process has been stable. 4696 proc.baseProcessTracker.addPss(pss[i], tmpUss[0], false, proc.pkgList); 4697 } 4698 } 4699 } 4700 } 4701 return pss; 4702 } 4703 4704 @Override 4705 public void killApplicationProcess(String processName, int uid) { 4706 if (processName == null) { 4707 return; 4708 } 4709 4710 int callerUid = Binder.getCallingUid(); 4711 // Only the system server can kill an application 4712 if (callerUid == Process.SYSTEM_UID) { 4713 synchronized (this) { 4714 ProcessRecord app = getProcessRecordLocked(processName, uid, true); 4715 if (app != null && app.thread != null) { 4716 try { 4717 app.thread.scheduleSuicide(); 4718 } catch (RemoteException e) { 4719 // If the other end already died, then our work here is done. 4720 } 4721 } else { 4722 Slog.w(TAG, "Process/uid not found attempting kill of " 4723 + processName + " / " + uid); 4724 } 4725 } 4726 } else { 4727 throw new SecurityException(callerUid + " cannot kill app process: " + 4728 processName); 4729 } 4730 } 4731 4732 private void forceStopPackageLocked(final String packageName, int uid, String reason) { 4733 forceStopPackageLocked(packageName, UserHandle.getAppId(uid), false, 4734 false, true, false, false, UserHandle.getUserId(uid), reason); 4735 Intent intent = new Intent(Intent.ACTION_PACKAGE_RESTARTED, 4736 Uri.fromParts("package", packageName, null)); 4737 if (!mProcessesReady) { 4738 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4739 | Intent.FLAG_RECEIVER_FOREGROUND); 4740 } 4741 intent.putExtra(Intent.EXTRA_UID, uid); 4742 intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(uid)); 4743 broadcastIntentLocked(null, null, intent, 4744 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 4745 false, false, 4746 MY_PID, Process.SYSTEM_UID, UserHandle.getUserId(uid)); 4747 } 4748 4749 private void forceStopUserLocked(int userId, String reason) { 4750 forceStopPackageLocked(null, -1, false, false, true, false, false, userId, reason); 4751 Intent intent = new Intent(Intent.ACTION_USER_STOPPED); 4752 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4753 | Intent.FLAG_RECEIVER_FOREGROUND); 4754 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 4755 broadcastIntentLocked(null, null, intent, 4756 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 4757 false, false, 4758 MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 4759 } 4760 4761 private final boolean killPackageProcessesLocked(String packageName, int appId, 4762 int userId, int minOomAdj, boolean callerWillRestart, boolean allowRestart, 4763 boolean doit, boolean evenPersistent, String reason) { 4764 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 4765 4766 // Remove all processes this package may have touched: all with the 4767 // same UID (except for the system or root user), and all whose name 4768 // matches the package name. 4769 final String procNamePrefix = packageName != null ? (packageName + ":") : null; 4770 final int NP = mProcessNames.getMap().size(); 4771 for (int ip=0; ip<NP; ip++) { 4772 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 4773 final int NA = apps.size(); 4774 for (int ia=0; ia<NA; ia++) { 4775 ProcessRecord app = apps.valueAt(ia); 4776 if (app.persistent && !evenPersistent) { 4777 // we don't kill persistent processes 4778 continue; 4779 } 4780 if (app.removed) { 4781 if (doit) { 4782 procs.add(app); 4783 } 4784 continue; 4785 } 4786 4787 // Skip process if it doesn't meet our oom adj requirement. 4788 if (app.setAdj < minOomAdj) { 4789 continue; 4790 } 4791 4792 // If no package is specified, we call all processes under the 4793 // give user id. 4794 if (packageName == null) { 4795 if (app.userId != userId) { 4796 continue; 4797 } 4798 if (appId >= 0 && UserHandle.getAppId(app.uid) != appId) { 4799 continue; 4800 } 4801 // Package has been specified, we want to hit all processes 4802 // that match it. We need to qualify this by the processes 4803 // that are running under the specified app and user ID. 4804 } else { 4805 if (UserHandle.getAppId(app.uid) != appId) { 4806 continue; 4807 } 4808 if (userId != UserHandle.USER_ALL && app.userId != userId) { 4809 continue; 4810 } 4811 if (!app.pkgList.containsKey(packageName)) { 4812 continue; 4813 } 4814 } 4815 4816 // Process has passed all conditions, kill it! 4817 if (!doit) { 4818 return true; 4819 } 4820 app.removed = true; 4821 procs.add(app); 4822 } 4823 } 4824 4825 int N = procs.size(); 4826 for (int i=0; i<N; i++) { 4827 removeProcessLocked(procs.get(i), callerWillRestart, allowRestart, reason); 4828 } 4829 updateOomAdjLocked(); 4830 return N > 0; 4831 } 4832 4833 private final boolean forceStopPackageLocked(String name, int appId, 4834 boolean callerWillRestart, boolean purgeCache, boolean doit, 4835 boolean evenPersistent, boolean uninstalling, int userId, String reason) { 4836 int i; 4837 int N; 4838 4839 if (userId == UserHandle.USER_ALL && name == null) { 4840 Slog.w(TAG, "Can't force stop all processes of all users, that is insane!"); 4841 } 4842 4843 if (appId < 0 && name != null) { 4844 try { 4845 appId = UserHandle.getAppId( 4846 AppGlobals.getPackageManager().getPackageUid(name, 0)); 4847 } catch (RemoteException e) { 4848 } 4849 } 4850 4851 if (doit) { 4852 if (name != null) { 4853 Slog.i(TAG, "Force stopping " + name + " appid=" + appId 4854 + " user=" + userId + ": " + reason); 4855 } else { 4856 Slog.i(TAG, "Force stopping u" + userId + ": " + reason); 4857 } 4858 4859 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 4860 for (int ip=pmap.size()-1; ip>=0; ip--) { 4861 SparseArray<Long> ba = pmap.valueAt(ip); 4862 for (i=ba.size()-1; i>=0; i--) { 4863 boolean remove = false; 4864 final int entUid = ba.keyAt(i); 4865 if (name != null) { 4866 if (userId == UserHandle.USER_ALL) { 4867 if (UserHandle.getAppId(entUid) == appId) { 4868 remove = true; 4869 } 4870 } else { 4871 if (entUid == UserHandle.getUid(userId, appId)) { 4872 remove = true; 4873 } 4874 } 4875 } else if (UserHandle.getUserId(entUid) == userId) { 4876 remove = true; 4877 } 4878 if (remove) { 4879 ba.removeAt(i); 4880 } 4881 } 4882 if (ba.size() == 0) { 4883 pmap.removeAt(ip); 4884 } 4885 } 4886 } 4887 4888 boolean didSomething = killPackageProcessesLocked(name, appId, userId, 4889 -100, callerWillRestart, true, doit, evenPersistent, 4890 name == null ? ("stop user " + userId) : ("stop " + name)); 4891 4892 if (mStackSupervisor.forceStopPackageLocked(name, doit, evenPersistent, userId)) { 4893 if (!doit) { 4894 return true; 4895 } 4896 didSomething = true; 4897 } 4898 4899 if (mServices.forceStopLocked(name, userId, evenPersistent, doit)) { 4900 if (!doit) { 4901 return true; 4902 } 4903 didSomething = true; 4904 } 4905 4906 if (name == null) { 4907 // Remove all sticky broadcasts from this user. 4908 mStickyBroadcasts.remove(userId); 4909 } 4910 4911 ArrayList<ContentProviderRecord> providers = new ArrayList<ContentProviderRecord>(); 4912 if (mProviderMap.collectForceStopProviders(name, appId, doit, evenPersistent, 4913 userId, providers)) { 4914 if (!doit) { 4915 return true; 4916 } 4917 didSomething = true; 4918 } 4919 N = providers.size(); 4920 for (i=0; i<N; i++) { 4921 removeDyingProviderLocked(null, providers.get(i), true); 4922 } 4923 4924 // Remove transient permissions granted from/to this package/user 4925 removeUriPermissionsForPackageLocked(name, userId, false); 4926 4927 if (name == null || uninstalling) { 4928 // Remove pending intents. For now we only do this when force 4929 // stopping users, because we have some problems when doing this 4930 // for packages -- app widgets are not currently cleaned up for 4931 // such packages, so they can be left with bad pending intents. 4932 if (mIntentSenderRecords.size() > 0) { 4933 Iterator<WeakReference<PendingIntentRecord>> it 4934 = mIntentSenderRecords.values().iterator(); 4935 while (it.hasNext()) { 4936 WeakReference<PendingIntentRecord> wpir = it.next(); 4937 if (wpir == null) { 4938 it.remove(); 4939 continue; 4940 } 4941 PendingIntentRecord pir = wpir.get(); 4942 if (pir == null) { 4943 it.remove(); 4944 continue; 4945 } 4946 if (name == null) { 4947 // Stopping user, remove all objects for the user. 4948 if (pir.key.userId != userId) { 4949 // Not the same user, skip it. 4950 continue; 4951 } 4952 } else { 4953 if (UserHandle.getAppId(pir.uid) != appId) { 4954 // Different app id, skip it. 4955 continue; 4956 } 4957 if (userId != UserHandle.USER_ALL && pir.key.userId != userId) { 4958 // Different user, skip it. 4959 continue; 4960 } 4961 if (!pir.key.packageName.equals(name)) { 4962 // Different package, skip it. 4963 continue; 4964 } 4965 } 4966 if (!doit) { 4967 return true; 4968 } 4969 didSomething = true; 4970 it.remove(); 4971 pir.canceled = true; 4972 if (pir.key.activity != null) { 4973 pir.key.activity.pendingResults.remove(pir.ref); 4974 } 4975 } 4976 } 4977 } 4978 4979 if (doit) { 4980 if (purgeCache && name != null) { 4981 AttributeCache ac = AttributeCache.instance(); 4982 if (ac != null) { 4983 ac.removePackage(name); 4984 } 4985 } 4986 if (mBooted) { 4987 mStackSupervisor.resumeTopActivitiesLocked(); 4988 mStackSupervisor.scheduleIdleLocked(); 4989 } 4990 } 4991 4992 return didSomething; 4993 } 4994 4995 private final boolean removeProcessLocked(ProcessRecord app, 4996 boolean callerWillRestart, boolean allowRestart, String reason) { 4997 final String name = app.processName; 4998 final int uid = app.uid; 4999 if (DEBUG_PROCESSES) Slog.d( 5000 TAG, "Force removing proc " + app.toShortString() + " (" + name 5001 + "/" + uid + ")"); 5002 5003 mProcessNames.remove(name, uid); 5004 mIsolatedProcesses.remove(app.uid); 5005 if (mHeavyWeightProcess == app) { 5006 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5007 mHeavyWeightProcess.userId, 0)); 5008 mHeavyWeightProcess = null; 5009 } 5010 boolean needRestart = false; 5011 if (app.pid > 0 && app.pid != MY_PID) { 5012 int pid = app.pid; 5013 synchronized (mPidsSelfLocked) { 5014 mPidsSelfLocked.remove(pid); 5015 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5016 } 5017 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_PROC_FINISH, 5018 app.processName, app.info.uid); 5019 if (app.isolated) { 5020 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5021 } 5022 killUnneededProcessLocked(app, reason); 5023 handleAppDiedLocked(app, true, allowRestart); 5024 removeLruProcessLocked(app); 5025 5026 if (app.persistent && !app.isolated) { 5027 if (!callerWillRestart) { 5028 addAppLocked(app.info, false, null /* ABI override */); 5029 } else { 5030 needRestart = true; 5031 } 5032 } 5033 } else { 5034 mRemovedProcesses.add(app); 5035 } 5036 5037 return needRestart; 5038 } 5039 5040 private final void processStartTimedOutLocked(ProcessRecord app) { 5041 final int pid = app.pid; 5042 boolean gone = false; 5043 synchronized (mPidsSelfLocked) { 5044 ProcessRecord knownApp = mPidsSelfLocked.get(pid); 5045 if (knownApp != null && knownApp.thread == null) { 5046 mPidsSelfLocked.remove(pid); 5047 gone = true; 5048 } 5049 } 5050 5051 if (gone) { 5052 Slog.w(TAG, "Process " + app + " failed to attach"); 5053 EventLog.writeEvent(EventLogTags.AM_PROCESS_START_TIMEOUT, app.userId, 5054 pid, app.uid, app.processName); 5055 mProcessNames.remove(app.processName, app.uid); 5056 mIsolatedProcesses.remove(app.uid); 5057 if (mHeavyWeightProcess == app) { 5058 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5059 mHeavyWeightProcess.userId, 0)); 5060 mHeavyWeightProcess = null; 5061 } 5062 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_PROC_FINISH, 5063 app.processName, app.info.uid); 5064 if (app.isolated) { 5065 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5066 } 5067 // Take care of any launching providers waiting for this process. 5068 checkAppInLaunchingProvidersLocked(app, true); 5069 // Take care of any services that are waiting for the process. 5070 mServices.processStartTimedOutLocked(app); 5071 killUnneededProcessLocked(app, "start timeout"); 5072 if (mBackupTarget != null && mBackupTarget.app.pid == pid) { 5073 Slog.w(TAG, "Unattached app died before backup, skipping"); 5074 try { 5075 IBackupManager bm = IBackupManager.Stub.asInterface( 5076 ServiceManager.getService(Context.BACKUP_SERVICE)); 5077 bm.agentDisconnected(app.info.packageName); 5078 } catch (RemoteException e) { 5079 // Can't happen; the backup manager is local 5080 } 5081 } 5082 if (isPendingBroadcastProcessLocked(pid)) { 5083 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 5084 skipPendingBroadcastLocked(pid); 5085 } 5086 } else { 5087 Slog.w(TAG, "Spurious process start timeout - pid not known for " + app); 5088 } 5089 } 5090 5091 private final boolean attachApplicationLocked(IApplicationThread thread, 5092 int pid) { 5093 5094 // Find the application record that is being attached... either via 5095 // the pid if we are running in multiple processes, or just pull the 5096 // next app record if we are emulating process with anonymous threads. 5097 ProcessRecord app; 5098 if (pid != MY_PID && pid >= 0) { 5099 synchronized (mPidsSelfLocked) { 5100 app = mPidsSelfLocked.get(pid); 5101 } 5102 } else { 5103 app = null; 5104 } 5105 5106 if (app == null) { 5107 Slog.w(TAG, "No pending application record for pid " + pid 5108 + " (IApplicationThread " + thread + "); dropping process"); 5109 EventLog.writeEvent(EventLogTags.AM_DROP_PROCESS, pid); 5110 if (pid > 0 && pid != MY_PID) { 5111 Process.killProcessQuiet(pid); 5112 } else { 5113 try { 5114 thread.scheduleExit(); 5115 } catch (Exception e) { 5116 // Ignore exceptions. 5117 } 5118 } 5119 return false; 5120 } 5121 5122 // If this application record is still attached to a previous 5123 // process, clean it up now. 5124 if (app.thread != null) { 5125 handleAppDiedLocked(app, true, true); 5126 } 5127 5128 // Tell the process all about itself. 5129 5130 if (localLOGV) Slog.v( 5131 TAG, "Binding process pid " + pid + " to record " + app); 5132 5133 final String processName = app.processName; 5134 try { 5135 AppDeathRecipient adr = new AppDeathRecipient( 5136 app, pid, thread); 5137 thread.asBinder().linkToDeath(adr, 0); 5138 app.deathRecipient = adr; 5139 } catch (RemoteException e) { 5140 app.resetPackageList(mProcessStats); 5141 startProcessLocked(app, "link fail", processName, null /* ABI override */); 5142 return false; 5143 } 5144 5145 EventLog.writeEvent(EventLogTags.AM_PROC_BOUND, app.userId, app.pid, app.processName); 5146 5147 app.makeActive(thread, mProcessStats); 5148 app.curAdj = app.setAdj = -100; 5149 app.curSchedGroup = app.setSchedGroup = Process.THREAD_GROUP_DEFAULT; 5150 app.forcingToForeground = null; 5151 updateProcessForegroundLocked(app, false, false); 5152 app.hasShownUi = false; 5153 app.debugging = false; 5154 app.cached = false; 5155 5156 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5157 5158 boolean normalMode = mProcessesReady || isAllowedWhileBooting(app.info); 5159 List<ProviderInfo> providers = normalMode ? generateApplicationProvidersLocked(app) : null; 5160 5161 if (!normalMode) { 5162 Slog.i(TAG, "Launching preboot mode app: " + app); 5163 } 5164 5165 if (localLOGV) Slog.v( 5166 TAG, "New app record " + app 5167 + " thread=" + thread.asBinder() + " pid=" + pid); 5168 try { 5169 int testMode = IApplicationThread.DEBUG_OFF; 5170 if (mDebugApp != null && mDebugApp.equals(processName)) { 5171 testMode = mWaitForDebugger 5172 ? IApplicationThread.DEBUG_WAIT 5173 : IApplicationThread.DEBUG_ON; 5174 app.debugging = true; 5175 if (mDebugTransient) { 5176 mDebugApp = mOrigDebugApp; 5177 mWaitForDebugger = mOrigWaitForDebugger; 5178 } 5179 } 5180 String profileFile = app.instrumentationProfileFile; 5181 ParcelFileDescriptor profileFd = null; 5182 boolean profileAutoStop = false; 5183 if (mProfileApp != null && mProfileApp.equals(processName)) { 5184 mProfileProc = app; 5185 profileFile = mProfileFile; 5186 profileFd = mProfileFd; 5187 profileAutoStop = mAutoStopProfiler; 5188 } 5189 boolean enableOpenGlTrace = false; 5190 if (mOpenGlTraceApp != null && mOpenGlTraceApp.equals(processName)) { 5191 enableOpenGlTrace = true; 5192 mOpenGlTraceApp = null; 5193 } 5194 5195 // If the app is being launched for restore or full backup, set it up specially 5196 boolean isRestrictedBackupMode = false; 5197 if (mBackupTarget != null && mBackupAppName.equals(processName)) { 5198 isRestrictedBackupMode = (mBackupTarget.backupMode == BackupRecord.RESTORE) 5199 || (mBackupTarget.backupMode == BackupRecord.RESTORE_FULL) 5200 || (mBackupTarget.backupMode == BackupRecord.BACKUP_FULL); 5201 } 5202 5203 ensurePackageDexOpt(app.instrumentationInfo != null 5204 ? app.instrumentationInfo.packageName 5205 : app.info.packageName); 5206 if (app.instrumentationClass != null) { 5207 ensurePackageDexOpt(app.instrumentationClass.getPackageName()); 5208 } 5209 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Binding proc " 5210 + processName + " with config " + mConfiguration); 5211 ApplicationInfo appInfo = app.instrumentationInfo != null 5212 ? app.instrumentationInfo : app.info; 5213 app.compat = compatibilityInfoForPackageLocked(appInfo); 5214 if (profileFd != null) { 5215 profileFd = profileFd.dup(); 5216 } 5217 thread.bindApplication(processName, appInfo, providers, 5218 app.instrumentationClass, profileFile, profileFd, profileAutoStop, 5219 app.instrumentationArguments, app.instrumentationWatcher, 5220 app.instrumentationUiAutomationConnection, testMode, enableOpenGlTrace, 5221 isRestrictedBackupMode || !normalMode, app.persistent, 5222 new Configuration(mConfiguration), app.compat, getCommonServicesLocked(), 5223 mCoreSettingsObserver.getCoreSettingsLocked()); 5224 updateLruProcessLocked(app, false, null); 5225 app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis(); 5226 } catch (Exception e) { 5227 // todo: Yikes! What should we do? For now we will try to 5228 // start another process, but that could easily get us in 5229 // an infinite loop of restarting processes... 5230 Slog.w(TAG, "Exception thrown during bind!", e); 5231 5232 app.resetPackageList(mProcessStats); 5233 app.unlinkDeathRecipient(); 5234 startProcessLocked(app, "bind fail", processName, null /* ABI override */); 5235 return false; 5236 } 5237 5238 // Remove this record from the list of starting applications. 5239 mPersistentStartingProcesses.remove(app); 5240 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 5241 "Attach application locked removing on hold: " + app); 5242 mProcessesOnHold.remove(app); 5243 5244 boolean badApp = false; 5245 boolean didSomething = false; 5246 5247 // See if the top visible activity is waiting to run in this process... 5248 if (normalMode) { 5249 try { 5250 if (mStackSupervisor.attachApplicationLocked(app)) { 5251 didSomething = true; 5252 } 5253 } catch (Exception e) { 5254 badApp = true; 5255 } 5256 } 5257 5258 // Find any services that should be running in this process... 5259 if (!badApp) { 5260 try { 5261 didSomething |= mServices.attachApplicationLocked(app, processName); 5262 } catch (Exception e) { 5263 badApp = true; 5264 } 5265 } 5266 5267 // Check if a next-broadcast receiver is in this process... 5268 if (!badApp && isPendingBroadcastProcessLocked(pid)) { 5269 try { 5270 didSomething |= sendPendingBroadcastsLocked(app); 5271 } catch (Exception e) { 5272 // If the app died trying to launch the receiver we declare it 'bad' 5273 badApp = true; 5274 } 5275 } 5276 5277 // Check whether the next backup agent is in this process... 5278 if (!badApp && mBackupTarget != null && mBackupTarget.appInfo.uid == app.uid) { 5279 if (DEBUG_BACKUP) Slog.v(TAG, "New app is backup target, launching agent for " + app); 5280 ensurePackageDexOpt(mBackupTarget.appInfo.packageName); 5281 try { 5282 thread.scheduleCreateBackupAgent(mBackupTarget.appInfo, 5283 compatibilityInfoForPackageLocked(mBackupTarget.appInfo), 5284 mBackupTarget.backupMode); 5285 } catch (Exception e) { 5286 Slog.w(TAG, "Exception scheduling backup agent creation: "); 5287 e.printStackTrace(); 5288 } 5289 } 5290 5291 if (badApp) { 5292 // todo: Also need to kill application to deal with all 5293 // kinds of exceptions. 5294 handleAppDiedLocked(app, false, true); 5295 return false; 5296 } 5297 5298 if (!didSomething) { 5299 updateOomAdjLocked(); 5300 } 5301 5302 return true; 5303 } 5304 5305 @Override 5306 public final void attachApplication(IApplicationThread thread) { 5307 synchronized (this) { 5308 int callingPid = Binder.getCallingPid(); 5309 final long origId = Binder.clearCallingIdentity(); 5310 attachApplicationLocked(thread, callingPid); 5311 Binder.restoreCallingIdentity(origId); 5312 } 5313 } 5314 5315 @Override 5316 public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) { 5317 final long origId = Binder.clearCallingIdentity(); 5318 synchronized (this) { 5319 ActivityStack stack = ActivityRecord.getStackLocked(token); 5320 if (stack != null) { 5321 ActivityRecord r = 5322 mStackSupervisor.activityIdleInternalLocked(token, false, config); 5323 if (stopProfiling) { 5324 if ((mProfileProc == r.app) && (mProfileFd != null)) { 5325 try { 5326 mProfileFd.close(); 5327 } catch (IOException e) { 5328 } 5329 clearProfilerLocked(); 5330 } 5331 } 5332 } 5333 } 5334 Binder.restoreCallingIdentity(origId); 5335 } 5336 5337 void enableScreenAfterBoot() { 5338 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN, 5339 SystemClock.uptimeMillis()); 5340 mWindowManager.enableScreenAfterBoot(); 5341 5342 synchronized (this) { 5343 updateEventDispatchingLocked(); 5344 } 5345 } 5346 5347 @Override 5348 public void showBootMessage(final CharSequence msg, final boolean always) { 5349 enforceNotIsolatedCaller("showBootMessage"); 5350 mWindowManager.showBootMessage(msg, always); 5351 } 5352 5353 @Override 5354 public void dismissKeyguardOnNextActivity() { 5355 enforceNotIsolatedCaller("dismissKeyguardOnNextActivity"); 5356 final long token = Binder.clearCallingIdentity(); 5357 try { 5358 synchronized (this) { 5359 if (DEBUG_LOCKSCREEN) logLockScreen(""); 5360 if (mLockScreenShown) { 5361 mLockScreenShown = false; 5362 comeOutOfSleepIfNeededLocked(); 5363 } 5364 mStackSupervisor.setDismissKeyguard(true); 5365 } 5366 } finally { 5367 Binder.restoreCallingIdentity(token); 5368 } 5369 } 5370 5371 final void finishBooting() { 5372 // Register receivers to handle package update events 5373 mPackageMonitor.register(mContext, Looper.getMainLooper(), false); 5374 5375 synchronized (this) { 5376 // Ensure that any processes we had put on hold are now started 5377 // up. 5378 final int NP = mProcessesOnHold.size(); 5379 if (NP > 0) { 5380 ArrayList<ProcessRecord> procs = 5381 new ArrayList<ProcessRecord>(mProcessesOnHold); 5382 for (int ip=0; ip<NP; ip++) { 5383 if (DEBUG_PROCESSES) Slog.v(TAG, "Starting process on hold: " 5384 + procs.get(ip)); 5385 startProcessLocked(procs.get(ip), "on-hold", null, null /* ABI override */); 5386 } 5387 } 5388 5389 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 5390 // Start looking for apps that are abusing wake locks. 5391 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 5392 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 5393 // Tell anyone interested that we are done booting! 5394 SystemProperties.set("sys.boot_completed", "1"); 5395 SystemProperties.set("dev.bootcomplete", "1"); 5396 for (int i=0; i<mStartedUsers.size(); i++) { 5397 UserStartedState uss = mStartedUsers.valueAt(i); 5398 if (uss.mState == UserStartedState.STATE_BOOTING) { 5399 uss.mState = UserStartedState.STATE_RUNNING; 5400 final int userId = mStartedUsers.keyAt(i); 5401 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 5402 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 5403 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 5404 broadcastIntentLocked(null, null, intent, null, 5405 new IIntentReceiver.Stub() { 5406 @Override 5407 public void performReceive(Intent intent, int resultCode, 5408 String data, Bundle extras, boolean ordered, 5409 boolean sticky, int sendingUser) { 5410 synchronized (ActivityManagerService.this) { 5411 requestPssAllProcsLocked(SystemClock.uptimeMillis(), 5412 true, false); 5413 } 5414 } 5415 }, 5416 0, null, null, 5417 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, 5418 AppOpsManager.OP_NONE, true, false, MY_PID, Process.SYSTEM_UID, 5419 userId); 5420 } 5421 } 5422 scheduleStartProfilesLocked(); 5423 } 5424 } 5425 } 5426 5427 final void ensureBootCompleted() { 5428 boolean booting; 5429 boolean enableScreen; 5430 synchronized (this) { 5431 booting = mBooting; 5432 mBooting = false; 5433 enableScreen = !mBooted; 5434 mBooted = true; 5435 } 5436 5437 if (booting) { 5438 finishBooting(); 5439 } 5440 5441 if (enableScreen) { 5442 enableScreenAfterBoot(); 5443 } 5444 } 5445 5446 @Override 5447 public final void activityResumed(IBinder token) { 5448 final long origId = Binder.clearCallingIdentity(); 5449 synchronized(this) { 5450 ActivityStack stack = ActivityRecord.getStackLocked(token); 5451 if (stack != null) { 5452 ActivityRecord.activityResumedLocked(token); 5453 } 5454 } 5455 Binder.restoreCallingIdentity(origId); 5456 } 5457 5458 @Override 5459 public final void activityPaused(IBinder token, PersistableBundle persistentState) { 5460 final long origId = Binder.clearCallingIdentity(); 5461 synchronized(this) { 5462 ActivityStack stack = ActivityRecord.getStackLocked(token); 5463 if (stack != null) { 5464 stack.activityPausedLocked(token, false, persistentState); 5465 } 5466 } 5467 Binder.restoreCallingIdentity(origId); 5468 } 5469 5470 @Override 5471 public final void activityStopped(IBinder token, Bundle icicle, 5472 PersistableBundle persistentState, CharSequence description) { 5473 if (localLOGV) Slog.v(TAG, "Activity stopped: token=" + token); 5474 5475 // Refuse possible leaked file descriptors 5476 if (icicle != null && icicle.hasFileDescriptors()) { 5477 throw new IllegalArgumentException("File descriptors passed in Bundle"); 5478 } 5479 5480 final long origId = Binder.clearCallingIdentity(); 5481 5482 synchronized (this) { 5483 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5484 if (r != null) { 5485 r.task.stack.activityStoppedLocked(r, icicle, persistentState, description); 5486 } 5487 } 5488 5489 trimApplications(); 5490 5491 Binder.restoreCallingIdentity(origId); 5492 } 5493 5494 @Override 5495 public final void activityDestroyed(IBinder token) { 5496 if (DEBUG_SWITCH) Slog.v(TAG, "ACTIVITY DESTROYED: " + token); 5497 synchronized (this) { 5498 ActivityStack stack = ActivityRecord.getStackLocked(token); 5499 if (stack != null) { 5500 stack.activityDestroyedLocked(token); 5501 } 5502 } 5503 } 5504 5505 @Override 5506 public String getCallingPackage(IBinder token) { 5507 synchronized (this) { 5508 ActivityRecord r = getCallingRecordLocked(token); 5509 return r != null ? r.info.packageName : null; 5510 } 5511 } 5512 5513 @Override 5514 public ComponentName getCallingActivity(IBinder token) { 5515 synchronized (this) { 5516 ActivityRecord r = getCallingRecordLocked(token); 5517 return r != null ? r.intent.getComponent() : null; 5518 } 5519 } 5520 5521 private ActivityRecord getCallingRecordLocked(IBinder token) { 5522 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5523 if (r == null) { 5524 return null; 5525 } 5526 return r.resultTo; 5527 } 5528 5529 @Override 5530 public ComponentName getActivityClassForToken(IBinder token) { 5531 synchronized(this) { 5532 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5533 if (r == null) { 5534 return null; 5535 } 5536 return r.intent.getComponent(); 5537 } 5538 } 5539 5540 @Override 5541 public String getPackageForToken(IBinder token) { 5542 synchronized(this) { 5543 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5544 if (r == null) { 5545 return null; 5546 } 5547 return r.packageName; 5548 } 5549 } 5550 5551 @Override 5552 public IIntentSender getIntentSender(int type, 5553 String packageName, IBinder token, String resultWho, 5554 int requestCode, Intent[] intents, String[] resolvedTypes, 5555 int flags, Bundle options, int userId) { 5556 enforceNotIsolatedCaller("getIntentSender"); 5557 // Refuse possible leaked file descriptors 5558 if (intents != null) { 5559 if (intents.length < 1) { 5560 throw new IllegalArgumentException("Intents array length must be >= 1"); 5561 } 5562 for (int i=0; i<intents.length; i++) { 5563 Intent intent = intents[i]; 5564 if (intent != null) { 5565 if (intent.hasFileDescriptors()) { 5566 throw new IllegalArgumentException("File descriptors passed in Intent"); 5567 } 5568 if (type == ActivityManager.INTENT_SENDER_BROADCAST && 5569 (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 5570 throw new IllegalArgumentException( 5571 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 5572 } 5573 intents[i] = new Intent(intent); 5574 } 5575 } 5576 if (resolvedTypes != null && resolvedTypes.length != intents.length) { 5577 throw new IllegalArgumentException( 5578 "Intent array length does not match resolvedTypes length"); 5579 } 5580 } 5581 if (options != null) { 5582 if (options.hasFileDescriptors()) { 5583 throw new IllegalArgumentException("File descriptors passed in options"); 5584 } 5585 } 5586 5587 synchronized(this) { 5588 int callingUid = Binder.getCallingUid(); 5589 int origUserId = userId; 5590 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 5591 type == ActivityManager.INTENT_SENDER_BROADCAST, false, 5592 "getIntentSender", null); 5593 if (origUserId == UserHandle.USER_CURRENT) { 5594 // We don't want to evaluate this until the pending intent is 5595 // actually executed. However, we do want to always do the 5596 // security checking for it above. 5597 userId = UserHandle.USER_CURRENT; 5598 } 5599 try { 5600 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 5601 int uid = AppGlobals.getPackageManager() 5602 .getPackageUid(packageName, UserHandle.getUserId(callingUid)); 5603 if (!UserHandle.isSameApp(callingUid, uid)) { 5604 String msg = "Permission Denial: getIntentSender() from pid=" 5605 + Binder.getCallingPid() 5606 + ", uid=" + Binder.getCallingUid() 5607 + ", (need uid=" + uid + ")" 5608 + " is not allowed to send as package " + packageName; 5609 Slog.w(TAG, msg); 5610 throw new SecurityException(msg); 5611 } 5612 } 5613 5614 return getIntentSenderLocked(type, packageName, callingUid, userId, 5615 token, resultWho, requestCode, intents, resolvedTypes, flags, options); 5616 5617 } catch (RemoteException e) { 5618 throw new SecurityException(e); 5619 } 5620 } 5621 } 5622 5623 IIntentSender getIntentSenderLocked(int type, String packageName, 5624 int callingUid, int userId, IBinder token, String resultWho, 5625 int requestCode, Intent[] intents, String[] resolvedTypes, int flags, 5626 Bundle options) { 5627 if (DEBUG_MU) 5628 Slog.v(TAG_MU, "getIntentSenderLocked(): uid=" + callingUid); 5629 ActivityRecord activity = null; 5630 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 5631 activity = ActivityRecord.isInStackLocked(token); 5632 if (activity == null) { 5633 return null; 5634 } 5635 if (activity.finishing) { 5636 return null; 5637 } 5638 } 5639 5640 final boolean noCreate = (flags&PendingIntent.FLAG_NO_CREATE) != 0; 5641 final boolean cancelCurrent = (flags&PendingIntent.FLAG_CANCEL_CURRENT) != 0; 5642 final boolean updateCurrent = (flags&PendingIntent.FLAG_UPDATE_CURRENT) != 0; 5643 flags &= ~(PendingIntent.FLAG_NO_CREATE|PendingIntent.FLAG_CANCEL_CURRENT 5644 |PendingIntent.FLAG_UPDATE_CURRENT); 5645 5646 PendingIntentRecord.Key key = new PendingIntentRecord.Key( 5647 type, packageName, activity, resultWho, 5648 requestCode, intents, resolvedTypes, flags, options, userId); 5649 WeakReference<PendingIntentRecord> ref; 5650 ref = mIntentSenderRecords.get(key); 5651 PendingIntentRecord rec = ref != null ? ref.get() : null; 5652 if (rec != null) { 5653 if (!cancelCurrent) { 5654 if (updateCurrent) { 5655 if (rec.key.requestIntent != null) { 5656 rec.key.requestIntent.replaceExtras(intents != null ? 5657 intents[intents.length - 1] : null); 5658 } 5659 if (intents != null) { 5660 intents[intents.length-1] = rec.key.requestIntent; 5661 rec.key.allIntents = intents; 5662 rec.key.allResolvedTypes = resolvedTypes; 5663 } else { 5664 rec.key.allIntents = null; 5665 rec.key.allResolvedTypes = null; 5666 } 5667 } 5668 return rec; 5669 } 5670 rec.canceled = true; 5671 mIntentSenderRecords.remove(key); 5672 } 5673 if (noCreate) { 5674 return rec; 5675 } 5676 rec = new PendingIntentRecord(this, key, callingUid); 5677 mIntentSenderRecords.put(key, rec.ref); 5678 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 5679 if (activity.pendingResults == null) { 5680 activity.pendingResults 5681 = new HashSet<WeakReference<PendingIntentRecord>>(); 5682 } 5683 activity.pendingResults.add(rec.ref); 5684 } 5685 return rec; 5686 } 5687 5688 @Override 5689 public void cancelIntentSender(IIntentSender sender) { 5690 if (!(sender instanceof PendingIntentRecord)) { 5691 return; 5692 } 5693 synchronized(this) { 5694 PendingIntentRecord rec = (PendingIntentRecord)sender; 5695 try { 5696 int uid = AppGlobals.getPackageManager() 5697 .getPackageUid(rec.key.packageName, UserHandle.getCallingUserId()); 5698 if (!UserHandle.isSameApp(uid, Binder.getCallingUid())) { 5699 String msg = "Permission Denial: cancelIntentSender() from pid=" 5700 + Binder.getCallingPid() 5701 + ", uid=" + Binder.getCallingUid() 5702 + " is not allowed to cancel packges " 5703 + rec.key.packageName; 5704 Slog.w(TAG, msg); 5705 throw new SecurityException(msg); 5706 } 5707 } catch (RemoteException e) { 5708 throw new SecurityException(e); 5709 } 5710 cancelIntentSenderLocked(rec, true); 5711 } 5712 } 5713 5714 void cancelIntentSenderLocked(PendingIntentRecord rec, boolean cleanActivity) { 5715 rec.canceled = true; 5716 mIntentSenderRecords.remove(rec.key); 5717 if (cleanActivity && rec.key.activity != null) { 5718 rec.key.activity.pendingResults.remove(rec.ref); 5719 } 5720 } 5721 5722 @Override 5723 public String getPackageForIntentSender(IIntentSender pendingResult) { 5724 if (!(pendingResult instanceof PendingIntentRecord)) { 5725 return null; 5726 } 5727 try { 5728 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5729 return res.key.packageName; 5730 } catch (ClassCastException e) { 5731 } 5732 return null; 5733 } 5734 5735 @Override 5736 public int getUidForIntentSender(IIntentSender sender) { 5737 if (sender instanceof PendingIntentRecord) { 5738 try { 5739 PendingIntentRecord res = (PendingIntentRecord)sender; 5740 return res.uid; 5741 } catch (ClassCastException e) { 5742 } 5743 } 5744 return -1; 5745 } 5746 5747 @Override 5748 public boolean isIntentSenderTargetedToPackage(IIntentSender pendingResult) { 5749 if (!(pendingResult instanceof PendingIntentRecord)) { 5750 return false; 5751 } 5752 try { 5753 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5754 if (res.key.allIntents == null) { 5755 return false; 5756 } 5757 for (int i=0; i<res.key.allIntents.length; i++) { 5758 Intent intent = res.key.allIntents[i]; 5759 if (intent.getPackage() != null && intent.getComponent() != null) { 5760 return false; 5761 } 5762 } 5763 return true; 5764 } catch (ClassCastException e) { 5765 } 5766 return false; 5767 } 5768 5769 @Override 5770 public boolean isIntentSenderAnActivity(IIntentSender pendingResult) { 5771 if (!(pendingResult instanceof PendingIntentRecord)) { 5772 return false; 5773 } 5774 try { 5775 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5776 if (res.key.type == ActivityManager.INTENT_SENDER_ACTIVITY) { 5777 return true; 5778 } 5779 return false; 5780 } catch (ClassCastException e) { 5781 } 5782 return false; 5783 } 5784 5785 @Override 5786 public Intent getIntentForIntentSender(IIntentSender pendingResult) { 5787 if (!(pendingResult instanceof PendingIntentRecord)) { 5788 return null; 5789 } 5790 try { 5791 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5792 return res.key.requestIntent != null ? new Intent(res.key.requestIntent) : null; 5793 } catch (ClassCastException e) { 5794 } 5795 return null; 5796 } 5797 5798 @Override 5799 public String getTagForIntentSender(IIntentSender pendingResult, String prefix) { 5800 if (!(pendingResult instanceof PendingIntentRecord)) { 5801 return null; 5802 } 5803 try { 5804 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5805 Intent intent = res.key.requestIntent; 5806 if (intent != null) { 5807 if (res.lastTag != null && res.lastTagPrefix == prefix && (res.lastTagPrefix == null 5808 || res.lastTagPrefix.equals(prefix))) { 5809 return res.lastTag; 5810 } 5811 res.lastTagPrefix = prefix; 5812 StringBuilder sb = new StringBuilder(128); 5813 if (prefix != null) { 5814 sb.append(prefix); 5815 } 5816 if (intent.getAction() != null) { 5817 sb.append(intent.getAction()); 5818 } else if (intent.getComponent() != null) { 5819 intent.getComponent().appendShortString(sb); 5820 } else { 5821 sb.append("?"); 5822 } 5823 return res.lastTag = sb.toString(); 5824 } 5825 } catch (ClassCastException e) { 5826 } 5827 return null; 5828 } 5829 5830 @Override 5831 public void setProcessLimit(int max) { 5832 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 5833 "setProcessLimit()"); 5834 synchronized (this) { 5835 mProcessLimit = max < 0 ? ProcessList.MAX_CACHED_APPS : max; 5836 mProcessLimitOverride = max; 5837 } 5838 trimApplications(); 5839 } 5840 5841 @Override 5842 public int getProcessLimit() { 5843 synchronized (this) { 5844 return mProcessLimitOverride; 5845 } 5846 } 5847 5848 void foregroundTokenDied(ForegroundToken token) { 5849 synchronized (ActivityManagerService.this) { 5850 synchronized (mPidsSelfLocked) { 5851 ForegroundToken cur 5852 = mForegroundProcesses.get(token.pid); 5853 if (cur != token) { 5854 return; 5855 } 5856 mForegroundProcesses.remove(token.pid); 5857 ProcessRecord pr = mPidsSelfLocked.get(token.pid); 5858 if (pr == null) { 5859 return; 5860 } 5861 pr.forcingToForeground = null; 5862 updateProcessForegroundLocked(pr, false, false); 5863 } 5864 updateOomAdjLocked(); 5865 } 5866 } 5867 5868 @Override 5869 public void setProcessForeground(IBinder token, int pid, boolean isForeground) { 5870 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 5871 "setProcessForeground()"); 5872 synchronized(this) { 5873 boolean changed = false; 5874 5875 synchronized (mPidsSelfLocked) { 5876 ProcessRecord pr = mPidsSelfLocked.get(pid); 5877 if (pr == null && isForeground) { 5878 Slog.w(TAG, "setProcessForeground called on unknown pid: " + pid); 5879 return; 5880 } 5881 ForegroundToken oldToken = mForegroundProcesses.get(pid); 5882 if (oldToken != null) { 5883 oldToken.token.unlinkToDeath(oldToken, 0); 5884 mForegroundProcesses.remove(pid); 5885 if (pr != null) { 5886 pr.forcingToForeground = null; 5887 } 5888 changed = true; 5889 } 5890 if (isForeground && token != null) { 5891 ForegroundToken newToken = new ForegroundToken() { 5892 @Override 5893 public void binderDied() { 5894 foregroundTokenDied(this); 5895 } 5896 }; 5897 newToken.pid = pid; 5898 newToken.token = token; 5899 try { 5900 token.linkToDeath(newToken, 0); 5901 mForegroundProcesses.put(pid, newToken); 5902 pr.forcingToForeground = token; 5903 changed = true; 5904 } catch (RemoteException e) { 5905 // If the process died while doing this, we will later 5906 // do the cleanup with the process death link. 5907 } 5908 } 5909 } 5910 5911 if (changed) { 5912 updateOomAdjLocked(); 5913 } 5914 } 5915 } 5916 5917 // ========================================================= 5918 // PERMISSIONS 5919 // ========================================================= 5920 5921 static class PermissionController extends IPermissionController.Stub { 5922 ActivityManagerService mActivityManagerService; 5923 PermissionController(ActivityManagerService activityManagerService) { 5924 mActivityManagerService = activityManagerService; 5925 } 5926 5927 @Override 5928 public boolean checkPermission(String permission, int pid, int uid) { 5929 return mActivityManagerService.checkPermission(permission, pid, 5930 uid) == PackageManager.PERMISSION_GRANTED; 5931 } 5932 } 5933 5934 class IntentFirewallInterface implements IntentFirewall.AMSInterface { 5935 @Override 5936 public int checkComponentPermission(String permission, int pid, int uid, 5937 int owningUid, boolean exported) { 5938 return ActivityManagerService.this.checkComponentPermission(permission, pid, uid, 5939 owningUid, exported); 5940 } 5941 5942 @Override 5943 public Object getAMSLock() { 5944 return ActivityManagerService.this; 5945 } 5946 } 5947 5948 /** 5949 * This can be called with or without the global lock held. 5950 */ 5951 int checkComponentPermission(String permission, int pid, int uid, 5952 int owningUid, boolean exported) { 5953 // We might be performing an operation on behalf of an indirect binder 5954 // invocation, e.g. via {@link #openContentUri}. Check and adjust the 5955 // client identity accordingly before proceeding. 5956 Identity tlsIdentity = sCallerIdentity.get(); 5957 if (tlsIdentity != null) { 5958 Slog.d(TAG, "checkComponentPermission() adjusting {pid,uid} to {" 5959 + tlsIdentity.pid + "," + tlsIdentity.uid + "}"); 5960 uid = tlsIdentity.uid; 5961 pid = tlsIdentity.pid; 5962 } 5963 5964 if (pid == MY_PID) { 5965 return PackageManager.PERMISSION_GRANTED; 5966 } 5967 5968 return ActivityManager.checkComponentPermission(permission, uid, 5969 owningUid, exported); 5970 } 5971 5972 /** 5973 * As the only public entry point for permissions checking, this method 5974 * can enforce the semantic that requesting a check on a null global 5975 * permission is automatically denied. (Internally a null permission 5976 * string is used when calling {@link #checkComponentPermission} in cases 5977 * when only uid-based security is needed.) 5978 * 5979 * This can be called with or without the global lock held. 5980 */ 5981 @Override 5982 public int checkPermission(String permission, int pid, int uid) { 5983 if (permission == null) { 5984 return PackageManager.PERMISSION_DENIED; 5985 } 5986 return checkComponentPermission(permission, pid, UserHandle.getAppId(uid), -1, true); 5987 } 5988 5989 /** 5990 * Binder IPC calls go through the public entry point. 5991 * This can be called with or without the global lock held. 5992 */ 5993 int checkCallingPermission(String permission) { 5994 return checkPermission(permission, 5995 Binder.getCallingPid(), 5996 UserHandle.getAppId(Binder.getCallingUid())); 5997 } 5998 5999 /** 6000 * This can be called with or without the global lock held. 6001 */ 6002 void enforceCallingPermission(String permission, String func) { 6003 if (checkCallingPermission(permission) 6004 == PackageManager.PERMISSION_GRANTED) { 6005 return; 6006 } 6007 6008 String msg = "Permission Denial: " + func + " from pid=" 6009 + Binder.getCallingPid() 6010 + ", uid=" + Binder.getCallingUid() 6011 + " requires " + permission; 6012 Slog.w(TAG, msg); 6013 throw new SecurityException(msg); 6014 } 6015 6016 /** 6017 * Determine if UID is holding permissions required to access {@link Uri} in 6018 * the given {@link ProviderInfo}. Final permission checking is always done 6019 * in {@link ContentProvider}. 6020 */ 6021 private final boolean checkHoldingPermissionsLocked( 6022 IPackageManager pm, ProviderInfo pi, GrantUri grantUri, int uid, final int modeFlags) { 6023 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6024 "checkHoldingPermissionsLocked: uri=" + grantUri + " uid=" + uid); 6025 if (UserHandle.getUserId(uid) != grantUri.sourceUserId) { 6026 return false; 6027 } 6028 6029 if (pi.applicationInfo.uid == uid) { 6030 return true; 6031 } else if (!pi.exported) { 6032 return false; 6033 } 6034 6035 boolean readMet = (modeFlags & Intent.FLAG_GRANT_READ_URI_PERMISSION) == 0; 6036 boolean writeMet = (modeFlags & Intent.FLAG_GRANT_WRITE_URI_PERMISSION) == 0; 6037 try { 6038 // check if target holds top-level <provider> permissions 6039 if (!readMet && pi.readPermission != null 6040 && (pm.checkUidPermission(pi.readPermission, uid) == PERMISSION_GRANTED)) { 6041 readMet = true; 6042 } 6043 if (!writeMet && pi.writePermission != null 6044 && (pm.checkUidPermission(pi.writePermission, uid) == PERMISSION_GRANTED)) { 6045 writeMet = true; 6046 } 6047 6048 // track if unprotected read/write is allowed; any denied 6049 // <path-permission> below removes this ability 6050 boolean allowDefaultRead = pi.readPermission == null; 6051 boolean allowDefaultWrite = pi.writePermission == null; 6052 6053 // check if target holds any <path-permission> that match uri 6054 final PathPermission[] pps = pi.pathPermissions; 6055 if (pps != null) { 6056 final String path = grantUri.uri.getPath(); 6057 int i = pps.length; 6058 while (i > 0 && (!readMet || !writeMet)) { 6059 i--; 6060 PathPermission pp = pps[i]; 6061 if (pp.match(path)) { 6062 if (!readMet) { 6063 final String pprperm = pp.getReadPermission(); 6064 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking read perm for " 6065 + pprperm + " for " + pp.getPath() 6066 + ": match=" + pp.match(path) 6067 + " check=" + pm.checkUidPermission(pprperm, uid)); 6068 if (pprperm != null) { 6069 if (pm.checkUidPermission(pprperm, uid) == PERMISSION_GRANTED) { 6070 readMet = true; 6071 } else { 6072 allowDefaultRead = false; 6073 } 6074 } 6075 } 6076 if (!writeMet) { 6077 final String ppwperm = pp.getWritePermission(); 6078 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking write perm " 6079 + ppwperm + " for " + pp.getPath() 6080 + ": match=" + pp.match(path) 6081 + " check=" + pm.checkUidPermission(ppwperm, uid)); 6082 if (ppwperm != null) { 6083 if (pm.checkUidPermission(ppwperm, uid) == PERMISSION_GRANTED) { 6084 writeMet = true; 6085 } else { 6086 allowDefaultWrite = false; 6087 } 6088 } 6089 } 6090 } 6091 } 6092 } 6093 6094 // grant unprotected <provider> read/write, if not blocked by 6095 // <path-permission> above 6096 if (allowDefaultRead) readMet = true; 6097 if (allowDefaultWrite) writeMet = true; 6098 6099 } catch (RemoteException e) { 6100 return false; 6101 } 6102 6103 return readMet && writeMet; 6104 } 6105 6106 private ProviderInfo getProviderInfoLocked(String authority, int userHandle) { 6107 ProviderInfo pi = null; 6108 ContentProviderRecord cpr = mProviderMap.getProviderByName(authority, userHandle); 6109 if (cpr != null) { 6110 pi = cpr.info; 6111 } else { 6112 try { 6113 pi = AppGlobals.getPackageManager().resolveContentProvider( 6114 authority, PackageManager.GET_URI_PERMISSION_PATTERNS, userHandle); 6115 } catch (RemoteException ex) { 6116 } 6117 } 6118 return pi; 6119 } 6120 6121 private UriPermission findUriPermissionLocked(int targetUid, GrantUri grantUri) { 6122 final ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6123 if (targetUris != null) { 6124 return targetUris.get(grantUri); 6125 } 6126 return null; 6127 } 6128 6129 private UriPermission findOrCreateUriPermissionLocked(String sourcePkg, 6130 String targetPkg, int targetUid, GrantUri grantUri) { 6131 ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6132 if (targetUris == null) { 6133 targetUris = Maps.newArrayMap(); 6134 mGrantedUriPermissions.put(targetUid, targetUris); 6135 } 6136 6137 UriPermission perm = targetUris.get(grantUri); 6138 if (perm == null) { 6139 perm = new UriPermission(sourcePkg, targetPkg, targetUid, grantUri); 6140 targetUris.put(grantUri, perm); 6141 } 6142 6143 return perm; 6144 } 6145 6146 private final boolean checkUriPermissionLocked(GrantUri grantUri, int uid, 6147 final int modeFlags) { 6148 final boolean persistable = (modeFlags & Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION) != 0; 6149 final int minStrength = persistable ? UriPermission.STRENGTH_PERSISTABLE 6150 : UriPermission.STRENGTH_OWNED; 6151 6152 // Root gets to do everything. 6153 if (uid == 0) { 6154 return true; 6155 } 6156 6157 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 6158 if (perms == null) return false; 6159 6160 // First look for exact match 6161 final UriPermission exactPerm = perms.get(grantUri); 6162 if (exactPerm != null && exactPerm.getStrength(modeFlags) >= minStrength) { 6163 return true; 6164 } 6165 6166 // No exact match, look for prefixes 6167 final int N = perms.size(); 6168 for (int i = 0; i < N; i++) { 6169 final UriPermission perm = perms.valueAt(i); 6170 if (perm.uri.prefix && grantUri.uri.isPathPrefixMatch(perm.uri.uri) 6171 && perm.getStrength(modeFlags) >= minStrength) { 6172 return true; 6173 } 6174 } 6175 6176 return false; 6177 } 6178 6179 @Override 6180 public int checkUriPermission(Uri uri, int pid, int uid, 6181 final int modeFlags, int userId) { 6182 enforceNotIsolatedCaller("checkUriPermission"); 6183 6184 // Another redirected-binder-call permissions check as in 6185 // {@link checkComponentPermission}. 6186 Identity tlsIdentity = sCallerIdentity.get(); 6187 if (tlsIdentity != null) { 6188 uid = tlsIdentity.uid; 6189 pid = tlsIdentity.pid; 6190 } 6191 6192 // Our own process gets to do everything. 6193 if (pid == MY_PID) { 6194 return PackageManager.PERMISSION_GRANTED; 6195 } 6196 synchronized (this) { 6197 return checkUriPermissionLocked(new GrantUri(userId, uri, false), uid, modeFlags) 6198 ? PackageManager.PERMISSION_GRANTED 6199 : PackageManager.PERMISSION_DENIED; 6200 } 6201 } 6202 6203 /** 6204 * Check if the targetPkg can be granted permission to access uri by 6205 * the callingUid using the given modeFlags. Throws a security exception 6206 * if callingUid is not allowed to do this. Returns the uid of the target 6207 * if the URI permission grant should be performed; returns -1 if it is not 6208 * needed (for example targetPkg already has permission to access the URI). 6209 * If you already know the uid of the target, you can supply it in 6210 * lastTargetUid else set that to -1. 6211 */ 6212 int checkGrantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 6213 final int modeFlags, int lastTargetUid) { 6214 if (!Intent.isAccessUriMode(modeFlags)) { 6215 return -1; 6216 } 6217 6218 if (targetPkg != null) { 6219 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6220 "Checking grant " + targetPkg + " permission to " + grantUri); 6221 } 6222 6223 final IPackageManager pm = AppGlobals.getPackageManager(); 6224 6225 // If this is not a content: uri, we can't do anything with it. 6226 if (!ContentResolver.SCHEME_CONTENT.equals(grantUri.uri.getScheme())) { 6227 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6228 "Can't grant URI permission for non-content URI: " + grantUri); 6229 return -1; 6230 } 6231 6232 final String authority = grantUri.uri.getAuthority(); 6233 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6234 if (pi == null) { 6235 Slog.w(TAG, "No content provider found for permission check: " + 6236 grantUri.uri.toSafeString()); 6237 return -1; 6238 } 6239 6240 int targetUid = lastTargetUid; 6241 if (targetUid < 0 && targetPkg != null) { 6242 try { 6243 targetUid = pm.getPackageUid(targetPkg, UserHandle.getUserId(callingUid)); 6244 if (targetUid < 0) { 6245 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6246 "Can't grant URI permission no uid for: " + targetPkg); 6247 return -1; 6248 } 6249 } catch (RemoteException ex) { 6250 return -1; 6251 } 6252 } 6253 6254 if (targetUid >= 0) { 6255 // First... does the target actually need this permission? 6256 if (checkHoldingPermissionsLocked(pm, pi, grantUri, targetUid, modeFlags)) { 6257 // No need to grant the target this permission. 6258 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6259 "Target " + targetPkg + " already has full permission to " + grantUri); 6260 return -1; 6261 } 6262 } else { 6263 // First... there is no target package, so can anyone access it? 6264 boolean allowed = pi.exported; 6265 if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) { 6266 if (pi.readPermission != null) { 6267 allowed = false; 6268 } 6269 } 6270 if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) { 6271 if (pi.writePermission != null) { 6272 allowed = false; 6273 } 6274 } 6275 if (allowed) { 6276 return -1; 6277 } 6278 } 6279 6280 // Second... is the provider allowing granting of URI permissions? 6281 if (!pi.grantUriPermissions) { 6282 throw new SecurityException("Provider " + pi.packageName 6283 + "/" + pi.name 6284 + " does not allow granting of Uri permissions (uri " 6285 + grantUri + ")"); 6286 } 6287 if (pi.uriPermissionPatterns != null) { 6288 final int N = pi.uriPermissionPatterns.length; 6289 boolean allowed = false; 6290 for (int i=0; i<N; i++) { 6291 if (pi.uriPermissionPatterns[i] != null 6292 && pi.uriPermissionPatterns[i].match(grantUri.uri.getPath())) { 6293 allowed = true; 6294 break; 6295 } 6296 } 6297 if (!allowed) { 6298 throw new SecurityException("Provider " + pi.packageName 6299 + "/" + pi.name 6300 + " does not allow granting of permission to path of Uri " 6301 + grantUri); 6302 } 6303 } 6304 6305 // Third... does the caller itself have permission to access 6306 // this uri? 6307 if (UserHandle.getAppId(callingUid) != Process.SYSTEM_UID) { 6308 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 6309 // Require they hold a strong enough Uri permission 6310 if (!checkUriPermissionLocked(grantUri, callingUid, modeFlags)) { 6311 throw new SecurityException("Uid " + callingUid 6312 + " does not have permission to uri " + grantUri); 6313 } 6314 } 6315 } 6316 return targetUid; 6317 } 6318 6319 @Override 6320 public int checkGrantUriPermission(int callingUid, String targetPkg, Uri uri, 6321 final int modeFlags, int userId) { 6322 enforceNotIsolatedCaller("checkGrantUriPermission"); 6323 synchronized(this) { 6324 return checkGrantUriPermissionLocked(callingUid, targetPkg, 6325 new GrantUri(userId, uri, false), modeFlags, -1); 6326 } 6327 } 6328 6329 void grantUriPermissionUncheckedLocked(int targetUid, String targetPkg, GrantUri grantUri, 6330 final int modeFlags, UriPermissionOwner owner) { 6331 if (!Intent.isAccessUriMode(modeFlags)) { 6332 return; 6333 } 6334 6335 // So here we are: the caller has the assumed permission 6336 // to the uri, and the target doesn't. Let's now give this to 6337 // the target. 6338 6339 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6340 "Granting " + targetPkg + "/" + targetUid + " permission to " + grantUri); 6341 6342 final String authority = grantUri.uri.getAuthority(); 6343 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6344 if (pi == null) { 6345 Slog.w(TAG, "No content provider found for grant: " + grantUri.toSafeString()); 6346 return; 6347 } 6348 6349 if ((modeFlags & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0) { 6350 grantUri.prefix = true; 6351 } 6352 final UriPermission perm = findOrCreateUriPermissionLocked( 6353 pi.packageName, targetPkg, targetUid, grantUri); 6354 perm.grantModes(modeFlags, owner); 6355 } 6356 6357 void grantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 6358 final int modeFlags, UriPermissionOwner owner) { 6359 if (targetPkg == null) { 6360 throw new NullPointerException("targetPkg"); 6361 } 6362 6363 int targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, modeFlags, 6364 -1); 6365 if (targetUid < 0) { 6366 return; 6367 } 6368 6369 grantUriPermissionUncheckedLocked(targetUid, targetPkg, grantUri, modeFlags, 6370 owner); 6371 } 6372 6373 static class NeededUriGrants extends ArrayList<GrantUri> { 6374 final String targetPkg; 6375 final int targetUid; 6376 final int flags; 6377 6378 NeededUriGrants(String targetPkg, int targetUid, int flags) { 6379 this.targetPkg = targetPkg; 6380 this.targetUid = targetUid; 6381 this.flags = flags; 6382 } 6383 } 6384 6385 /** 6386 * Like checkGrantUriPermissionLocked, but takes an Intent. 6387 */ 6388 NeededUriGrants checkGrantUriPermissionFromIntentLocked(int callingUid, 6389 String targetPkg, Intent intent, int mode, NeededUriGrants needed, int targetUserId) { 6390 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6391 "Checking URI perm to data=" + (intent != null ? intent.getData() : null) 6392 + " clip=" + (intent != null ? intent.getClipData() : null) 6393 + " from " + intent + "; flags=0x" 6394 + Integer.toHexString(intent != null ? intent.getFlags() : 0)); 6395 6396 if (targetPkg == null) { 6397 throw new NullPointerException("targetPkg"); 6398 } 6399 6400 if (intent == null) { 6401 return null; 6402 } 6403 Uri data = intent.getData(); 6404 ClipData clip = intent.getClipData(); 6405 if (data == null && clip == null) { 6406 return null; 6407 } 6408 final IPackageManager pm = AppGlobals.getPackageManager(); 6409 int targetUid; 6410 if (needed != null) { 6411 targetUid = needed.targetUid; 6412 } else { 6413 try { 6414 targetUid = pm.getPackageUid(targetPkg, targetUserId); 6415 } catch (RemoteException ex) { 6416 return null; 6417 } 6418 if (targetUid < 0) { 6419 if (DEBUG_URI_PERMISSION) { 6420 Slog.v(TAG, "Can't grant URI permission no uid for: " + targetPkg 6421 + " on user " + targetUserId); 6422 } 6423 return null; 6424 } 6425 } 6426 if (data != null) { 6427 GrantUri grantUri = GrantUri.resolve(UserHandle.getUserId(callingUid), data); 6428 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 6429 targetUid); 6430 if (targetUid > 0) { 6431 if (needed == null) { 6432 needed = new NeededUriGrants(targetPkg, targetUid, mode); 6433 } 6434 needed.add(grantUri); 6435 } 6436 } 6437 if (clip != null) { 6438 for (int i=0; i<clip.getItemCount(); i++) { 6439 Uri uri = clip.getItemAt(i).getUri(); 6440 if (uri != null) { 6441 GrantUri grantUri = GrantUri.resolve(UserHandle.getUserId(callingUid), uri); 6442 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 6443 targetUid); 6444 if (targetUid > 0) { 6445 if (needed == null) { 6446 needed = new NeededUriGrants(targetPkg, targetUid, mode); 6447 } 6448 needed.add(grantUri); 6449 } 6450 } else { 6451 Intent clipIntent = clip.getItemAt(i).getIntent(); 6452 if (clipIntent != null) { 6453 NeededUriGrants newNeeded = checkGrantUriPermissionFromIntentLocked( 6454 callingUid, targetPkg, clipIntent, mode, needed, targetUserId); 6455 if (newNeeded != null) { 6456 needed = newNeeded; 6457 } 6458 } 6459 } 6460 } 6461 } 6462 6463 return needed; 6464 } 6465 6466 /** 6467 * Like grantUriPermissionUncheckedLocked, but takes an Intent. 6468 */ 6469 void grantUriPermissionUncheckedFromIntentLocked(NeededUriGrants needed, 6470 UriPermissionOwner owner) { 6471 if (needed != null) { 6472 for (int i=0; i<needed.size(); i++) { 6473 GrantUri grantUri = needed.get(i); 6474 grantUriPermissionUncheckedLocked(needed.targetUid, needed.targetPkg, 6475 grantUri, needed.flags, owner); 6476 } 6477 } 6478 } 6479 6480 void grantUriPermissionFromIntentLocked(int callingUid, 6481 String targetPkg, Intent intent, UriPermissionOwner owner, int targetUserId) { 6482 NeededUriGrants needed = checkGrantUriPermissionFromIntentLocked(callingUid, targetPkg, 6483 intent, intent != null ? intent.getFlags() : 0, null, targetUserId); 6484 if (needed == null) { 6485 return; 6486 } 6487 6488 grantUriPermissionUncheckedFromIntentLocked(needed, owner); 6489 } 6490 6491 @Override 6492 public void grantUriPermission(IApplicationThread caller, String targetPkg, Uri uri, 6493 final int modeFlags, int userId) { 6494 enforceNotIsolatedCaller("grantUriPermission"); 6495 GrantUri grantUri = new GrantUri(userId, uri, false); 6496 synchronized(this) { 6497 final ProcessRecord r = getRecordForAppLocked(caller); 6498 if (r == null) { 6499 throw new SecurityException("Unable to find app for caller " 6500 + caller 6501 + " when granting permission to uri " + grantUri); 6502 } 6503 if (targetPkg == null) { 6504 throw new IllegalArgumentException("null target"); 6505 } 6506 if (grantUri == null) { 6507 throw new IllegalArgumentException("null uri"); 6508 } 6509 6510 Preconditions.checkFlagsArgument(modeFlags, Intent.FLAG_GRANT_READ_URI_PERMISSION 6511 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION 6512 | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION 6513 | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION); 6514 6515 grantUriPermissionLocked(r.uid, targetPkg, grantUri, modeFlags, null); 6516 } 6517 } 6518 6519 void removeUriPermissionIfNeededLocked(UriPermission perm) { 6520 if (perm.modeFlags == 0) { 6521 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 6522 perm.targetUid); 6523 if (perms != null) { 6524 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6525 "Removing " + perm.targetUid + " permission to " + perm.uri); 6526 6527 perms.remove(perm.uri); 6528 if (perms.isEmpty()) { 6529 mGrantedUriPermissions.remove(perm.targetUid); 6530 } 6531 } 6532 } 6533 } 6534 6535 private void revokeUriPermissionLocked(int callingUid, GrantUri grantUri, final int modeFlags) { 6536 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Revoking all granted permissions to " + grantUri); 6537 6538 final IPackageManager pm = AppGlobals.getPackageManager(); 6539 final String authority = grantUri.uri.getAuthority(); 6540 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6541 if (pi == null) { 6542 Slog.w(TAG, "No content provider found for permission revoke: " 6543 + grantUri.toSafeString()); 6544 return; 6545 } 6546 6547 // Does the caller have this permission on the URI? 6548 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 6549 // Right now, if you are not the original owner of the permission, 6550 // you are not allowed to revoke it. 6551 //if (!checkUriPermissionLocked(uri, callingUid, modeFlags)) { 6552 throw new SecurityException("Uid " + callingUid 6553 + " does not have permission to uri " + grantUri); 6554 //} 6555 } 6556 6557 boolean persistChanged = false; 6558 6559 // Go through all of the permissions and remove any that match. 6560 int N = mGrantedUriPermissions.size(); 6561 for (int i = 0; i < N; i++) { 6562 final int targetUid = mGrantedUriPermissions.keyAt(i); 6563 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6564 6565 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 6566 final UriPermission perm = it.next(); 6567 if (perm.uri.sourceUserId == grantUri.sourceUserId 6568 && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) { 6569 if (DEBUG_URI_PERMISSION) 6570 Slog.v(TAG, 6571 "Revoking " + perm.targetUid + " permission to " + perm.uri); 6572 persistChanged |= perm.revokeModes( 6573 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 6574 if (perm.modeFlags == 0) { 6575 it.remove(); 6576 } 6577 } 6578 } 6579 6580 if (perms.isEmpty()) { 6581 mGrantedUriPermissions.remove(targetUid); 6582 N--; 6583 i--; 6584 } 6585 } 6586 6587 if (persistChanged) { 6588 schedulePersistUriGrants(); 6589 } 6590 } 6591 6592 @Override 6593 public void revokeUriPermission(IApplicationThread caller, Uri uri, final int modeFlags, 6594 int userId) { 6595 enforceNotIsolatedCaller("revokeUriPermission"); 6596 synchronized(this) { 6597 final ProcessRecord r = getRecordForAppLocked(caller); 6598 if (r == null) { 6599 throw new SecurityException("Unable to find app for caller " 6600 + caller 6601 + " when revoking permission to uri " + uri); 6602 } 6603 if (uri == null) { 6604 Slog.w(TAG, "revokeUriPermission: null uri"); 6605 return; 6606 } 6607 6608 if (!Intent.isAccessUriMode(modeFlags)) { 6609 return; 6610 } 6611 6612 final IPackageManager pm = AppGlobals.getPackageManager(); 6613 final String authority = uri.getAuthority(); 6614 final ProviderInfo pi = getProviderInfoLocked(authority, userId); 6615 if (pi == null) { 6616 Slog.w(TAG, "No content provider found for permission revoke: " 6617 + uri.toSafeString()); 6618 return; 6619 } 6620 6621 revokeUriPermissionLocked(r.uid, new GrantUri(userId, uri, false), modeFlags); 6622 } 6623 } 6624 6625 /** 6626 * Remove any {@link UriPermission} granted <em>from</em> or <em>to</em> the 6627 * given package. 6628 * 6629 * @param packageName Package name to match, or {@code null} to apply to all 6630 * packages. 6631 * @param userHandle User to match, or {@link UserHandle#USER_ALL} to apply 6632 * to all users. 6633 * @param persistable If persistable grants should be removed. 6634 */ 6635 private void removeUriPermissionsForPackageLocked( 6636 String packageName, int userHandle, boolean persistable) { 6637 if (userHandle == UserHandle.USER_ALL && packageName == null) { 6638 throw new IllegalArgumentException("Must narrow by either package or user"); 6639 } 6640 6641 boolean persistChanged = false; 6642 6643 int N = mGrantedUriPermissions.size(); 6644 for (int i = 0; i < N; i++) { 6645 final int targetUid = mGrantedUriPermissions.keyAt(i); 6646 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6647 6648 // Only inspect grants matching user 6649 if (userHandle == UserHandle.USER_ALL 6650 || userHandle == UserHandle.getUserId(targetUid)) { 6651 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 6652 final UriPermission perm = it.next(); 6653 6654 // Only inspect grants matching package 6655 if (packageName == null || perm.sourcePkg.equals(packageName) 6656 || perm.targetPkg.equals(packageName)) { 6657 persistChanged |= perm.revokeModes( 6658 persistable ? ~0 : ~Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 6659 6660 // Only remove when no modes remain; any persisted grants 6661 // will keep this alive. 6662 if (perm.modeFlags == 0) { 6663 it.remove(); 6664 } 6665 } 6666 } 6667 6668 if (perms.isEmpty()) { 6669 mGrantedUriPermissions.remove(targetUid); 6670 N--; 6671 i--; 6672 } 6673 } 6674 } 6675 6676 if (persistChanged) { 6677 schedulePersistUriGrants(); 6678 } 6679 } 6680 6681 @Override 6682 public IBinder newUriPermissionOwner(String name) { 6683 enforceNotIsolatedCaller("newUriPermissionOwner"); 6684 synchronized(this) { 6685 UriPermissionOwner owner = new UriPermissionOwner(this, name); 6686 return owner.getExternalTokenLocked(); 6687 } 6688 } 6689 6690 @Override 6691 public void grantUriPermissionFromOwner(IBinder token, int fromUid, String targetPkg, Uri uri, 6692 final int modeFlags, int userId) { 6693 synchronized(this) { 6694 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 6695 if (owner == null) { 6696 throw new IllegalArgumentException("Unknown owner: " + token); 6697 } 6698 if (fromUid != Binder.getCallingUid()) { 6699 if (Binder.getCallingUid() != Process.myUid()) { 6700 // Only system code can grant URI permissions on behalf 6701 // of other users. 6702 throw new SecurityException("nice try"); 6703 } 6704 } 6705 if (targetPkg == null) { 6706 throw new IllegalArgumentException("null target"); 6707 } 6708 if (uri == null) { 6709 throw new IllegalArgumentException("null uri"); 6710 } 6711 6712 grantUriPermissionLocked(fromUid, targetPkg, new GrantUri(userId, uri, false), 6713 modeFlags, owner); 6714 } 6715 } 6716 6717 @Override 6718 public void revokeUriPermissionFromOwner(IBinder token, Uri uri, int mode, int userId) { 6719 synchronized(this) { 6720 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 6721 if (owner == null) { 6722 throw new IllegalArgumentException("Unknown owner: " + token); 6723 } 6724 6725 if (uri == null) { 6726 owner.removeUriPermissionsLocked(mode); 6727 } else { 6728 owner.removeUriPermissionLocked(new GrantUri(userId, uri, false), mode); 6729 } 6730 } 6731 } 6732 6733 private void schedulePersistUriGrants() { 6734 if (!mHandler.hasMessages(PERSIST_URI_GRANTS_MSG)) { 6735 mHandler.sendMessageDelayed(mHandler.obtainMessage(PERSIST_URI_GRANTS_MSG), 6736 10 * DateUtils.SECOND_IN_MILLIS); 6737 } 6738 } 6739 6740 private void writeGrantedUriPermissions() { 6741 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "writeGrantedUriPermissions()"); 6742 6743 // Snapshot permissions so we can persist without lock 6744 ArrayList<UriPermission.Snapshot> persist = Lists.newArrayList(); 6745 synchronized (this) { 6746 final int size = mGrantedUriPermissions.size(); 6747 for (int i = 0; i < size; i++) { 6748 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6749 for (UriPermission perm : perms.values()) { 6750 if (perm.persistedModeFlags != 0) { 6751 persist.add(perm.snapshot()); 6752 } 6753 } 6754 } 6755 } 6756 6757 FileOutputStream fos = null; 6758 try { 6759 fos = mGrantFile.startWrite(); 6760 6761 XmlSerializer out = new FastXmlSerializer(); 6762 out.setOutput(fos, "utf-8"); 6763 out.startDocument(null, true); 6764 out.startTag(null, TAG_URI_GRANTS); 6765 for (UriPermission.Snapshot perm : persist) { 6766 out.startTag(null, TAG_URI_GRANT); 6767 writeIntAttribute(out, ATTR_SOURCE_USER_ID, perm.uri.sourceUserId); 6768 writeIntAttribute(out, ATTR_TARGET_USER_ID, perm.targetUserId); 6769 out.attribute(null, ATTR_SOURCE_PKG, perm.sourcePkg); 6770 out.attribute(null, ATTR_TARGET_PKG, perm.targetPkg); 6771 out.attribute(null, ATTR_URI, String.valueOf(perm.uri.uri)); 6772 writeBooleanAttribute(out, ATTR_PREFIX, perm.uri.prefix); 6773 writeIntAttribute(out, ATTR_MODE_FLAGS, perm.persistedModeFlags); 6774 writeLongAttribute(out, ATTR_CREATED_TIME, perm.persistedCreateTime); 6775 out.endTag(null, TAG_URI_GRANT); 6776 } 6777 out.endTag(null, TAG_URI_GRANTS); 6778 out.endDocument(); 6779 6780 mGrantFile.finishWrite(fos); 6781 } catch (IOException e) { 6782 if (fos != null) { 6783 mGrantFile.failWrite(fos); 6784 } 6785 } 6786 } 6787 6788 private void readGrantedUriPermissionsLocked() { 6789 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "readGrantedUriPermissions()"); 6790 6791 final long now = System.currentTimeMillis(); 6792 6793 FileInputStream fis = null; 6794 try { 6795 fis = mGrantFile.openRead(); 6796 final XmlPullParser in = Xml.newPullParser(); 6797 in.setInput(fis, null); 6798 6799 int type; 6800 while ((type = in.next()) != END_DOCUMENT) { 6801 final String tag = in.getName(); 6802 if (type == START_TAG) { 6803 if (TAG_URI_GRANT.equals(tag)) { 6804 final int sourceUserId; 6805 final int targetUserId; 6806 final int userHandle = readIntAttribute(in, 6807 ATTR_USER_HANDLE, UserHandle.USER_NULL); 6808 if (userHandle != UserHandle.USER_NULL) { 6809 // For backwards compatibility. 6810 sourceUserId = userHandle; 6811 targetUserId = userHandle; 6812 } else { 6813 sourceUserId = readIntAttribute(in, ATTR_SOURCE_USER_ID); 6814 targetUserId = readIntAttribute(in, ATTR_TARGET_USER_ID); 6815 } 6816 final String sourcePkg = in.getAttributeValue(null, ATTR_SOURCE_PKG); 6817 final String targetPkg = in.getAttributeValue(null, ATTR_TARGET_PKG); 6818 final Uri uri = Uri.parse(in.getAttributeValue(null, ATTR_URI)); 6819 final boolean prefix = readBooleanAttribute(in, ATTR_PREFIX); 6820 final int modeFlags = readIntAttribute(in, ATTR_MODE_FLAGS); 6821 final long createdTime = readLongAttribute(in, ATTR_CREATED_TIME, now); 6822 6823 // Sanity check that provider still belongs to source package 6824 final ProviderInfo pi = getProviderInfoLocked( 6825 uri.getAuthority(), sourceUserId); 6826 if (pi != null && sourcePkg.equals(pi.packageName)) { 6827 int targetUid = -1; 6828 try { 6829 targetUid = AppGlobals.getPackageManager() 6830 .getPackageUid(targetPkg, targetUserId); 6831 } catch (RemoteException e) { 6832 } 6833 if (targetUid != -1) { 6834 final UriPermission perm = findOrCreateUriPermissionLocked( 6835 sourcePkg, targetPkg, targetUid, 6836 new GrantUri(sourceUserId, uri, prefix)); 6837 perm.initPersistedModes(modeFlags, createdTime); 6838 } 6839 } else { 6840 Slog.w(TAG, "Persisted grant for " + uri + " had source " + sourcePkg 6841 + " but instead found " + pi); 6842 } 6843 } 6844 } 6845 } 6846 } catch (FileNotFoundException e) { 6847 // Missing grants is okay 6848 } catch (IOException e) { 6849 Log.wtf(TAG, "Failed reading Uri grants", e); 6850 } catch (XmlPullParserException e) { 6851 Log.wtf(TAG, "Failed reading Uri grants", e); 6852 } finally { 6853 IoUtils.closeQuietly(fis); 6854 } 6855 } 6856 6857 @Override 6858 public void takePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 6859 enforceNotIsolatedCaller("takePersistableUriPermission"); 6860 6861 Preconditions.checkFlagsArgument(modeFlags, 6862 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 6863 6864 synchronized (this) { 6865 final int callingUid = Binder.getCallingUid(); 6866 boolean persistChanged = false; 6867 GrantUri grantUri = new GrantUri(userId, uri, false); 6868 6869 UriPermission exactPerm = findUriPermissionLocked(callingUid, 6870 new GrantUri(userId, uri, false)); 6871 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 6872 new GrantUri(userId, uri, true)); 6873 6874 final boolean exactValid = (exactPerm != null) 6875 && ((modeFlags & exactPerm.persistableModeFlags) == modeFlags); 6876 final boolean prefixValid = (prefixPerm != null) 6877 && ((modeFlags & prefixPerm.persistableModeFlags) == modeFlags); 6878 6879 if (!(exactValid || prefixValid)) { 6880 throw new SecurityException("No persistable permission grants found for UID " 6881 + callingUid + " and Uri " + grantUri.toSafeString()); 6882 } 6883 6884 if (exactValid) { 6885 persistChanged |= exactPerm.takePersistableModes(modeFlags); 6886 } 6887 if (prefixValid) { 6888 persistChanged |= prefixPerm.takePersistableModes(modeFlags); 6889 } 6890 6891 persistChanged |= maybePrunePersistedUriGrantsLocked(callingUid); 6892 6893 if (persistChanged) { 6894 schedulePersistUriGrants(); 6895 } 6896 } 6897 } 6898 6899 @Override 6900 public void releasePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 6901 enforceNotIsolatedCaller("releasePersistableUriPermission"); 6902 6903 Preconditions.checkFlagsArgument(modeFlags, 6904 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 6905 6906 synchronized (this) { 6907 final int callingUid = Binder.getCallingUid(); 6908 boolean persistChanged = false; 6909 6910 UriPermission exactPerm = findUriPermissionLocked(callingUid, 6911 new GrantUri(userId, uri, false)); 6912 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 6913 new GrantUri(userId, uri, true)); 6914 if (exactPerm == null && prefixPerm == null) { 6915 throw new SecurityException("No permission grants found for UID " + callingUid 6916 + " and Uri " + uri.toSafeString()); 6917 } 6918 6919 if (exactPerm != null) { 6920 persistChanged |= exactPerm.releasePersistableModes(modeFlags); 6921 removeUriPermissionIfNeededLocked(exactPerm); 6922 } 6923 if (prefixPerm != null) { 6924 persistChanged |= prefixPerm.releasePersistableModes(modeFlags); 6925 removeUriPermissionIfNeededLocked(prefixPerm); 6926 } 6927 6928 if (persistChanged) { 6929 schedulePersistUriGrants(); 6930 } 6931 } 6932 } 6933 6934 /** 6935 * Prune any older {@link UriPermission} for the given UID until outstanding 6936 * persisted grants are below {@link #MAX_PERSISTED_URI_GRANTS}. 6937 * 6938 * @return if any mutations occured that require persisting. 6939 */ 6940 private boolean maybePrunePersistedUriGrantsLocked(int uid) { 6941 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 6942 if (perms == null) return false; 6943 if (perms.size() < MAX_PERSISTED_URI_GRANTS) return false; 6944 6945 final ArrayList<UriPermission> persisted = Lists.newArrayList(); 6946 for (UriPermission perm : perms.values()) { 6947 if (perm.persistedModeFlags != 0) { 6948 persisted.add(perm); 6949 } 6950 } 6951 6952 final int trimCount = persisted.size() - MAX_PERSISTED_URI_GRANTS; 6953 if (trimCount <= 0) return false; 6954 6955 Collections.sort(persisted, new UriPermission.PersistedTimeComparator()); 6956 for (int i = 0; i < trimCount; i++) { 6957 final UriPermission perm = persisted.get(i); 6958 6959 if (DEBUG_URI_PERMISSION) { 6960 Slog.v(TAG, "Trimming grant created at " + perm.persistedCreateTime); 6961 } 6962 6963 perm.releasePersistableModes(~0); 6964 removeUriPermissionIfNeededLocked(perm); 6965 } 6966 6967 return true; 6968 } 6969 6970 @Override 6971 public ParceledListSlice<android.content.UriPermission> getPersistedUriPermissions( 6972 String packageName, boolean incoming) { 6973 enforceNotIsolatedCaller("getPersistedUriPermissions"); 6974 Preconditions.checkNotNull(packageName, "packageName"); 6975 6976 final int callingUid = Binder.getCallingUid(); 6977 final IPackageManager pm = AppGlobals.getPackageManager(); 6978 try { 6979 final int packageUid = pm.getPackageUid(packageName, UserHandle.getUserId(callingUid)); 6980 if (packageUid != callingUid) { 6981 throw new SecurityException( 6982 "Package " + packageName + " does not belong to calling UID " + callingUid); 6983 } 6984 } catch (RemoteException e) { 6985 throw new SecurityException("Failed to verify package name ownership"); 6986 } 6987 6988 final ArrayList<android.content.UriPermission> result = Lists.newArrayList(); 6989 synchronized (this) { 6990 if (incoming) { 6991 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 6992 callingUid); 6993 if (perms == null) { 6994 Slog.w(TAG, "No permission grants found for " + packageName); 6995 } else { 6996 for (UriPermission perm : perms.values()) { 6997 if (packageName.equals(perm.targetPkg) && perm.persistedModeFlags != 0) { 6998 result.add(perm.buildPersistedPublicApiObject()); 6999 } 7000 } 7001 } 7002 } else { 7003 final int size = mGrantedUriPermissions.size(); 7004 for (int i = 0; i < size; i++) { 7005 final ArrayMap<GrantUri, UriPermission> perms = 7006 mGrantedUriPermissions.valueAt(i); 7007 for (UriPermission perm : perms.values()) { 7008 if (packageName.equals(perm.sourcePkg) && perm.persistedModeFlags != 0) { 7009 result.add(perm.buildPersistedPublicApiObject()); 7010 } 7011 } 7012 } 7013 } 7014 } 7015 return new ParceledListSlice<android.content.UriPermission>(result); 7016 } 7017 7018 @Override 7019 public void showWaitingForDebugger(IApplicationThread who, boolean waiting) { 7020 synchronized (this) { 7021 ProcessRecord app = 7022 who != null ? getRecordForAppLocked(who) : null; 7023 if (app == null) return; 7024 7025 Message msg = Message.obtain(); 7026 msg.what = WAIT_FOR_DEBUGGER_MSG; 7027 msg.obj = app; 7028 msg.arg1 = waiting ? 1 : 0; 7029 mHandler.sendMessage(msg); 7030 } 7031 } 7032 7033 @Override 7034 public void getMemoryInfo(ActivityManager.MemoryInfo outInfo) { 7035 final long homeAppMem = mProcessList.getMemLevel(ProcessList.HOME_APP_ADJ); 7036 final long cachedAppMem = mProcessList.getMemLevel(ProcessList.CACHED_APP_MIN_ADJ); 7037 outInfo.availMem = Process.getFreeMemory(); 7038 outInfo.totalMem = Process.getTotalMemory(); 7039 outInfo.threshold = homeAppMem; 7040 outInfo.lowMemory = outInfo.availMem < (homeAppMem + ((cachedAppMem-homeAppMem)/2)); 7041 outInfo.hiddenAppThreshold = cachedAppMem; 7042 outInfo.secondaryServerThreshold = mProcessList.getMemLevel( 7043 ProcessList.SERVICE_ADJ); 7044 outInfo.visibleAppThreshold = mProcessList.getMemLevel( 7045 ProcessList.VISIBLE_APP_ADJ); 7046 outInfo.foregroundAppThreshold = mProcessList.getMemLevel( 7047 ProcessList.FOREGROUND_APP_ADJ); 7048 } 7049 7050 // ========================================================= 7051 // TASK MANAGEMENT 7052 // ========================================================= 7053 7054 @Override 7055 public List<IAppTask> getAppTasks() { 7056 int callingUid = Binder.getCallingUid(); 7057 long ident = Binder.clearCallingIdentity(); 7058 synchronized(this) { 7059 ArrayList<IAppTask> list = new ArrayList<IAppTask>(); 7060 try { 7061 if (localLOGV) Slog.v(TAG, "getAppTasks"); 7062 7063 final int N = mRecentTasks.size(); 7064 for (int i = 0; i < N; i++) { 7065 TaskRecord tr = mRecentTasks.get(i); 7066 // Skip tasks that are not created by the caller 7067 if (tr.creatorUid == callingUid) { 7068 ActivityManager.RecentTaskInfo taskInfo = 7069 createRecentTaskInfoFromTaskRecord(tr); 7070 AppTaskImpl taskImpl = new AppTaskImpl(taskInfo.persistentId, callingUid); 7071 list.add(taskImpl); 7072 } 7073 } 7074 } finally { 7075 Binder.restoreCallingIdentity(ident); 7076 } 7077 return list; 7078 } 7079 } 7080 7081 @Override 7082 public List<RunningTaskInfo> getTasks(int maxNum, int flags) { 7083 final int callingUid = Binder.getCallingUid(); 7084 ArrayList<RunningTaskInfo> list = new ArrayList<RunningTaskInfo>(); 7085 7086 synchronized(this) { 7087 if (localLOGV) Slog.v( 7088 TAG, "getTasks: max=" + maxNum + ", flags=" + flags); 7089 7090 final boolean allowed = checkCallingPermission( 7091 android.Manifest.permission.GET_TASKS) 7092 == PackageManager.PERMISSION_GRANTED; 7093 if (!allowed) { 7094 Slog.w(TAG, "getTasks: caller " + callingUid 7095 + " does not hold GET_TASKS; limiting output"); 7096 } 7097 7098 // TODO: Improve with MRU list from all ActivityStacks. 7099 mStackSupervisor.getTasksLocked(maxNum, list, callingUid, allowed); 7100 } 7101 7102 return list; 7103 } 7104 7105 TaskRecord getMostRecentTask() { 7106 return mRecentTasks.get(0); 7107 } 7108 7109 /** 7110 * Creates a new RecentTaskInfo from a TaskRecord. 7111 */ 7112 private ActivityManager.RecentTaskInfo createRecentTaskInfoFromTaskRecord(TaskRecord tr) { 7113 // Update the task description to reflect any changes in the task stack 7114 tr.updateTaskDescription(); 7115 7116 // Compose the recent task info 7117 ActivityManager.RecentTaskInfo rti 7118 = new ActivityManager.RecentTaskInfo(); 7119 rti.id = tr.mActivities.isEmpty() ? -1 : tr.taskId; 7120 rti.persistentId = tr.taskId; 7121 rti.baseIntent = new Intent(tr.getBaseIntent()); 7122 rti.origActivity = tr.origActivity; 7123 rti.description = tr.lastDescription; 7124 rti.stackId = tr.stack != null ? tr.stack.mStackId : -1; 7125 rti.userId = tr.userId; 7126 rti.taskDescription = new ActivityManager.TaskDescription(tr.lastTaskDescription); 7127 return rti; 7128 } 7129 7130 @Override 7131 public List<ActivityManager.RecentTaskInfo> getRecentTasks(int maxNum, 7132 int flags, int userId) { 7133 final int callingUid = Binder.getCallingUid(); 7134 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 7135 false, true, "getRecentTasks", null); 7136 7137 synchronized (this) { 7138 final boolean allowed = checkCallingPermission( 7139 android.Manifest.permission.GET_TASKS) 7140 == PackageManager.PERMISSION_GRANTED; 7141 if (!allowed) { 7142 Slog.w(TAG, "getRecentTasks: caller " + callingUid 7143 + " does not hold GET_TASKS; limiting output"); 7144 } 7145 final boolean detailed = checkCallingPermission( 7146 android.Manifest.permission.GET_DETAILED_TASKS) 7147 == PackageManager.PERMISSION_GRANTED; 7148 7149 IPackageManager pm = AppGlobals.getPackageManager(); 7150 7151 final int N = mRecentTasks.size(); 7152 ArrayList<ActivityManager.RecentTaskInfo> res 7153 = new ArrayList<ActivityManager.RecentTaskInfo>( 7154 maxNum < N ? maxNum : N); 7155 7156 final Set<Integer> includedUsers; 7157 if ((flags & ActivityManager.RECENT_INCLUDE_PROFILES) != 0) { 7158 includedUsers = getProfileIdsLocked(userId); 7159 } else { 7160 includedUsers = new HashSet<Integer>(); 7161 } 7162 includedUsers.add(Integer.valueOf(userId)); 7163 for (int i=0; i<N && maxNum > 0; i++) { 7164 TaskRecord tr = mRecentTasks.get(i); 7165 // Only add calling user or related users recent tasks 7166 if (!includedUsers.contains(Integer.valueOf(tr.userId))) continue; 7167 7168 // Return the entry if desired by the caller. We always return 7169 // the first entry, because callers always expect this to be the 7170 // foreground app. We may filter others if the caller has 7171 // not supplied RECENT_WITH_EXCLUDED and there is some reason 7172 // we should exclude the entry. 7173 7174 if (i == 0 7175 || ((flags&ActivityManager.RECENT_WITH_EXCLUDED) != 0) 7176 || (tr.intent == null) 7177 || ((tr.intent.getFlags() 7178 &Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS) == 0)) { 7179 if (!allowed) { 7180 // If the caller doesn't have the GET_TASKS permission, then only 7181 // allow them to see a small subset of tasks -- their own and home. 7182 if (!tr.isHomeTask() && tr.creatorUid != callingUid) { 7183 continue; 7184 } 7185 } 7186 7187 ActivityManager.RecentTaskInfo rti = createRecentTaskInfoFromTaskRecord(tr); 7188 if (!detailed) { 7189 rti.baseIntent.replaceExtras((Bundle)null); 7190 } 7191 7192 if ((flags&ActivityManager.RECENT_IGNORE_UNAVAILABLE) != 0) { 7193 // Check whether this activity is currently available. 7194 try { 7195 if (rti.origActivity != null) { 7196 if (pm.getActivityInfo(rti.origActivity, 0, userId) 7197 == null) { 7198 continue; 7199 } 7200 } else if (rti.baseIntent != null) { 7201 if (pm.queryIntentActivities(rti.baseIntent, 7202 null, 0, userId) == null) { 7203 continue; 7204 } 7205 } 7206 } catch (RemoteException e) { 7207 // Will never happen. 7208 } 7209 } 7210 7211 res.add(rti); 7212 maxNum--; 7213 } 7214 } 7215 return res; 7216 } 7217 } 7218 7219 private TaskRecord recentTaskForIdLocked(int id) { 7220 final int N = mRecentTasks.size(); 7221 for (int i=0; i<N; i++) { 7222 TaskRecord tr = mRecentTasks.get(i); 7223 if (tr.taskId == id) { 7224 return tr; 7225 } 7226 } 7227 return null; 7228 } 7229 7230 @Override 7231 public ActivityManager.TaskThumbnails getTaskThumbnails(int id) { 7232 synchronized (this) { 7233 enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER, 7234 "getTaskThumbnails()"); 7235 TaskRecord tr = recentTaskForIdLocked(id); 7236 if (tr != null) { 7237 return tr.getTaskThumbnailsLocked(); 7238 } 7239 } 7240 return null; 7241 } 7242 7243 @Override 7244 public Bitmap getTaskTopThumbnail(int id) { 7245 synchronized (this) { 7246 enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER, 7247 "getTaskTopThumbnail()"); 7248 TaskRecord tr = recentTaskForIdLocked(id); 7249 if (tr != null) { 7250 return tr.getTaskTopThumbnailLocked(); 7251 } 7252 } 7253 return null; 7254 } 7255 7256 @Override 7257 public void setTaskDescription(IBinder token, ActivityManager.TaskDescription td) { 7258 synchronized (this) { 7259 ActivityRecord r = ActivityRecord.isInStackLocked(token); 7260 if (r != null) { 7261 r.taskDescription = td; 7262 r.task.updateTaskDescription(); 7263 } 7264 } 7265 } 7266 7267 @Override 7268 public boolean removeSubTask(int taskId, int subTaskIndex) { 7269 synchronized (this) { 7270 enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, 7271 "removeSubTask()"); 7272 long ident = Binder.clearCallingIdentity(); 7273 try { 7274 TaskRecord tr = recentTaskForIdLocked(taskId); 7275 if (tr != null) { 7276 return tr.removeTaskActivitiesLocked(subTaskIndex, true) != null; 7277 } 7278 return false; 7279 } finally { 7280 Binder.restoreCallingIdentity(ident); 7281 } 7282 } 7283 } 7284 7285 private void killUnneededProcessLocked(ProcessRecord pr, String reason) { 7286 if (!pr.killedByAm) { 7287 Slog.i(TAG, "Killing " + pr.toShortString() + " (adj " + pr.setAdj + "): " + reason); 7288 EventLog.writeEvent(EventLogTags.AM_KILL, pr.userId, pr.pid, 7289 pr.processName, pr.setAdj, reason); 7290 pr.killedByAm = true; 7291 Process.killProcessQuiet(pr.pid); 7292 } 7293 } 7294 7295 private void cleanUpRemovedTaskLocked(TaskRecord tr, int flags) { 7296 tr.disposeThumbnail(); 7297 mRecentTasks.remove(tr); 7298 final boolean killProcesses = (flags&ActivityManager.REMOVE_TASK_KILL_PROCESS) != 0; 7299 Intent baseIntent = new Intent( 7300 tr.intent != null ? tr.intent : tr.affinityIntent); 7301 ComponentName component = baseIntent.getComponent(); 7302 if (component == null) { 7303 Slog.w(TAG, "Now component for base intent of task: " + tr); 7304 return; 7305 } 7306 7307 // Find any running services associated with this app. 7308 mServices.cleanUpRemovedTaskLocked(tr, component, baseIntent); 7309 7310 if (killProcesses) { 7311 // Find any running processes associated with this app. 7312 final String pkg = component.getPackageName(); 7313 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 7314 ArrayMap<String, SparseArray<ProcessRecord>> pmap = mProcessNames.getMap(); 7315 for (int i=0; i<pmap.size(); i++) { 7316 SparseArray<ProcessRecord> uids = pmap.valueAt(i); 7317 for (int j=0; j<uids.size(); j++) { 7318 ProcessRecord proc = uids.valueAt(j); 7319 if (proc.userId != tr.userId) { 7320 continue; 7321 } 7322 if (!proc.pkgList.containsKey(pkg)) { 7323 continue; 7324 } 7325 procs.add(proc); 7326 } 7327 } 7328 7329 // Kill the running processes. 7330 for (int i=0; i<procs.size(); i++) { 7331 ProcessRecord pr = procs.get(i); 7332 if (pr == mHomeProcess) { 7333 // Don't kill the home process along with tasks from the same package. 7334 continue; 7335 } 7336 if (pr.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 7337 killUnneededProcessLocked(pr, "remove task"); 7338 } else { 7339 pr.waitingToKill = "remove task"; 7340 } 7341 } 7342 } 7343 } 7344 7345 /** 7346 * Removes the task with the specified task id. 7347 * 7348 * @param taskId Identifier of the task to be removed. 7349 * @param flags Additional operational flags. May be 0 or 7350 * {@link ActivityManager#REMOVE_TASK_KILL_PROCESS}. 7351 * @return Returns true if the given task was found and removed. 7352 */ 7353 private boolean removeTaskByIdLocked(int taskId, int flags) { 7354 TaskRecord tr = recentTaskForIdLocked(taskId); 7355 if (tr != null) { 7356 tr.removeTaskActivitiesLocked(-1, false); 7357 cleanUpRemovedTaskLocked(tr, flags); 7358 if (tr.isPersistable) { 7359 notifyTaskPersisterLocked(tr, true); 7360 } 7361 return true; 7362 } 7363 return false; 7364 } 7365 7366 @Override 7367 public boolean removeTask(int taskId, int flags) { 7368 synchronized (this) { 7369 enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, 7370 "removeTask()"); 7371 long ident = Binder.clearCallingIdentity(); 7372 try { 7373 return removeTaskByIdLocked(taskId, flags); 7374 } finally { 7375 Binder.restoreCallingIdentity(ident); 7376 } 7377 } 7378 } 7379 7380 /** 7381 * TODO: Add mController hook 7382 */ 7383 @Override 7384 public void moveTaskToFront(int taskId, int flags, Bundle options) { 7385 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7386 "moveTaskToFront()"); 7387 7388 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToFront: moving taskId=" + taskId); 7389 synchronized(this) { 7390 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7391 Binder.getCallingUid(), "Task to front")) { 7392 ActivityOptions.abort(options); 7393 return; 7394 } 7395 final long origId = Binder.clearCallingIdentity(); 7396 try { 7397 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 7398 if (task == null) { 7399 return; 7400 } 7401 if (mStackSupervisor.isLockTaskModeViolation(task)) { 7402 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode"); 7403 return; 7404 } 7405 mStackSupervisor.findTaskToMoveToFrontLocked(task, flags, options); 7406 } finally { 7407 Binder.restoreCallingIdentity(origId); 7408 } 7409 ActivityOptions.abort(options); 7410 } 7411 } 7412 7413 @Override 7414 public void moveTaskToBack(int taskId) { 7415 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7416 "moveTaskToBack()"); 7417 7418 synchronized(this) { 7419 TaskRecord tr = recentTaskForIdLocked(taskId); 7420 if (tr != null) { 7421 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToBack: moving task=" + tr); 7422 ActivityStack stack = tr.stack; 7423 if (stack.mResumedActivity != null && stack.mResumedActivity.task == tr) { 7424 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7425 Binder.getCallingUid(), "Task to back")) { 7426 return; 7427 } 7428 } 7429 final long origId = Binder.clearCallingIdentity(); 7430 try { 7431 stack.moveTaskToBackLocked(taskId, null); 7432 } finally { 7433 Binder.restoreCallingIdentity(origId); 7434 } 7435 } 7436 } 7437 } 7438 7439 /** 7440 * Moves an activity, and all of the other activities within the same task, to the bottom 7441 * of the history stack. The activity's order within the task is unchanged. 7442 * 7443 * @param token A reference to the activity we wish to move 7444 * @param nonRoot If false then this only works if the activity is the root 7445 * of a task; if true it will work for any activity in a task. 7446 * @return Returns true if the move completed, false if not. 7447 */ 7448 @Override 7449 public boolean moveActivityTaskToBack(IBinder token, boolean nonRoot) { 7450 enforceNotIsolatedCaller("moveActivityTaskToBack"); 7451 synchronized(this) { 7452 final long origId = Binder.clearCallingIdentity(); 7453 int taskId = ActivityRecord.getTaskForActivityLocked(token, !nonRoot); 7454 if (taskId >= 0) { 7455 return ActivityRecord.getStackLocked(token).moveTaskToBackLocked(taskId, null); 7456 } 7457 Binder.restoreCallingIdentity(origId); 7458 } 7459 return false; 7460 } 7461 7462 @Override 7463 public void moveTaskBackwards(int task) { 7464 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7465 "moveTaskBackwards()"); 7466 7467 synchronized(this) { 7468 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7469 Binder.getCallingUid(), "Task backwards")) { 7470 return; 7471 } 7472 final long origId = Binder.clearCallingIdentity(); 7473 moveTaskBackwardsLocked(task); 7474 Binder.restoreCallingIdentity(origId); 7475 } 7476 } 7477 7478 private final void moveTaskBackwardsLocked(int task) { 7479 Slog.e(TAG, "moveTaskBackwards not yet implemented!"); 7480 } 7481 7482 @Override 7483 public IBinder getHomeActivityToken() throws RemoteException { 7484 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7485 "getHomeActivityToken()"); 7486 synchronized (this) { 7487 return mStackSupervisor.getHomeActivityToken(); 7488 } 7489 } 7490 7491 @Override 7492 public IActivityContainer createActivityContainer(IBinder parentActivityToken, 7493 IActivityContainerCallback callback) throws RemoteException { 7494 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7495 "createActivityContainer()"); 7496 synchronized (this) { 7497 if (parentActivityToken == null) { 7498 throw new IllegalArgumentException("parent token must not be null"); 7499 } 7500 ActivityRecord r = ActivityRecord.forToken(parentActivityToken); 7501 if (r == null) { 7502 return null; 7503 } 7504 if (callback == null) { 7505 throw new IllegalArgumentException("callback must not be null"); 7506 } 7507 return mStackSupervisor.createActivityContainer(r, callback); 7508 } 7509 } 7510 7511 @Override 7512 public void deleteActivityContainer(IActivityContainer container) throws RemoteException { 7513 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7514 "deleteActivityContainer()"); 7515 synchronized (this) { 7516 mStackSupervisor.deleteActivityContainer(container); 7517 } 7518 } 7519 7520 @Override 7521 public IActivityContainer getEnclosingActivityContainer(IBinder activityToken) 7522 throws RemoteException { 7523 synchronized (this) { 7524 ActivityStack stack = ActivityRecord.getStackLocked(activityToken); 7525 if (stack != null) { 7526 return stack.mActivityContainer; 7527 } 7528 return null; 7529 } 7530 } 7531 7532 @Override 7533 public void moveTaskToStack(int taskId, int stackId, boolean toTop) { 7534 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7535 "moveTaskToStack()"); 7536 if (stackId == HOME_STACK_ID) { 7537 Slog.e(TAG, "moveTaskToStack: Attempt to move task " + taskId + " to home stack", 7538 new RuntimeException("here").fillInStackTrace()); 7539 } 7540 synchronized (this) { 7541 long ident = Binder.clearCallingIdentity(); 7542 try { 7543 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToStack: moving task=" + taskId + " to stackId=" 7544 + stackId + " toTop=" + toTop); 7545 mStackSupervisor.moveTaskToStack(taskId, stackId, toTop); 7546 } finally { 7547 Binder.restoreCallingIdentity(ident); 7548 } 7549 } 7550 } 7551 7552 @Override 7553 public void resizeStack(int stackBoxId, Rect bounds) { 7554 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7555 "resizeStackBox()"); 7556 long ident = Binder.clearCallingIdentity(); 7557 try { 7558 mWindowManager.resizeStack(stackBoxId, bounds); 7559 } finally { 7560 Binder.restoreCallingIdentity(ident); 7561 } 7562 } 7563 7564 @Override 7565 public List<StackInfo> getAllStackInfos() { 7566 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7567 "getAllStackInfos()"); 7568 long ident = Binder.clearCallingIdentity(); 7569 try { 7570 synchronized (this) { 7571 return mStackSupervisor.getAllStackInfosLocked(); 7572 } 7573 } finally { 7574 Binder.restoreCallingIdentity(ident); 7575 } 7576 } 7577 7578 @Override 7579 public StackInfo getStackInfo(int stackId) { 7580 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7581 "getStackInfo()"); 7582 long ident = Binder.clearCallingIdentity(); 7583 try { 7584 synchronized (this) { 7585 return mStackSupervisor.getStackInfoLocked(stackId); 7586 } 7587 } finally { 7588 Binder.restoreCallingIdentity(ident); 7589 } 7590 } 7591 7592 @Override 7593 public boolean isInHomeStack(int taskId) { 7594 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7595 "getStackInfo()"); 7596 long ident = Binder.clearCallingIdentity(); 7597 try { 7598 synchronized (this) { 7599 TaskRecord tr = recentTaskForIdLocked(taskId); 7600 return tr != null && tr.stack != null && tr.stack.isHomeStack(); 7601 } 7602 } finally { 7603 Binder.restoreCallingIdentity(ident); 7604 } 7605 } 7606 7607 @Override 7608 public int getTaskForActivity(IBinder token, boolean onlyRoot) { 7609 synchronized(this) { 7610 return ActivityRecord.getTaskForActivityLocked(token, onlyRoot); 7611 } 7612 } 7613 7614 private boolean isLockTaskAuthorized(ComponentName name) { 7615 final DevicePolicyManager dpm = (DevicePolicyManager) 7616 mContext.getSystemService(Context.DEVICE_POLICY_SERVICE); 7617 return dpm != null && dpm.isLockTaskPermitted(name); 7618 } 7619 7620 private void startLockTaskMode(TaskRecord task) { 7621 if (!isLockTaskAuthorized(task.intent.getComponent())) { 7622 return; 7623 } 7624 long ident = Binder.clearCallingIdentity(); 7625 try { 7626 synchronized (this) { 7627 // Since we lost lock on task, make sure it is still there. 7628 task = mStackSupervisor.anyTaskForIdLocked(task.taskId); 7629 if (task != null) { 7630 mStackSupervisor.setLockTaskModeLocked(task); 7631 } 7632 } 7633 } finally { 7634 Binder.restoreCallingIdentity(ident); 7635 } 7636 } 7637 7638 @Override 7639 public void startLockTaskMode(int taskId) { 7640 long ident = Binder.clearCallingIdentity(); 7641 try { 7642 final TaskRecord task; 7643 synchronized (this) { 7644 task = mStackSupervisor.anyTaskForIdLocked(taskId); 7645 } 7646 if (task != null) { 7647 startLockTaskMode(task); 7648 } 7649 } finally { 7650 Binder.restoreCallingIdentity(ident); 7651 } 7652 } 7653 7654 @Override 7655 public void startLockTaskMode(IBinder token) { 7656 long ident = Binder.clearCallingIdentity(); 7657 try { 7658 final TaskRecord task; 7659 synchronized (this) { 7660 final ActivityRecord r = ActivityRecord.forToken(token); 7661 if (r == null) { 7662 return; 7663 } 7664 task = r.task; 7665 } 7666 if (task != null) { 7667 startLockTaskMode(task); 7668 } 7669 } finally { 7670 Binder.restoreCallingIdentity(ident); 7671 } 7672 } 7673 7674 @Override 7675 public void stopLockTaskMode() { 7676 // Check if the calling task is eligible to use lock task 7677 final int uid = Binder.getCallingUid(); 7678 try { 7679 final String name = AppGlobals.getPackageManager().getNameForUid(uid); 7680 if (!isLockTaskAuthorized(new ComponentName(name, name))) { 7681 return; 7682 } 7683 } catch (RemoteException e) { 7684 Log.d(TAG, "stopLockTaskMode " + e); 7685 return; 7686 } 7687 // Stop lock task 7688 synchronized (this) { 7689 mStackSupervisor.setLockTaskModeLocked(null); 7690 } 7691 } 7692 7693 @Override 7694 public boolean isInLockTaskMode() { 7695 synchronized (this) { 7696 return mStackSupervisor.isInLockTaskMode(); 7697 } 7698 } 7699 7700 // ========================================================= 7701 // CONTENT PROVIDERS 7702 // ========================================================= 7703 7704 private final List<ProviderInfo> generateApplicationProvidersLocked(ProcessRecord app) { 7705 List<ProviderInfo> providers = null; 7706 try { 7707 providers = AppGlobals.getPackageManager(). 7708 queryContentProviders(app.processName, app.uid, 7709 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS); 7710 } catch (RemoteException ex) { 7711 } 7712 if (DEBUG_MU) 7713 Slog.v(TAG_MU, "generateApplicationProvidersLocked, app.info.uid = " + app.uid); 7714 int userId = app.userId; 7715 if (providers != null) { 7716 int N = providers.size(); 7717 app.pubProviders.ensureCapacity(N + app.pubProviders.size()); 7718 for (int i=0; i<N; i++) { 7719 ProviderInfo cpi = 7720 (ProviderInfo)providers.get(i); 7721 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo, 7722 cpi.name, cpi.flags); 7723 if (singleton && UserHandle.getUserId(app.uid) != 0) { 7724 // This is a singleton provider, but a user besides the 7725 // default user is asking to initialize a process it runs 7726 // in... well, no, it doesn't actually run in this process, 7727 // it runs in the process of the default user. Get rid of it. 7728 providers.remove(i); 7729 N--; 7730 i--; 7731 continue; 7732 } 7733 7734 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 7735 ContentProviderRecord cpr = mProviderMap.getProviderByClass(comp, userId); 7736 if (cpr == null) { 7737 cpr = new ContentProviderRecord(this, cpi, app.info, comp, singleton); 7738 mProviderMap.putProviderByClass(comp, cpr); 7739 } 7740 if (DEBUG_MU) 7741 Slog.v(TAG_MU, "generateApplicationProvidersLocked, cpi.uid = " + cpr.uid); 7742 app.pubProviders.put(cpi.name, cpr); 7743 if (!cpi.multiprocess || !"android".equals(cpi.packageName)) { 7744 // Don't add this if it is a platform component that is marked 7745 // to run in multiple processes, because this is actually 7746 // part of the framework so doesn't make sense to track as a 7747 // separate apk in the process. 7748 app.addPackage(cpi.applicationInfo.packageName, mProcessStats); 7749 } 7750 ensurePackageDexOpt(cpi.applicationInfo.packageName); 7751 } 7752 } 7753 return providers; 7754 } 7755 7756 /** 7757 * Check if {@link ProcessRecord} has a possible chance at accessing the 7758 * given {@link ProviderInfo}. Final permission checking is always done 7759 * in {@link ContentProvider}. 7760 */ 7761 private final String checkContentProviderPermissionLocked( 7762 ProviderInfo cpi, ProcessRecord r, int userId, boolean checkUser) { 7763 final int callingPid = (r != null) ? r.pid : Binder.getCallingPid(); 7764 final int callingUid = (r != null) ? r.uid : Binder.getCallingUid(); 7765 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 7766 // Looking for cross-user grants before to enforce the typical cross-users permissions 7767 if (userId != UserHandle.getUserId(callingUid)) { 7768 if (perms != null) { 7769 for (GrantUri grantUri : perms.keySet()) { 7770 if (grantUri.sourceUserId == userId) { 7771 String authority = grantUri.uri.getAuthority(); 7772 if (authority.equals(cpi.authority)) { 7773 return null; 7774 } 7775 } 7776 } 7777 } 7778 } 7779 if (checkUser) { 7780 userId = handleIncomingUser(callingPid, callingUid, userId, 7781 false, true, "checkContentProviderPermissionLocked " + cpi.authority, null); 7782 } 7783 if (checkComponentPermission(cpi.readPermission, callingPid, callingUid, 7784 cpi.applicationInfo.uid, cpi.exported) 7785 == PackageManager.PERMISSION_GRANTED) { 7786 return null; 7787 } 7788 if (checkComponentPermission(cpi.writePermission, callingPid, callingUid, 7789 cpi.applicationInfo.uid, cpi.exported) 7790 == PackageManager.PERMISSION_GRANTED) { 7791 return null; 7792 } 7793 7794 PathPermission[] pps = cpi.pathPermissions; 7795 if (pps != null) { 7796 int i = pps.length; 7797 while (i > 0) { 7798 i--; 7799 PathPermission pp = pps[i]; 7800 if (checkComponentPermission(pp.getReadPermission(), callingPid, callingUid, 7801 cpi.applicationInfo.uid, cpi.exported) 7802 == PackageManager.PERMISSION_GRANTED) { 7803 return null; 7804 } 7805 if (checkComponentPermission(pp.getWritePermission(), callingPid, callingUid, 7806 cpi.applicationInfo.uid, cpi.exported) 7807 == PackageManager.PERMISSION_GRANTED) { 7808 return null; 7809 } 7810 } 7811 } 7812 7813 if (perms != null) { 7814 for (GrantUri grantUri : perms.keySet()) { 7815 if (grantUri.uri.getAuthority().equals(cpi.authority)) { 7816 return null; 7817 } 7818 } 7819 } 7820 7821 String msg; 7822 if (!cpi.exported) { 7823 msg = "Permission Denial: opening provider " + cpi.name 7824 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 7825 + ", uid=" + callingUid + ") that is not exported from uid " 7826 + cpi.applicationInfo.uid; 7827 } else { 7828 msg = "Permission Denial: opening provider " + cpi.name 7829 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 7830 + ", uid=" + callingUid + ") requires " 7831 + cpi.readPermission + " or " + cpi.writePermission; 7832 } 7833 Slog.w(TAG, msg); 7834 return msg; 7835 } 7836 7837 ContentProviderConnection incProviderCountLocked(ProcessRecord r, 7838 final ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 7839 if (r != null) { 7840 for (int i=0; i<r.conProviders.size(); i++) { 7841 ContentProviderConnection conn = r.conProviders.get(i); 7842 if (conn.provider == cpr) { 7843 if (DEBUG_PROVIDER) Slog.v(TAG, 7844 "Adding provider requested by " 7845 + r.processName + " from process " 7846 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 7847 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 7848 if (stable) { 7849 conn.stableCount++; 7850 conn.numStableIncs++; 7851 } else { 7852 conn.unstableCount++; 7853 conn.numUnstableIncs++; 7854 } 7855 return conn; 7856 } 7857 } 7858 ContentProviderConnection conn = new ContentProviderConnection(cpr, r); 7859 if (stable) { 7860 conn.stableCount = 1; 7861 conn.numStableIncs = 1; 7862 } else { 7863 conn.unstableCount = 1; 7864 conn.numUnstableIncs = 1; 7865 } 7866 cpr.connections.add(conn); 7867 r.conProviders.add(conn); 7868 return conn; 7869 } 7870 cpr.addExternalProcessHandleLocked(externalProcessToken); 7871 return null; 7872 } 7873 7874 boolean decProviderCountLocked(ContentProviderConnection conn, 7875 ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 7876 if (conn != null) { 7877 cpr = conn.provider; 7878 if (DEBUG_PROVIDER) Slog.v(TAG, 7879 "Removing provider requested by " 7880 + conn.client.processName + " from process " 7881 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 7882 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 7883 if (stable) { 7884 conn.stableCount--; 7885 } else { 7886 conn.unstableCount--; 7887 } 7888 if (conn.stableCount == 0 && conn.unstableCount == 0) { 7889 cpr.connections.remove(conn); 7890 conn.client.conProviders.remove(conn); 7891 return true; 7892 } 7893 return false; 7894 } 7895 cpr.removeExternalProcessHandleLocked(externalProcessToken); 7896 return false; 7897 } 7898 7899 private final ContentProviderHolder getContentProviderImpl(IApplicationThread caller, 7900 String name, IBinder token, boolean stable, int userId) { 7901 ContentProviderRecord cpr; 7902 ContentProviderConnection conn = null; 7903 ProviderInfo cpi = null; 7904 7905 synchronized(this) { 7906 ProcessRecord r = null; 7907 if (caller != null) { 7908 r = getRecordForAppLocked(caller); 7909 if (r == null) { 7910 throw new SecurityException( 7911 "Unable to find app for caller " + caller 7912 + " (pid=" + Binder.getCallingPid() 7913 + ") when getting content provider " + name); 7914 } 7915 } 7916 7917 boolean checkCrossUser = true; 7918 7919 // First check if this content provider has been published... 7920 cpr = mProviderMap.getProviderByName(name, userId); 7921 // If that didn't work, check if it exists for user 0 and then 7922 // verify that it's a singleton provider before using it. 7923 if (cpr == null && userId != UserHandle.USER_OWNER) { 7924 cpr = mProviderMap.getProviderByName(name, UserHandle.USER_OWNER); 7925 if (cpr != null) { 7926 cpi = cpr.info; 7927 if (isSingleton(cpi.processName, cpi.applicationInfo, 7928 cpi.name, cpi.flags) 7929 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid)) { 7930 userId = UserHandle.USER_OWNER; 7931 checkCrossUser = false; 7932 } else { 7933 cpr = null; 7934 cpi = null; 7935 } 7936 } 7937 } 7938 7939 boolean providerRunning = cpr != null; 7940 if (providerRunning) { 7941 cpi = cpr.info; 7942 String msg; 7943 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, checkCrossUser)) 7944 != null) { 7945 throw new SecurityException(msg); 7946 } 7947 7948 if (r != null && cpr.canRunHere(r)) { 7949 // This provider has been published or is in the process 7950 // of being published... but it is also allowed to run 7951 // in the caller's process, so don't make a connection 7952 // and just let the caller instantiate its own instance. 7953 ContentProviderHolder holder = cpr.newHolder(null); 7954 // don't give caller the provider object, it needs 7955 // to make its own. 7956 holder.provider = null; 7957 return holder; 7958 } 7959 7960 final long origId = Binder.clearCallingIdentity(); 7961 7962 // In this case the provider instance already exists, so we can 7963 // return it right away. 7964 conn = incProviderCountLocked(r, cpr, token, stable); 7965 if (conn != null && (conn.stableCount+conn.unstableCount) == 1) { 7966 if (cpr.proc != null && r.setAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 7967 // If this is a perceptible app accessing the provider, 7968 // make sure to count it as being accessed and thus 7969 // back up on the LRU list. This is good because 7970 // content providers are often expensive to start. 7971 updateLruProcessLocked(cpr.proc, false, null); 7972 } 7973 } 7974 7975 if (cpr.proc != null) { 7976 if (false) { 7977 if (cpr.name.flattenToShortString().equals( 7978 "com.android.providers.calendar/.CalendarProvider2")) { 7979 Slog.v(TAG, "****************** KILLING " 7980 + cpr.name.flattenToShortString()); 7981 Process.killProcess(cpr.proc.pid); 7982 } 7983 } 7984 boolean success = updateOomAdjLocked(cpr.proc); 7985 if (DEBUG_PROVIDER) Slog.i(TAG, "Adjust success: " + success); 7986 // NOTE: there is still a race here where a signal could be 7987 // pending on the process even though we managed to update its 7988 // adj level. Not sure what to do about this, but at least 7989 // the race is now smaller. 7990 if (!success) { 7991 // Uh oh... it looks like the provider's process 7992 // has been killed on us. We need to wait for a new 7993 // process to be started, and make sure its death 7994 // doesn't kill our process. 7995 Slog.i(TAG, 7996 "Existing provider " + cpr.name.flattenToShortString() 7997 + " is crashing; detaching " + r); 7998 boolean lastRef = decProviderCountLocked(conn, cpr, token, stable); 7999 appDiedLocked(cpr.proc, cpr.proc.pid, cpr.proc.thread); 8000 if (!lastRef) { 8001 // This wasn't the last ref our process had on 8002 // the provider... we have now been killed, bail. 8003 return null; 8004 } 8005 providerRunning = false; 8006 conn = null; 8007 } 8008 } 8009 8010 Binder.restoreCallingIdentity(origId); 8011 } 8012 8013 boolean singleton; 8014 if (!providerRunning) { 8015 try { 8016 cpi = AppGlobals.getPackageManager(). 8017 resolveContentProvider(name, 8018 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS, userId); 8019 } catch (RemoteException ex) { 8020 } 8021 if (cpi == null) { 8022 return null; 8023 } 8024 // If the provider is a singleton AND 8025 // (it's a call within the same user || the provider is a 8026 // privileged app) 8027 // Then allow connecting to the singleton provider 8028 singleton = isSingleton(cpi.processName, cpi.applicationInfo, 8029 cpi.name, cpi.flags) 8030 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid); 8031 if (singleton) { 8032 userId = UserHandle.USER_OWNER; 8033 } 8034 cpi.applicationInfo = getAppInfoForUser(cpi.applicationInfo, userId); 8035 8036 String msg; 8037 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, !singleton)) 8038 != null) { 8039 throw new SecurityException(msg); 8040 } 8041 8042 if (!mProcessesReady && !mDidUpdate && !mWaitingUpdate 8043 && !cpi.processName.equals("system")) { 8044 // If this content provider does not run in the system 8045 // process, and the system is not yet ready to run other 8046 // processes, then fail fast instead of hanging. 8047 throw new IllegalArgumentException( 8048 "Attempt to launch content provider before system ready"); 8049 } 8050 8051 // Make sure that the user who owns this provider is started. If not, 8052 // we don't want to allow it to run. 8053 if (mStartedUsers.get(userId) == null) { 8054 Slog.w(TAG, "Unable to launch app " 8055 + cpi.applicationInfo.packageName + "/" 8056 + cpi.applicationInfo.uid + " for provider " 8057 + name + ": user " + userId + " is stopped"); 8058 return null; 8059 } 8060 8061 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 8062 cpr = mProviderMap.getProviderByClass(comp, userId); 8063 final boolean firstClass = cpr == null; 8064 if (firstClass) { 8065 try { 8066 ApplicationInfo ai = 8067 AppGlobals.getPackageManager(). 8068 getApplicationInfo( 8069 cpi.applicationInfo.packageName, 8070 STOCK_PM_FLAGS, userId); 8071 if (ai == null) { 8072 Slog.w(TAG, "No package info for content provider " 8073 + cpi.name); 8074 return null; 8075 } 8076 ai = getAppInfoForUser(ai, userId); 8077 cpr = new ContentProviderRecord(this, cpi, ai, comp, singleton); 8078 } catch (RemoteException ex) { 8079 // pm is in same process, this will never happen. 8080 } 8081 } 8082 8083 if (r != null && cpr.canRunHere(r)) { 8084 // If this is a multiprocess provider, then just return its 8085 // info and allow the caller to instantiate it. Only do 8086 // this if the provider is the same user as the caller's 8087 // process, or can run as root (so can be in any process). 8088 return cpr.newHolder(null); 8089 } 8090 8091 if (DEBUG_PROVIDER) { 8092 RuntimeException e = new RuntimeException("here"); 8093 Slog.w(TAG, "LAUNCHING REMOTE PROVIDER (myuid " + (r != null ? r.uid : null) 8094 + " pruid " + cpr.appInfo.uid + "): " + cpr.info.name, e); 8095 } 8096 8097 // This is single process, and our app is now connecting to it. 8098 // See if we are already in the process of launching this 8099 // provider. 8100 final int N = mLaunchingProviders.size(); 8101 int i; 8102 for (i=0; i<N; i++) { 8103 if (mLaunchingProviders.get(i) == cpr) { 8104 break; 8105 } 8106 } 8107 8108 // If the provider is not already being launched, then get it 8109 // started. 8110 if (i >= N) { 8111 final long origId = Binder.clearCallingIdentity(); 8112 8113 try { 8114 // Content provider is now in use, its package can't be stopped. 8115 try { 8116 AppGlobals.getPackageManager().setPackageStoppedState( 8117 cpr.appInfo.packageName, false, userId); 8118 } catch (RemoteException e) { 8119 } catch (IllegalArgumentException e) { 8120 Slog.w(TAG, "Failed trying to unstop package " 8121 + cpr.appInfo.packageName + ": " + e); 8122 } 8123 8124 // Use existing process if already started 8125 ProcessRecord proc = getProcessRecordLocked( 8126 cpi.processName, cpr.appInfo.uid, false); 8127 if (proc != null && proc.thread != null) { 8128 if (DEBUG_PROVIDER) { 8129 Slog.d(TAG, "Installing in existing process " + proc); 8130 } 8131 proc.pubProviders.put(cpi.name, cpr); 8132 try { 8133 proc.thread.scheduleInstallProvider(cpi); 8134 } catch (RemoteException e) { 8135 } 8136 } else { 8137 proc = startProcessLocked(cpi.processName, 8138 cpr.appInfo, false, 0, "content provider", 8139 new ComponentName(cpi.applicationInfo.packageName, 8140 cpi.name), false, false, false); 8141 if (proc == null) { 8142 Slog.w(TAG, "Unable to launch app " 8143 + cpi.applicationInfo.packageName + "/" 8144 + cpi.applicationInfo.uid + " for provider " 8145 + name + ": process is bad"); 8146 return null; 8147 } 8148 } 8149 cpr.launchingApp = proc; 8150 mLaunchingProviders.add(cpr); 8151 } finally { 8152 Binder.restoreCallingIdentity(origId); 8153 } 8154 } 8155 8156 // Make sure the provider is published (the same provider class 8157 // may be published under multiple names). 8158 if (firstClass) { 8159 mProviderMap.putProviderByClass(comp, cpr); 8160 } 8161 8162 mProviderMap.putProviderByName(name, cpr); 8163 conn = incProviderCountLocked(r, cpr, token, stable); 8164 if (conn != null) { 8165 conn.waiting = true; 8166 } 8167 } 8168 } 8169 8170 // Wait for the provider to be published... 8171 synchronized (cpr) { 8172 while (cpr.provider == null) { 8173 if (cpr.launchingApp == null) { 8174 Slog.w(TAG, "Unable to launch app " 8175 + cpi.applicationInfo.packageName + "/" 8176 + cpi.applicationInfo.uid + " for provider " 8177 + name + ": launching app became null"); 8178 EventLog.writeEvent(EventLogTags.AM_PROVIDER_LOST_PROCESS, 8179 UserHandle.getUserId(cpi.applicationInfo.uid), 8180 cpi.applicationInfo.packageName, 8181 cpi.applicationInfo.uid, name); 8182 return null; 8183 } 8184 try { 8185 if (DEBUG_MU) { 8186 Slog.v(TAG_MU, "Waiting to start provider " + cpr + " launchingApp=" 8187 + cpr.launchingApp); 8188 } 8189 if (conn != null) { 8190 conn.waiting = true; 8191 } 8192 cpr.wait(); 8193 } catch (InterruptedException ex) { 8194 } finally { 8195 if (conn != null) { 8196 conn.waiting = false; 8197 } 8198 } 8199 } 8200 } 8201 return cpr != null ? cpr.newHolder(conn) : null; 8202 } 8203 8204 @Override 8205 public final ContentProviderHolder getContentProvider( 8206 IApplicationThread caller, String name, int userId, boolean stable) { 8207 enforceNotIsolatedCaller("getContentProvider"); 8208 if (caller == null) { 8209 String msg = "null IApplicationThread when getting content provider " 8210 + name; 8211 Slog.w(TAG, msg); 8212 throw new SecurityException(msg); 8213 } 8214 // The incoming user check is now handled in checkContentProviderPermissionLocked() to deal 8215 // with cross-user grant. 8216 return getContentProviderImpl(caller, name, null, stable, userId); 8217 } 8218 8219 public ContentProviderHolder getContentProviderExternal( 8220 String name, int userId, IBinder token) { 8221 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 8222 "Do not have permission in call getContentProviderExternal()"); 8223 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 8224 false, true, "getContentProvider", null); 8225 return getContentProviderExternalUnchecked(name, token, userId); 8226 } 8227 8228 private ContentProviderHolder getContentProviderExternalUnchecked(String name, 8229 IBinder token, int userId) { 8230 return getContentProviderImpl(null, name, token, true, userId); 8231 } 8232 8233 /** 8234 * Drop a content provider from a ProcessRecord's bookkeeping 8235 */ 8236 public void removeContentProvider(IBinder connection, boolean stable) { 8237 enforceNotIsolatedCaller("removeContentProvider"); 8238 long ident = Binder.clearCallingIdentity(); 8239 try { 8240 synchronized (this) { 8241 ContentProviderConnection conn; 8242 try { 8243 conn = (ContentProviderConnection)connection; 8244 } catch (ClassCastException e) { 8245 String msg ="removeContentProvider: " + connection 8246 + " not a ContentProviderConnection"; 8247 Slog.w(TAG, msg); 8248 throw new IllegalArgumentException(msg); 8249 } 8250 if (conn == null) { 8251 throw new NullPointerException("connection is null"); 8252 } 8253 if (decProviderCountLocked(conn, null, null, stable)) { 8254 updateOomAdjLocked(); 8255 } 8256 } 8257 } finally { 8258 Binder.restoreCallingIdentity(ident); 8259 } 8260 } 8261 8262 public void removeContentProviderExternal(String name, IBinder token) { 8263 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 8264 "Do not have permission in call removeContentProviderExternal()"); 8265 removeContentProviderExternalUnchecked(name, token, UserHandle.getCallingUserId()); 8266 } 8267 8268 private void removeContentProviderExternalUnchecked(String name, IBinder token, int userId) { 8269 synchronized (this) { 8270 ContentProviderRecord cpr = mProviderMap.getProviderByName(name, userId); 8271 if(cpr == null) { 8272 //remove from mProvidersByClass 8273 if(localLOGV) Slog.v(TAG, name+" content provider not found in providers list"); 8274 return; 8275 } 8276 8277 //update content provider record entry info 8278 ComponentName comp = new ComponentName(cpr.info.packageName, cpr.info.name); 8279 ContentProviderRecord localCpr = mProviderMap.getProviderByClass(comp, userId); 8280 if (localCpr.hasExternalProcessHandles()) { 8281 if (localCpr.removeExternalProcessHandleLocked(token)) { 8282 updateOomAdjLocked(); 8283 } else { 8284 Slog.e(TAG, "Attmpt to remove content provider " + localCpr 8285 + " with no external reference for token: " 8286 + token + "."); 8287 } 8288 } else { 8289 Slog.e(TAG, "Attmpt to remove content provider: " + localCpr 8290 + " with no external references."); 8291 } 8292 } 8293 } 8294 8295 public final void publishContentProviders(IApplicationThread caller, 8296 List<ContentProviderHolder> providers) { 8297 if (providers == null) { 8298 return; 8299 } 8300 8301 enforceNotIsolatedCaller("publishContentProviders"); 8302 synchronized (this) { 8303 final ProcessRecord r = getRecordForAppLocked(caller); 8304 if (DEBUG_MU) 8305 Slog.v(TAG_MU, "ProcessRecord uid = " + r.uid); 8306 if (r == null) { 8307 throw new SecurityException( 8308 "Unable to find app for caller " + caller 8309 + " (pid=" + Binder.getCallingPid() 8310 + ") when publishing content providers"); 8311 } 8312 8313 final long origId = Binder.clearCallingIdentity(); 8314 8315 final int N = providers.size(); 8316 for (int i=0; i<N; i++) { 8317 ContentProviderHolder src = providers.get(i); 8318 if (src == null || src.info == null || src.provider == null) { 8319 continue; 8320 } 8321 ContentProviderRecord dst = r.pubProviders.get(src.info.name); 8322 if (DEBUG_MU) 8323 Slog.v(TAG_MU, "ContentProviderRecord uid = " + dst.uid); 8324 if (dst != null) { 8325 ComponentName comp = new ComponentName(dst.info.packageName, dst.info.name); 8326 mProviderMap.putProviderByClass(comp, dst); 8327 String names[] = dst.info.authority.split(";"); 8328 for (int j = 0; j < names.length; j++) { 8329 mProviderMap.putProviderByName(names[j], dst); 8330 } 8331 8332 int NL = mLaunchingProviders.size(); 8333 int j; 8334 for (j=0; j<NL; j++) { 8335 if (mLaunchingProviders.get(j) == dst) { 8336 mLaunchingProviders.remove(j); 8337 j--; 8338 NL--; 8339 } 8340 } 8341 synchronized (dst) { 8342 dst.provider = src.provider; 8343 dst.proc = r; 8344 dst.notifyAll(); 8345 } 8346 updateOomAdjLocked(r); 8347 } 8348 } 8349 8350 Binder.restoreCallingIdentity(origId); 8351 } 8352 } 8353 8354 public boolean refContentProvider(IBinder connection, int stable, int unstable) { 8355 ContentProviderConnection conn; 8356 try { 8357 conn = (ContentProviderConnection)connection; 8358 } catch (ClassCastException e) { 8359 String msg ="refContentProvider: " + connection 8360 + " not a ContentProviderConnection"; 8361 Slog.w(TAG, msg); 8362 throw new IllegalArgumentException(msg); 8363 } 8364 if (conn == null) { 8365 throw new NullPointerException("connection is null"); 8366 } 8367 8368 synchronized (this) { 8369 if (stable > 0) { 8370 conn.numStableIncs += stable; 8371 } 8372 stable = conn.stableCount + stable; 8373 if (stable < 0) { 8374 throw new IllegalStateException("stableCount < 0: " + stable); 8375 } 8376 8377 if (unstable > 0) { 8378 conn.numUnstableIncs += unstable; 8379 } 8380 unstable = conn.unstableCount + unstable; 8381 if (unstable < 0) { 8382 throw new IllegalStateException("unstableCount < 0: " + unstable); 8383 } 8384 8385 if ((stable+unstable) <= 0) { 8386 throw new IllegalStateException("ref counts can't go to zero here: stable=" 8387 + stable + " unstable=" + unstable); 8388 } 8389 conn.stableCount = stable; 8390 conn.unstableCount = unstable; 8391 return !conn.dead; 8392 } 8393 } 8394 8395 public void unstableProviderDied(IBinder connection) { 8396 ContentProviderConnection conn; 8397 try { 8398 conn = (ContentProviderConnection)connection; 8399 } catch (ClassCastException e) { 8400 String msg ="refContentProvider: " + connection 8401 + " not a ContentProviderConnection"; 8402 Slog.w(TAG, msg); 8403 throw new IllegalArgumentException(msg); 8404 } 8405 if (conn == null) { 8406 throw new NullPointerException("connection is null"); 8407 } 8408 8409 // Safely retrieve the content provider associated with the connection. 8410 IContentProvider provider; 8411 synchronized (this) { 8412 provider = conn.provider.provider; 8413 } 8414 8415 if (provider == null) { 8416 // Um, yeah, we're way ahead of you. 8417 return; 8418 } 8419 8420 // Make sure the caller is being honest with us. 8421 if (provider.asBinder().pingBinder()) { 8422 // Er, no, still looks good to us. 8423 synchronized (this) { 8424 Slog.w(TAG, "unstableProviderDied: caller " + Binder.getCallingUid() 8425 + " says " + conn + " died, but we don't agree"); 8426 return; 8427 } 8428 } 8429 8430 // Well look at that! It's dead! 8431 synchronized (this) { 8432 if (conn.provider.provider != provider) { 8433 // But something changed... good enough. 8434 return; 8435 } 8436 8437 ProcessRecord proc = conn.provider.proc; 8438 if (proc == null || proc.thread == null) { 8439 // Seems like the process is already cleaned up. 8440 return; 8441 } 8442 8443 // As far as we're concerned, this is just like receiving a 8444 // death notification... just a bit prematurely. 8445 Slog.i(TAG, "Process " + proc.processName + " (pid " + proc.pid 8446 + ") early provider death"); 8447 final long ident = Binder.clearCallingIdentity(); 8448 try { 8449 appDiedLocked(proc, proc.pid, proc.thread); 8450 } finally { 8451 Binder.restoreCallingIdentity(ident); 8452 } 8453 } 8454 } 8455 8456 @Override 8457 public void appNotRespondingViaProvider(IBinder connection) { 8458 enforceCallingPermission( 8459 android.Manifest.permission.REMOVE_TASKS, "appNotRespondingViaProvider()"); 8460 8461 final ContentProviderConnection conn = (ContentProviderConnection) connection; 8462 if (conn == null) { 8463 Slog.w(TAG, "ContentProviderConnection is null"); 8464 return; 8465 } 8466 8467 final ProcessRecord host = conn.provider.proc; 8468 if (host == null) { 8469 Slog.w(TAG, "Failed to find hosting ProcessRecord"); 8470 return; 8471 } 8472 8473 final long token = Binder.clearCallingIdentity(); 8474 try { 8475 appNotResponding(host, null, null, false, "ContentProvider not responding"); 8476 } finally { 8477 Binder.restoreCallingIdentity(token); 8478 } 8479 } 8480 8481 public final void installSystemProviders() { 8482 List<ProviderInfo> providers; 8483 synchronized (this) { 8484 ProcessRecord app = mProcessNames.get("system", Process.SYSTEM_UID); 8485 providers = generateApplicationProvidersLocked(app); 8486 if (providers != null) { 8487 for (int i=providers.size()-1; i>=0; i--) { 8488 ProviderInfo pi = (ProviderInfo)providers.get(i); 8489 if ((pi.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) == 0) { 8490 Slog.w(TAG, "Not installing system proc provider " + pi.name 8491 + ": not system .apk"); 8492 providers.remove(i); 8493 } 8494 } 8495 } 8496 } 8497 if (providers != null) { 8498 mSystemThread.installSystemProviders(providers); 8499 } 8500 8501 mCoreSettingsObserver = new CoreSettingsObserver(this); 8502 8503 mUsageStatsService.monitorPackages(); 8504 } 8505 8506 /** 8507 * Allows app to retrieve the MIME type of a URI without having permission 8508 * to access its content provider. 8509 * 8510 * CTS tests for this functionality can be run with "runtest cts-appsecurity". 8511 * 8512 * Test cases are at cts/tests/appsecurity-tests/test-apps/UsePermissionDiffCert/ 8513 * src/com/android/cts/usespermissiondiffcertapp/AccessPermissionWithDiffSigTest.java 8514 */ 8515 public String getProviderMimeType(Uri uri, int userId) { 8516 enforceNotIsolatedCaller("getProviderMimeType"); 8517 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 8518 userId, false, true, "getProviderMimeType", null); 8519 final String name = uri.getAuthority(); 8520 final long ident = Binder.clearCallingIdentity(); 8521 ContentProviderHolder holder = null; 8522 8523 try { 8524 holder = getContentProviderExternalUnchecked(name, null, userId); 8525 if (holder != null) { 8526 return holder.provider.getType(uri); 8527 } 8528 } catch (RemoteException e) { 8529 Log.w(TAG, "Content provider dead retrieving " + uri, e); 8530 return null; 8531 } finally { 8532 if (holder != null) { 8533 removeContentProviderExternalUnchecked(name, null, userId); 8534 } 8535 Binder.restoreCallingIdentity(ident); 8536 } 8537 8538 return null; 8539 } 8540 8541 // ========================================================= 8542 // GLOBAL MANAGEMENT 8543 // ========================================================= 8544 8545 final ProcessRecord newProcessRecordLocked(ApplicationInfo info, String customProcess, 8546 boolean isolated) { 8547 String proc = customProcess != null ? customProcess : info.processName; 8548 BatteryStatsImpl.Uid.Proc ps = null; 8549 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 8550 int uid = info.uid; 8551 if (isolated) { 8552 int userId = UserHandle.getUserId(uid); 8553 int stepsLeft = Process.LAST_ISOLATED_UID - Process.FIRST_ISOLATED_UID + 1; 8554 while (true) { 8555 if (mNextIsolatedProcessUid < Process.FIRST_ISOLATED_UID 8556 || mNextIsolatedProcessUid > Process.LAST_ISOLATED_UID) { 8557 mNextIsolatedProcessUid = Process.FIRST_ISOLATED_UID; 8558 } 8559 uid = UserHandle.getUid(userId, mNextIsolatedProcessUid); 8560 mNextIsolatedProcessUid++; 8561 if (mIsolatedProcesses.indexOfKey(uid) < 0) { 8562 // No process for this uid, use it. 8563 break; 8564 } 8565 stepsLeft--; 8566 if (stepsLeft <= 0) { 8567 return null; 8568 } 8569 } 8570 } 8571 return new ProcessRecord(stats, info, proc, uid); 8572 } 8573 8574 final ProcessRecord addAppLocked(ApplicationInfo info, boolean isolated, 8575 String abiOverride) { 8576 ProcessRecord app; 8577 if (!isolated) { 8578 app = getProcessRecordLocked(info.processName, info.uid, true); 8579 } else { 8580 app = null; 8581 } 8582 8583 if (app == null) { 8584 app = newProcessRecordLocked(info, null, isolated); 8585 mProcessNames.put(info.processName, app.uid, app); 8586 if (isolated) { 8587 mIsolatedProcesses.put(app.uid, app); 8588 } 8589 updateLruProcessLocked(app, false, null); 8590 updateOomAdjLocked(); 8591 } 8592 8593 // This package really, really can not be stopped. 8594 try { 8595 AppGlobals.getPackageManager().setPackageStoppedState( 8596 info.packageName, false, UserHandle.getUserId(app.uid)); 8597 } catch (RemoteException e) { 8598 } catch (IllegalArgumentException e) { 8599 Slog.w(TAG, "Failed trying to unstop package " 8600 + info.packageName + ": " + e); 8601 } 8602 8603 if ((info.flags&(ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) 8604 == (ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) { 8605 app.persistent = true; 8606 app.maxAdj = ProcessList.PERSISTENT_PROC_ADJ; 8607 } 8608 if (app.thread == null && mPersistentStartingProcesses.indexOf(app) < 0) { 8609 mPersistentStartingProcesses.add(app); 8610 startProcessLocked(app, "added application", app.processName, 8611 abiOverride); 8612 } 8613 8614 return app; 8615 } 8616 8617 public void unhandledBack() { 8618 enforceCallingPermission(android.Manifest.permission.FORCE_BACK, 8619 "unhandledBack()"); 8620 8621 synchronized(this) { 8622 final long origId = Binder.clearCallingIdentity(); 8623 try { 8624 getFocusedStack().unhandledBackLocked(); 8625 } finally { 8626 Binder.restoreCallingIdentity(origId); 8627 } 8628 } 8629 } 8630 8631 public ParcelFileDescriptor openContentUri(Uri uri) throws RemoteException { 8632 enforceNotIsolatedCaller("openContentUri"); 8633 final int userId = UserHandle.getCallingUserId(); 8634 String name = uri.getAuthority(); 8635 ContentProviderHolder cph = getContentProviderExternalUnchecked(name, null, userId); 8636 ParcelFileDescriptor pfd = null; 8637 if (cph != null) { 8638 // We record the binder invoker's uid in thread-local storage before 8639 // going to the content provider to open the file. Later, in the code 8640 // that handles all permissions checks, we look for this uid and use 8641 // that rather than the Activity Manager's own uid. The effect is that 8642 // we do the check against the caller's permissions even though it looks 8643 // to the content provider like the Activity Manager itself is making 8644 // the request. 8645 sCallerIdentity.set(new Identity( 8646 Binder.getCallingPid(), Binder.getCallingUid())); 8647 try { 8648 pfd = cph.provider.openFile(null, uri, "r", null); 8649 } catch (FileNotFoundException e) { 8650 // do nothing; pfd will be returned null 8651 } finally { 8652 // Ensure that whatever happens, we clean up the identity state 8653 sCallerIdentity.remove(); 8654 } 8655 8656 // We've got the fd now, so we're done with the provider. 8657 removeContentProviderExternalUnchecked(name, null, userId); 8658 } else { 8659 Slog.d(TAG, "Failed to get provider for authority '" + name + "'"); 8660 } 8661 return pfd; 8662 } 8663 8664 // Actually is sleeping or shutting down or whatever else in the future 8665 // is an inactive state. 8666 public boolean isSleepingOrShuttingDown() { 8667 return mSleeping || mShuttingDown; 8668 } 8669 8670 public boolean isSleeping() { 8671 return mSleeping; 8672 } 8673 8674 void goingToSleep() { 8675 synchronized(this) { 8676 mWentToSleep = true; 8677 updateEventDispatchingLocked(); 8678 goToSleepIfNeededLocked(); 8679 } 8680 } 8681 8682 void finishRunningVoiceLocked() { 8683 if (mRunningVoice) { 8684 mRunningVoice = false; 8685 goToSleepIfNeededLocked(); 8686 } 8687 } 8688 8689 void goToSleepIfNeededLocked() { 8690 if (mWentToSleep && !mRunningVoice) { 8691 if (!mSleeping) { 8692 mSleeping = true; 8693 mStackSupervisor.goingToSleepLocked(); 8694 8695 // Initialize the wake times of all processes. 8696 checkExcessivePowerUsageLocked(false); 8697 mHandler.removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 8698 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 8699 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 8700 } 8701 } 8702 } 8703 8704 void notifyTaskPersisterLocked(TaskRecord task, boolean flush) { 8705 mTaskPersister.notify(task, flush); 8706 } 8707 8708 @Override 8709 public boolean shutdown(int timeout) { 8710 if (checkCallingPermission(android.Manifest.permission.SHUTDOWN) 8711 != PackageManager.PERMISSION_GRANTED) { 8712 throw new SecurityException("Requires permission " 8713 + android.Manifest.permission.SHUTDOWN); 8714 } 8715 8716 boolean timedout = false; 8717 8718 synchronized(this) { 8719 mShuttingDown = true; 8720 updateEventDispatchingLocked(); 8721 timedout = mStackSupervisor.shutdownLocked(timeout); 8722 } 8723 8724 mAppOpsService.shutdown(); 8725 mUsageStatsService.shutdown(); 8726 mBatteryStatsService.shutdown(); 8727 synchronized (this) { 8728 mProcessStats.shutdownLocked(); 8729 } 8730 notifyTaskPersisterLocked(null, true); 8731 8732 return timedout; 8733 } 8734 8735 public final void activitySlept(IBinder token) { 8736 if (localLOGV) Slog.v(TAG, "Activity slept: token=" + token); 8737 8738 final long origId = Binder.clearCallingIdentity(); 8739 8740 synchronized (this) { 8741 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 8742 if (r != null) { 8743 mStackSupervisor.activitySleptLocked(r); 8744 } 8745 } 8746 8747 Binder.restoreCallingIdentity(origId); 8748 } 8749 8750 void logLockScreen(String msg) { 8751 if (DEBUG_LOCKSCREEN) Slog.d(TAG, Debug.getCallers(2) + ":" + msg + 8752 " mLockScreenShown=" + mLockScreenShown + " mWentToSleep=" + 8753 mWentToSleep + " mSleeping=" + mSleeping + " mDismissKeyguardOnNextActivity=" + 8754 mStackSupervisor.mDismissKeyguardOnNextActivity); 8755 } 8756 8757 private void comeOutOfSleepIfNeededLocked() { 8758 if ((!mWentToSleep && !mLockScreenShown) || mRunningVoice) { 8759 if (mSleeping) { 8760 mSleeping = false; 8761 mStackSupervisor.comeOutOfSleepIfNeededLocked(); 8762 } 8763 } 8764 } 8765 8766 void wakingUp() { 8767 synchronized(this) { 8768 mWentToSleep = false; 8769 updateEventDispatchingLocked(); 8770 comeOutOfSleepIfNeededLocked(); 8771 } 8772 } 8773 8774 void startRunningVoiceLocked() { 8775 if (!mRunningVoice) { 8776 mRunningVoice = true; 8777 comeOutOfSleepIfNeededLocked(); 8778 } 8779 } 8780 8781 private void updateEventDispatchingLocked() { 8782 mWindowManager.setEventDispatching(mBooted && !mWentToSleep && !mShuttingDown); 8783 } 8784 8785 public void setLockScreenShown(boolean shown) { 8786 if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER) 8787 != PackageManager.PERMISSION_GRANTED) { 8788 throw new SecurityException("Requires permission " 8789 + android.Manifest.permission.DEVICE_POWER); 8790 } 8791 8792 synchronized(this) { 8793 long ident = Binder.clearCallingIdentity(); 8794 try { 8795 if (DEBUG_LOCKSCREEN) logLockScreen(" shown=" + shown); 8796 mLockScreenShown = shown; 8797 comeOutOfSleepIfNeededLocked(); 8798 } finally { 8799 Binder.restoreCallingIdentity(ident); 8800 } 8801 } 8802 } 8803 8804 public void stopAppSwitches() { 8805 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 8806 != PackageManager.PERMISSION_GRANTED) { 8807 throw new SecurityException("Requires permission " 8808 + android.Manifest.permission.STOP_APP_SWITCHES); 8809 } 8810 8811 synchronized(this) { 8812 mAppSwitchesAllowedTime = SystemClock.uptimeMillis() 8813 + APP_SWITCH_DELAY_TIME; 8814 mDidAppSwitch = false; 8815 mHandler.removeMessages(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 8816 Message msg = mHandler.obtainMessage(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 8817 mHandler.sendMessageDelayed(msg, APP_SWITCH_DELAY_TIME); 8818 } 8819 } 8820 8821 public void resumeAppSwitches() { 8822 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 8823 != PackageManager.PERMISSION_GRANTED) { 8824 throw new SecurityException("Requires permission " 8825 + android.Manifest.permission.STOP_APP_SWITCHES); 8826 } 8827 8828 synchronized(this) { 8829 // Note that we don't execute any pending app switches... we will 8830 // let those wait until either the timeout, or the next start 8831 // activity request. 8832 mAppSwitchesAllowedTime = 0; 8833 } 8834 } 8835 8836 boolean checkAppSwitchAllowedLocked(int callingPid, int callingUid, 8837 String name) { 8838 if (mAppSwitchesAllowedTime < SystemClock.uptimeMillis()) { 8839 return true; 8840 } 8841 8842 final int perm = checkComponentPermission( 8843 android.Manifest.permission.STOP_APP_SWITCHES, callingPid, 8844 callingUid, -1, true); 8845 if (perm == PackageManager.PERMISSION_GRANTED) { 8846 return true; 8847 } 8848 8849 Slog.w(TAG, name + " request from " + callingUid + " stopped"); 8850 return false; 8851 } 8852 8853 public void setDebugApp(String packageName, boolean waitForDebugger, 8854 boolean persistent) { 8855 enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP, 8856 "setDebugApp()"); 8857 8858 long ident = Binder.clearCallingIdentity(); 8859 try { 8860 // Note that this is not really thread safe if there are multiple 8861 // callers into it at the same time, but that's not a situation we 8862 // care about. 8863 if (persistent) { 8864 final ContentResolver resolver = mContext.getContentResolver(); 8865 Settings.Global.putString( 8866 resolver, Settings.Global.DEBUG_APP, 8867 packageName); 8868 Settings.Global.putInt( 8869 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 8870 waitForDebugger ? 1 : 0); 8871 } 8872 8873 synchronized (this) { 8874 if (!persistent) { 8875 mOrigDebugApp = mDebugApp; 8876 mOrigWaitForDebugger = mWaitForDebugger; 8877 } 8878 mDebugApp = packageName; 8879 mWaitForDebugger = waitForDebugger; 8880 mDebugTransient = !persistent; 8881 if (packageName != null) { 8882 forceStopPackageLocked(packageName, -1, false, false, true, true, 8883 false, UserHandle.USER_ALL, "set debug app"); 8884 } 8885 } 8886 } finally { 8887 Binder.restoreCallingIdentity(ident); 8888 } 8889 } 8890 8891 void setOpenGlTraceApp(ApplicationInfo app, String processName) { 8892 synchronized (this) { 8893 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 8894 if (!isDebuggable) { 8895 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 8896 throw new SecurityException("Process not debuggable: " + app.packageName); 8897 } 8898 } 8899 8900 mOpenGlTraceApp = processName; 8901 } 8902 } 8903 8904 void setProfileApp(ApplicationInfo app, String processName, String profileFile, 8905 ParcelFileDescriptor profileFd, boolean autoStopProfiler) { 8906 synchronized (this) { 8907 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 8908 if (!isDebuggable) { 8909 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 8910 throw new SecurityException("Process not debuggable: " + app.packageName); 8911 } 8912 } 8913 mProfileApp = processName; 8914 mProfileFile = profileFile; 8915 if (mProfileFd != null) { 8916 try { 8917 mProfileFd.close(); 8918 } catch (IOException e) { 8919 } 8920 mProfileFd = null; 8921 } 8922 mProfileFd = profileFd; 8923 mProfileType = 0; 8924 mAutoStopProfiler = autoStopProfiler; 8925 } 8926 } 8927 8928 @Override 8929 public void setAlwaysFinish(boolean enabled) { 8930 enforceCallingPermission(android.Manifest.permission.SET_ALWAYS_FINISH, 8931 "setAlwaysFinish()"); 8932 8933 Settings.Global.putInt( 8934 mContext.getContentResolver(), 8935 Settings.Global.ALWAYS_FINISH_ACTIVITIES, enabled ? 1 : 0); 8936 8937 synchronized (this) { 8938 mAlwaysFinishActivities = enabled; 8939 } 8940 } 8941 8942 @Override 8943 public void setActivityController(IActivityController controller) { 8944 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 8945 "setActivityController()"); 8946 synchronized (this) { 8947 mController = controller; 8948 Watchdog.getInstance().setActivityController(controller); 8949 } 8950 } 8951 8952 @Override 8953 public void setUserIsMonkey(boolean userIsMonkey) { 8954 synchronized (this) { 8955 synchronized (mPidsSelfLocked) { 8956 final int callingPid = Binder.getCallingPid(); 8957 ProcessRecord precessRecord = mPidsSelfLocked.get(callingPid); 8958 if (precessRecord == null) { 8959 throw new SecurityException("Unknown process: " + callingPid); 8960 } 8961 if (precessRecord.instrumentationUiAutomationConnection == null) { 8962 throw new SecurityException("Only an instrumentation process " 8963 + "with a UiAutomation can call setUserIsMonkey"); 8964 } 8965 } 8966 mUserIsMonkey = userIsMonkey; 8967 } 8968 } 8969 8970 @Override 8971 public boolean isUserAMonkey() { 8972 synchronized (this) { 8973 // If there is a controller also implies the user is a monkey. 8974 return (mUserIsMonkey || mController != null); 8975 } 8976 } 8977 8978 public void requestBugReport() { 8979 enforceCallingPermission(android.Manifest.permission.DUMP, "requestBugReport"); 8980 SystemProperties.set("ctl.start", "bugreport"); 8981 } 8982 8983 public static long getInputDispatchingTimeoutLocked(ActivityRecord r) { 8984 return r != null ? getInputDispatchingTimeoutLocked(r.app) : KEY_DISPATCHING_TIMEOUT; 8985 } 8986 8987 public static long getInputDispatchingTimeoutLocked(ProcessRecord r) { 8988 if (r != null && (r.instrumentationClass != null || r.usingWrapper)) { 8989 return INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT; 8990 } 8991 return KEY_DISPATCHING_TIMEOUT; 8992 } 8993 8994 @Override 8995 public long inputDispatchingTimedOut(int pid, final boolean aboveSystem, String reason) { 8996 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 8997 != PackageManager.PERMISSION_GRANTED) { 8998 throw new SecurityException("Requires permission " 8999 + android.Manifest.permission.FILTER_EVENTS); 9000 } 9001 ProcessRecord proc; 9002 long timeout; 9003 synchronized (this) { 9004 synchronized (mPidsSelfLocked) { 9005 proc = mPidsSelfLocked.get(pid); 9006 } 9007 timeout = getInputDispatchingTimeoutLocked(proc); 9008 } 9009 9010 if (!inputDispatchingTimedOut(proc, null, null, aboveSystem, reason)) { 9011 return -1; 9012 } 9013 9014 return timeout; 9015 } 9016 9017 /** 9018 * Handle input dispatching timeouts. 9019 * Returns whether input dispatching should be aborted or not. 9020 */ 9021 public boolean inputDispatchingTimedOut(final ProcessRecord proc, 9022 final ActivityRecord activity, final ActivityRecord parent, 9023 final boolean aboveSystem, String reason) { 9024 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 9025 != PackageManager.PERMISSION_GRANTED) { 9026 throw new SecurityException("Requires permission " 9027 + android.Manifest.permission.FILTER_EVENTS); 9028 } 9029 9030 final String annotation; 9031 if (reason == null) { 9032 annotation = "Input dispatching timed out"; 9033 } else { 9034 annotation = "Input dispatching timed out (" + reason + ")"; 9035 } 9036 9037 if (proc != null) { 9038 synchronized (this) { 9039 if (proc.debugging) { 9040 return false; 9041 } 9042 9043 if (mDidDexOpt) { 9044 // Give more time since we were dexopting. 9045 mDidDexOpt = false; 9046 return false; 9047 } 9048 9049 if (proc.instrumentationClass != null) { 9050 Bundle info = new Bundle(); 9051 info.putString("shortMsg", "keyDispatchingTimedOut"); 9052 info.putString("longMsg", annotation); 9053 finishInstrumentationLocked(proc, Activity.RESULT_CANCELED, info); 9054 return true; 9055 } 9056 } 9057 mHandler.post(new Runnable() { 9058 @Override 9059 public void run() { 9060 appNotResponding(proc, activity, parent, aboveSystem, annotation); 9061 } 9062 }); 9063 } 9064 9065 return true; 9066 } 9067 9068 public Bundle getAssistContextExtras(int requestType) { 9069 enforceCallingPermission(android.Manifest.permission.GET_TOP_ACTIVITY_INFO, 9070 "getAssistContextExtras()"); 9071 PendingAssistExtras pae; 9072 Bundle extras = new Bundle(); 9073 synchronized (this) { 9074 ActivityRecord activity = getFocusedStack().mResumedActivity; 9075 if (activity == null) { 9076 Slog.w(TAG, "getAssistContextExtras failed: no resumed activity"); 9077 return null; 9078 } 9079 extras.putString(Intent.EXTRA_ASSIST_PACKAGE, activity.packageName); 9080 if (activity.app == null || activity.app.thread == null) { 9081 Slog.w(TAG, "getAssistContextExtras failed: no process for " + activity); 9082 return extras; 9083 } 9084 if (activity.app.pid == Binder.getCallingPid()) { 9085 Slog.w(TAG, "getAssistContextExtras failed: request process same as " + activity); 9086 return extras; 9087 } 9088 pae = new PendingAssistExtras(activity); 9089 try { 9090 activity.app.thread.requestAssistContextExtras(activity.appToken, pae, 9091 requestType); 9092 mPendingAssistExtras.add(pae); 9093 mHandler.postDelayed(pae, PENDING_ASSIST_EXTRAS_TIMEOUT); 9094 } catch (RemoteException e) { 9095 Slog.w(TAG, "getAssistContextExtras failed: crash calling " + activity); 9096 return extras; 9097 } 9098 } 9099 synchronized (pae) { 9100 while (!pae.haveResult) { 9101 try { 9102 pae.wait(); 9103 } catch (InterruptedException e) { 9104 } 9105 } 9106 if (pae.result != null) { 9107 extras.putBundle(Intent.EXTRA_ASSIST_CONTEXT, pae.result); 9108 } 9109 } 9110 synchronized (this) { 9111 mPendingAssistExtras.remove(pae); 9112 mHandler.removeCallbacks(pae); 9113 } 9114 return extras; 9115 } 9116 9117 public void reportAssistContextExtras(IBinder token, Bundle extras) { 9118 PendingAssistExtras pae = (PendingAssistExtras)token; 9119 synchronized (pae) { 9120 pae.result = extras; 9121 pae.haveResult = true; 9122 pae.notifyAll(); 9123 } 9124 } 9125 9126 public void registerProcessObserver(IProcessObserver observer) { 9127 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 9128 "registerProcessObserver()"); 9129 synchronized (this) { 9130 mProcessObservers.register(observer); 9131 } 9132 } 9133 9134 @Override 9135 public void unregisterProcessObserver(IProcessObserver observer) { 9136 synchronized (this) { 9137 mProcessObservers.unregister(observer); 9138 } 9139 } 9140 9141 @Override 9142 public boolean convertFromTranslucent(IBinder token) { 9143 final long origId = Binder.clearCallingIdentity(); 9144 try { 9145 synchronized (this) { 9146 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9147 if (r == null) { 9148 return false; 9149 } 9150 if (r.changeWindowTranslucency(true)) { 9151 mWindowManager.setAppFullscreen(token, true); 9152 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9153 return true; 9154 } 9155 return false; 9156 } 9157 } finally { 9158 Binder.restoreCallingIdentity(origId); 9159 } 9160 } 9161 9162 @Override 9163 public boolean convertToTranslucent(IBinder token, ActivityOptions options) { 9164 final long origId = Binder.clearCallingIdentity(); 9165 try { 9166 synchronized (this) { 9167 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9168 if (r == null) { 9169 return false; 9170 } 9171 if (r.changeWindowTranslucency(false)) { 9172 r.task.stack.convertToTranslucent(r, options); 9173 mWindowManager.setAppFullscreen(token, false); 9174 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9175 return true; 9176 } 9177 return false; 9178 } 9179 } finally { 9180 Binder.restoreCallingIdentity(origId); 9181 } 9182 } 9183 9184 @Override 9185 public ActivityOptions getActivityOptions(IBinder token) { 9186 final long origId = Binder.clearCallingIdentity(); 9187 try { 9188 synchronized (this) { 9189 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9190 if (r != null) { 9191 final ActivityOptions activityOptions = r.pendingOptions; 9192 r.pendingOptions = null; 9193 return activityOptions; 9194 } 9195 return null; 9196 } 9197 } finally { 9198 Binder.restoreCallingIdentity(origId); 9199 } 9200 } 9201 9202 @Override 9203 public void setImmersive(IBinder token, boolean immersive) { 9204 synchronized(this) { 9205 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9206 if (r == null) { 9207 throw new IllegalArgumentException(); 9208 } 9209 r.immersive = immersive; 9210 9211 // update associated state if we're frontmost 9212 if (r == mFocusedActivity) { 9213 if (DEBUG_IMMERSIVE) { 9214 Slog.d(TAG, "Frontmost changed immersion: "+ r); 9215 } 9216 applyUpdateLockStateLocked(r); 9217 } 9218 } 9219 } 9220 9221 @Override 9222 public boolean isImmersive(IBinder token) { 9223 synchronized (this) { 9224 ActivityRecord r = ActivityRecord.isInStackLocked(token); 9225 if (r == null) { 9226 throw new IllegalArgumentException(); 9227 } 9228 return r.immersive; 9229 } 9230 } 9231 9232 public boolean isTopActivityImmersive() { 9233 enforceNotIsolatedCaller("startActivity"); 9234 synchronized (this) { 9235 ActivityRecord r = getFocusedStack().topRunningActivityLocked(null); 9236 return (r != null) ? r.immersive : false; 9237 } 9238 } 9239 9240 public final void enterSafeMode() { 9241 synchronized(this) { 9242 // It only makes sense to do this before the system is ready 9243 // and started launching other packages. 9244 if (!mSystemReady) { 9245 try { 9246 AppGlobals.getPackageManager().enterSafeMode(); 9247 } catch (RemoteException e) { 9248 } 9249 } 9250 9251 mSafeMode = true; 9252 } 9253 } 9254 9255 public final void showSafeModeOverlay() { 9256 View v = LayoutInflater.from(mContext).inflate( 9257 com.android.internal.R.layout.safe_mode, null); 9258 WindowManager.LayoutParams lp = new WindowManager.LayoutParams(); 9259 lp.type = WindowManager.LayoutParams.TYPE_SECURE_SYSTEM_OVERLAY; 9260 lp.width = WindowManager.LayoutParams.WRAP_CONTENT; 9261 lp.height = WindowManager.LayoutParams.WRAP_CONTENT; 9262 lp.gravity = Gravity.BOTTOM | Gravity.START; 9263 lp.format = v.getBackground().getOpacity(); 9264 lp.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE 9265 | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE; 9266 lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; 9267 ((WindowManager)mContext.getSystemService( 9268 Context.WINDOW_SERVICE)).addView(v, lp); 9269 } 9270 9271 public void noteWakeupAlarm(IIntentSender sender, int sourceUid, String sourcePkg) { 9272 if (!(sender instanceof PendingIntentRecord)) { 9273 return; 9274 } 9275 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 9276 synchronized (stats) { 9277 if (mBatteryStatsService.isOnBattery()) { 9278 mBatteryStatsService.enforceCallingPermission(); 9279 PendingIntentRecord rec = (PendingIntentRecord)sender; 9280 int MY_UID = Binder.getCallingUid(); 9281 int uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid; 9282 BatteryStatsImpl.Uid.Pkg pkg = 9283 stats.getPackageStatsLocked(sourceUid >= 0 ? sourceUid : uid, 9284 sourcePkg != null ? sourcePkg : rec.key.packageName); 9285 pkg.incWakeupsLocked(); 9286 } 9287 } 9288 } 9289 9290 public boolean killPids(int[] pids, String pReason, boolean secure) { 9291 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9292 throw new SecurityException("killPids only available to the system"); 9293 } 9294 String reason = (pReason == null) ? "Unknown" : pReason; 9295 // XXX Note: don't acquire main activity lock here, because the window 9296 // manager calls in with its locks held. 9297 9298 boolean killed = false; 9299 synchronized (mPidsSelfLocked) { 9300 int[] types = new int[pids.length]; 9301 int worstType = 0; 9302 for (int i=0; i<pids.length; i++) { 9303 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 9304 if (proc != null) { 9305 int type = proc.setAdj; 9306 types[i] = type; 9307 if (type > worstType) { 9308 worstType = type; 9309 } 9310 } 9311 } 9312 9313 // If the worst oom_adj is somewhere in the cached proc LRU range, 9314 // then constrain it so we will kill all cached procs. 9315 if (worstType < ProcessList.CACHED_APP_MAX_ADJ 9316 && worstType > ProcessList.CACHED_APP_MIN_ADJ) { 9317 worstType = ProcessList.CACHED_APP_MIN_ADJ; 9318 } 9319 9320 // If this is not a secure call, don't let it kill processes that 9321 // are important. 9322 if (!secure && worstType < ProcessList.SERVICE_ADJ) { 9323 worstType = ProcessList.SERVICE_ADJ; 9324 } 9325 9326 Slog.w(TAG, "Killing processes " + reason + " at adjustment " + worstType); 9327 for (int i=0; i<pids.length; i++) { 9328 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 9329 if (proc == null) { 9330 continue; 9331 } 9332 int adj = proc.setAdj; 9333 if (adj >= worstType && !proc.killedByAm) { 9334 killUnneededProcessLocked(proc, reason); 9335 killed = true; 9336 } 9337 } 9338 } 9339 return killed; 9340 } 9341 9342 @Override 9343 public void killUid(int uid, String reason) { 9344 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9345 throw new SecurityException("killUid only available to the system"); 9346 } 9347 synchronized (this) { 9348 killPackageProcessesLocked(null, UserHandle.getAppId(uid), UserHandle.getUserId(uid), 9349 ProcessList.FOREGROUND_APP_ADJ-1, false, true, true, false, 9350 reason != null ? reason : "kill uid"); 9351 } 9352 } 9353 9354 @Override 9355 public boolean killProcessesBelowForeground(String reason) { 9356 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9357 throw new SecurityException("killProcessesBelowForeground() only available to system"); 9358 } 9359 9360 return killProcessesBelowAdj(ProcessList.FOREGROUND_APP_ADJ, reason); 9361 } 9362 9363 private boolean killProcessesBelowAdj(int belowAdj, String reason) { 9364 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9365 throw new SecurityException("killProcessesBelowAdj() only available to system"); 9366 } 9367 9368 boolean killed = false; 9369 synchronized (mPidsSelfLocked) { 9370 final int size = mPidsSelfLocked.size(); 9371 for (int i = 0; i < size; i++) { 9372 final int pid = mPidsSelfLocked.keyAt(i); 9373 final ProcessRecord proc = mPidsSelfLocked.valueAt(i); 9374 if (proc == null) continue; 9375 9376 final int adj = proc.setAdj; 9377 if (adj > belowAdj && !proc.killedByAm) { 9378 killUnneededProcessLocked(proc, reason); 9379 killed = true; 9380 } 9381 } 9382 } 9383 return killed; 9384 } 9385 9386 @Override 9387 public void hang(final IBinder who, boolean allowRestart) { 9388 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9389 != PackageManager.PERMISSION_GRANTED) { 9390 throw new SecurityException("Requires permission " 9391 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9392 } 9393 9394 final IBinder.DeathRecipient death = new DeathRecipient() { 9395 @Override 9396 public void binderDied() { 9397 synchronized (this) { 9398 notifyAll(); 9399 } 9400 } 9401 }; 9402 9403 try { 9404 who.linkToDeath(death, 0); 9405 } catch (RemoteException e) { 9406 Slog.w(TAG, "hang: given caller IBinder is already dead."); 9407 return; 9408 } 9409 9410 synchronized (this) { 9411 Watchdog.getInstance().setAllowRestart(allowRestart); 9412 Slog.i(TAG, "Hanging system process at request of pid " + Binder.getCallingPid()); 9413 synchronized (death) { 9414 while (who.isBinderAlive()) { 9415 try { 9416 death.wait(); 9417 } catch (InterruptedException e) { 9418 } 9419 } 9420 } 9421 Watchdog.getInstance().setAllowRestart(true); 9422 } 9423 } 9424 9425 @Override 9426 public void restart() { 9427 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9428 != PackageManager.PERMISSION_GRANTED) { 9429 throw new SecurityException("Requires permission " 9430 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9431 } 9432 9433 Log.i(TAG, "Sending shutdown broadcast..."); 9434 9435 BroadcastReceiver br = new BroadcastReceiver() { 9436 @Override public void onReceive(Context context, Intent intent) { 9437 // Now the broadcast is done, finish up the low-level shutdown. 9438 Log.i(TAG, "Shutting down activity manager..."); 9439 shutdown(10000); 9440 Log.i(TAG, "Shutdown complete, restarting!"); 9441 Process.killProcess(Process.myPid()); 9442 System.exit(10); 9443 } 9444 }; 9445 9446 // First send the high-level shut down broadcast. 9447 Intent intent = new Intent(Intent.ACTION_SHUTDOWN); 9448 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 9449 intent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 9450 /* For now we are not doing a clean shutdown, because things seem to get unhappy. 9451 mContext.sendOrderedBroadcastAsUser(intent, 9452 UserHandle.ALL, null, br, mHandler, 0, null, null); 9453 */ 9454 br.onReceive(mContext, intent); 9455 } 9456 9457 private long getLowRamTimeSinceIdle(long now) { 9458 return mLowRamTimeSinceLastIdle + (mLowRamStartTime > 0 ? (now-mLowRamStartTime) : 0); 9459 } 9460 9461 @Override 9462 public void performIdleMaintenance() { 9463 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9464 != PackageManager.PERMISSION_GRANTED) { 9465 throw new SecurityException("Requires permission " 9466 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9467 } 9468 9469 synchronized (this) { 9470 final long now = SystemClock.uptimeMillis(); 9471 final long timeSinceLastIdle = now - mLastIdleTime; 9472 final long lowRamSinceLastIdle = getLowRamTimeSinceIdle(now); 9473 mLastIdleTime = now; 9474 mLowRamTimeSinceLastIdle = 0; 9475 if (mLowRamStartTime != 0) { 9476 mLowRamStartTime = now; 9477 } 9478 9479 StringBuilder sb = new StringBuilder(128); 9480 sb.append("Idle maintenance over "); 9481 TimeUtils.formatDuration(timeSinceLastIdle, sb); 9482 sb.append(" low RAM for "); 9483 TimeUtils.formatDuration(lowRamSinceLastIdle, sb); 9484 Slog.i(TAG, sb.toString()); 9485 9486 // If at least 1/3 of our time since the last idle period has been spent 9487 // with RAM low, then we want to kill processes. 9488 boolean doKilling = lowRamSinceLastIdle > (timeSinceLastIdle/3); 9489 9490 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 9491 ProcessRecord proc = mLruProcesses.get(i); 9492 if (proc.notCachedSinceIdle) { 9493 if (proc.setProcState > ActivityManager.PROCESS_STATE_TOP 9494 && proc.setProcState <= ActivityManager.PROCESS_STATE_SERVICE) { 9495 if (doKilling && proc.initialIdlePss != 0 9496 && proc.lastPss > ((proc.initialIdlePss*3)/2)) { 9497 killUnneededProcessLocked(proc, "idle maint (pss " + proc.lastPss 9498 + " from " + proc.initialIdlePss + ")"); 9499 } 9500 } 9501 } else if (proc.setProcState < ActivityManager.PROCESS_STATE_HOME) { 9502 proc.notCachedSinceIdle = true; 9503 proc.initialIdlePss = 0; 9504 proc.nextPssTime = ProcessList.computeNextPssTime(proc.curProcState, true, 9505 isSleeping(), now); 9506 } 9507 } 9508 9509 mHandler.removeMessages(REQUEST_ALL_PSS_MSG); 9510 mHandler.sendEmptyMessageDelayed(REQUEST_ALL_PSS_MSG, 2*60*1000); 9511 } 9512 } 9513 9514 private void retrieveSettings() { 9515 final ContentResolver resolver = mContext.getContentResolver(); 9516 String debugApp = Settings.Global.getString( 9517 resolver, Settings.Global.DEBUG_APP); 9518 boolean waitForDebugger = Settings.Global.getInt( 9519 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 0) != 0; 9520 boolean alwaysFinishActivities = Settings.Global.getInt( 9521 resolver, Settings.Global.ALWAYS_FINISH_ACTIVITIES, 0) != 0; 9522 boolean forceRtl = Settings.Global.getInt( 9523 resolver, Settings.Global.DEVELOPMENT_FORCE_RTL, 0) != 0; 9524 // Transfer any global setting for forcing RTL layout, into a System Property 9525 SystemProperties.set(Settings.Global.DEVELOPMENT_FORCE_RTL, forceRtl ? "1":"0"); 9526 9527 Configuration configuration = new Configuration(); 9528 Settings.System.getConfiguration(resolver, configuration); 9529 if (forceRtl) { 9530 // This will take care of setting the correct layout direction flags 9531 configuration.setLayoutDirection(configuration.locale); 9532 } 9533 9534 synchronized (this) { 9535 mDebugApp = mOrigDebugApp = debugApp; 9536 mWaitForDebugger = mOrigWaitForDebugger = waitForDebugger; 9537 mAlwaysFinishActivities = alwaysFinishActivities; 9538 // This happens before any activities are started, so we can 9539 // change mConfiguration in-place. 9540 updateConfigurationLocked(configuration, null, false, true); 9541 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Initial config: " + mConfiguration); 9542 } 9543 } 9544 9545 public boolean testIsSystemReady() { 9546 // no need to synchronize(this) just to read & return the value 9547 return mSystemReady; 9548 } 9549 9550 private static File getCalledPreBootReceiversFile() { 9551 File dataDir = Environment.getDataDirectory(); 9552 File systemDir = new File(dataDir, "system"); 9553 File fname = new File(systemDir, "called_pre_boots.dat"); 9554 return fname; 9555 } 9556 9557 static final int LAST_DONE_VERSION = 10000; 9558 9559 private static ArrayList<ComponentName> readLastDonePreBootReceivers() { 9560 ArrayList<ComponentName> lastDoneReceivers = new ArrayList<ComponentName>(); 9561 File file = getCalledPreBootReceiversFile(); 9562 FileInputStream fis = null; 9563 try { 9564 fis = new FileInputStream(file); 9565 DataInputStream dis = new DataInputStream(new BufferedInputStream(fis, 2048)); 9566 int fvers = dis.readInt(); 9567 if (fvers == LAST_DONE_VERSION) { 9568 String vers = dis.readUTF(); 9569 String codename = dis.readUTF(); 9570 String build = dis.readUTF(); 9571 if (android.os.Build.VERSION.RELEASE.equals(vers) 9572 && android.os.Build.VERSION.CODENAME.equals(codename) 9573 && android.os.Build.VERSION.INCREMENTAL.equals(build)) { 9574 int num = dis.readInt(); 9575 while (num > 0) { 9576 num--; 9577 String pkg = dis.readUTF(); 9578 String cls = dis.readUTF(); 9579 lastDoneReceivers.add(new ComponentName(pkg, cls)); 9580 } 9581 } 9582 } 9583 } catch (FileNotFoundException e) { 9584 } catch (IOException e) { 9585 Slog.w(TAG, "Failure reading last done pre-boot receivers", e); 9586 } finally { 9587 if (fis != null) { 9588 try { 9589 fis.close(); 9590 } catch (IOException e) { 9591 } 9592 } 9593 } 9594 return lastDoneReceivers; 9595 } 9596 9597 private static void writeLastDonePreBootReceivers(ArrayList<ComponentName> list) { 9598 File file = getCalledPreBootReceiversFile(); 9599 FileOutputStream fos = null; 9600 DataOutputStream dos = null; 9601 try { 9602 Slog.i(TAG, "Writing new set of last done pre-boot receivers..."); 9603 fos = new FileOutputStream(file); 9604 dos = new DataOutputStream(new BufferedOutputStream(fos, 2048)); 9605 dos.writeInt(LAST_DONE_VERSION); 9606 dos.writeUTF(android.os.Build.VERSION.RELEASE); 9607 dos.writeUTF(android.os.Build.VERSION.CODENAME); 9608 dos.writeUTF(android.os.Build.VERSION.INCREMENTAL); 9609 dos.writeInt(list.size()); 9610 for (int i=0; i<list.size(); i++) { 9611 dos.writeUTF(list.get(i).getPackageName()); 9612 dos.writeUTF(list.get(i).getClassName()); 9613 } 9614 } catch (IOException e) { 9615 Slog.w(TAG, "Failure writing last done pre-boot receivers", e); 9616 file.delete(); 9617 } finally { 9618 FileUtils.sync(fos); 9619 if (dos != null) { 9620 try { 9621 dos.close(); 9622 } catch (IOException e) { 9623 // TODO Auto-generated catch block 9624 e.printStackTrace(); 9625 } 9626 } 9627 } 9628 } 9629 9630 public void systemReady(final Runnable goingCallback) { 9631 synchronized(this) { 9632 if (mSystemReady) { 9633 if (goingCallback != null) goingCallback.run(); 9634 return; 9635 } 9636 9637 if (mRecentTasks == null) { 9638 mRecentTasks = mTaskPersister.restoreTasksLocked(); 9639 if (!mRecentTasks.isEmpty()) { 9640 mStackSupervisor.createStackForRestoredTaskHistory(mRecentTasks); 9641 } 9642 mTaskPersister.startPersisting(); 9643 } 9644 9645 // Check to see if there are any update receivers to run. 9646 if (!mDidUpdate) { 9647 if (mWaitingUpdate) { 9648 return; 9649 } 9650 Intent intent = new Intent(Intent.ACTION_PRE_BOOT_COMPLETED); 9651 List<ResolveInfo> ris = null; 9652 try { 9653 ris = AppGlobals.getPackageManager().queryIntentReceivers( 9654 intent, null, 0, 0); 9655 } catch (RemoteException e) { 9656 } 9657 if (ris != null) { 9658 for (int i=ris.size()-1; i>=0; i--) { 9659 if ((ris.get(i).activityInfo.applicationInfo.flags 9660 &ApplicationInfo.FLAG_SYSTEM) == 0) { 9661 ris.remove(i); 9662 } 9663 } 9664 intent.addFlags(Intent.FLAG_RECEIVER_BOOT_UPGRADE); 9665 9666 ArrayList<ComponentName> lastDoneReceivers = readLastDonePreBootReceivers(); 9667 9668 final ArrayList<ComponentName> doneReceivers = new ArrayList<ComponentName>(); 9669 for (int i=0; i<ris.size(); i++) { 9670 ActivityInfo ai = ris.get(i).activityInfo; 9671 ComponentName comp = new ComponentName(ai.packageName, ai.name); 9672 if (lastDoneReceivers.contains(comp)) { 9673 // We already did the pre boot receiver for this app with the current 9674 // platform version, so don't do it again... 9675 ris.remove(i); 9676 i--; 9677 // ...however, do keep it as one that has been done, so we don't 9678 // forget about it when rewriting the file of last done receivers. 9679 doneReceivers.add(comp); 9680 } 9681 } 9682 9683 final int[] users = getUsersLocked(); 9684 for (int i=0; i<ris.size(); i++) { 9685 ActivityInfo ai = ris.get(i).activityInfo; 9686 ComponentName comp = new ComponentName(ai.packageName, ai.name); 9687 doneReceivers.add(comp); 9688 intent.setComponent(comp); 9689 for (int j=0; j<users.length; j++) { 9690 IIntentReceiver finisher = null; 9691 if (i == ris.size()-1 && j == users.length-1) { 9692 finisher = new IIntentReceiver.Stub() { 9693 public void performReceive(Intent intent, int resultCode, 9694 String data, Bundle extras, boolean ordered, 9695 boolean sticky, int sendingUser) { 9696 // The raw IIntentReceiver interface is called 9697 // with the AM lock held, so redispatch to 9698 // execute our code without the lock. 9699 mHandler.post(new Runnable() { 9700 public void run() { 9701 synchronized (ActivityManagerService.this) { 9702 mDidUpdate = true; 9703 } 9704 writeLastDonePreBootReceivers(doneReceivers); 9705 showBootMessage(mContext.getText( 9706 R.string.android_upgrading_complete), 9707 false); 9708 systemReady(goingCallback); 9709 } 9710 }); 9711 } 9712 }; 9713 } 9714 Slog.i(TAG, "Sending system update to " + intent.getComponent() 9715 + " for user " + users[j]); 9716 broadcastIntentLocked(null, null, intent, null, finisher, 9717 0, null, null, null, AppOpsManager.OP_NONE, 9718 true, false, MY_PID, Process.SYSTEM_UID, 9719 users[j]); 9720 if (finisher != null) { 9721 mWaitingUpdate = true; 9722 } 9723 } 9724 } 9725 } 9726 if (mWaitingUpdate) { 9727 return; 9728 } 9729 mDidUpdate = true; 9730 } 9731 9732 mAppOpsService.systemReady(); 9733 mUsageStatsService.systemReady(); 9734 mSystemReady = true; 9735 } 9736 9737 ArrayList<ProcessRecord> procsToKill = null; 9738 synchronized(mPidsSelfLocked) { 9739 for (int i=mPidsSelfLocked.size()-1; i>=0; i--) { 9740 ProcessRecord proc = mPidsSelfLocked.valueAt(i); 9741 if (!isAllowedWhileBooting(proc.info)){ 9742 if (procsToKill == null) { 9743 procsToKill = new ArrayList<ProcessRecord>(); 9744 } 9745 procsToKill.add(proc); 9746 } 9747 } 9748 } 9749 9750 synchronized(this) { 9751 if (procsToKill != null) { 9752 for (int i=procsToKill.size()-1; i>=0; i--) { 9753 ProcessRecord proc = procsToKill.get(i); 9754 Slog.i(TAG, "Removing system update proc: " + proc); 9755 removeProcessLocked(proc, true, false, "system update done"); 9756 } 9757 } 9758 9759 // Now that we have cleaned up any update processes, we 9760 // are ready to start launching real processes and know that 9761 // we won't trample on them any more. 9762 mProcessesReady = true; 9763 } 9764 9765 Slog.i(TAG, "System now ready"); 9766 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_AMS_READY, 9767 SystemClock.uptimeMillis()); 9768 9769 synchronized(this) { 9770 // Make sure we have no pre-ready processes sitting around. 9771 9772 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) { 9773 ResolveInfo ri = mContext.getPackageManager() 9774 .resolveActivity(new Intent(Intent.ACTION_FACTORY_TEST), 9775 STOCK_PM_FLAGS); 9776 CharSequence errorMsg = null; 9777 if (ri != null) { 9778 ActivityInfo ai = ri.activityInfo; 9779 ApplicationInfo app = ai.applicationInfo; 9780 if ((app.flags&ApplicationInfo.FLAG_SYSTEM) != 0) { 9781 mTopAction = Intent.ACTION_FACTORY_TEST; 9782 mTopData = null; 9783 mTopComponent = new ComponentName(app.packageName, 9784 ai.name); 9785 } else { 9786 errorMsg = mContext.getResources().getText( 9787 com.android.internal.R.string.factorytest_not_system); 9788 } 9789 } else { 9790 errorMsg = mContext.getResources().getText( 9791 com.android.internal.R.string.factorytest_no_action); 9792 } 9793 if (errorMsg != null) { 9794 mTopAction = null; 9795 mTopData = null; 9796 mTopComponent = null; 9797 Message msg = Message.obtain(); 9798 msg.what = SHOW_FACTORY_ERROR_MSG; 9799 msg.getData().putCharSequence("msg", errorMsg); 9800 mHandler.sendMessage(msg); 9801 } 9802 } 9803 } 9804 9805 retrieveSettings(); 9806 9807 synchronized (this) { 9808 readGrantedUriPermissionsLocked(); 9809 } 9810 9811 if (goingCallback != null) goingCallback.run(); 9812 9813 mSystemServiceManager.startUser(mCurrentUserId); 9814 9815 synchronized (this) { 9816 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 9817 try { 9818 List apps = AppGlobals.getPackageManager(). 9819 getPersistentApplications(STOCK_PM_FLAGS); 9820 if (apps != null) { 9821 int N = apps.size(); 9822 int i; 9823 for (i=0; i<N; i++) { 9824 ApplicationInfo info 9825 = (ApplicationInfo)apps.get(i); 9826 if (info != null && 9827 !info.packageName.equals("android")) { 9828 addAppLocked(info, false, null /* ABI override */); 9829 } 9830 } 9831 } 9832 } catch (RemoteException ex) { 9833 // pm is in same process, this will never happen. 9834 } 9835 } 9836 9837 // Start up initial activity. 9838 mBooting = true; 9839 9840 try { 9841 if (AppGlobals.getPackageManager().hasSystemUidErrors()) { 9842 Message msg = Message.obtain(); 9843 msg.what = SHOW_UID_ERROR_MSG; 9844 mHandler.sendMessage(msg); 9845 } 9846 } catch (RemoteException e) { 9847 } 9848 9849 long ident = Binder.clearCallingIdentity(); 9850 try { 9851 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 9852 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 9853 | Intent.FLAG_RECEIVER_FOREGROUND); 9854 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 9855 broadcastIntentLocked(null, null, intent, 9856 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 9857 false, false, MY_PID, Process.SYSTEM_UID, mCurrentUserId); 9858 intent = new Intent(Intent.ACTION_USER_STARTING); 9859 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 9860 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 9861 broadcastIntentLocked(null, null, intent, 9862 null, new IIntentReceiver.Stub() { 9863 @Override 9864 public void performReceive(Intent intent, int resultCode, String data, 9865 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 9866 throws RemoteException { 9867 } 9868 }, 0, null, null, 9869 android.Manifest.permission.INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 9870 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 9871 } catch (Throwable t) { 9872 Slog.wtf(TAG, "Failed sending first user broadcasts", t); 9873 } finally { 9874 Binder.restoreCallingIdentity(ident); 9875 } 9876 mStackSupervisor.resumeTopActivitiesLocked(); 9877 sendUserSwitchBroadcastsLocked(-1, mCurrentUserId); 9878 } 9879 } 9880 9881 private boolean makeAppCrashingLocked(ProcessRecord app, 9882 String shortMsg, String longMsg, String stackTrace) { 9883 app.crashing = true; 9884 app.crashingReport = generateProcessError(app, 9885 ActivityManager.ProcessErrorStateInfo.CRASHED, null, shortMsg, longMsg, stackTrace); 9886 startAppProblemLocked(app); 9887 app.stopFreezingAllLocked(); 9888 return handleAppCrashLocked(app, shortMsg, longMsg, stackTrace); 9889 } 9890 9891 private void makeAppNotRespondingLocked(ProcessRecord app, 9892 String activity, String shortMsg, String longMsg) { 9893 app.notResponding = true; 9894 app.notRespondingReport = generateProcessError(app, 9895 ActivityManager.ProcessErrorStateInfo.NOT_RESPONDING, 9896 activity, shortMsg, longMsg, null); 9897 startAppProblemLocked(app); 9898 app.stopFreezingAllLocked(); 9899 } 9900 9901 /** 9902 * Generate a process error record, suitable for attachment to a ProcessRecord. 9903 * 9904 * @param app The ProcessRecord in which the error occurred. 9905 * @param condition Crashing, Application Not Responding, etc. Values are defined in 9906 * ActivityManager.AppErrorStateInfo 9907 * @param activity The activity associated with the crash, if known. 9908 * @param shortMsg Short message describing the crash. 9909 * @param longMsg Long message describing the crash. 9910 * @param stackTrace Full crash stack trace, may be null. 9911 * 9912 * @return Returns a fully-formed AppErrorStateInfo record. 9913 */ 9914 private ActivityManager.ProcessErrorStateInfo generateProcessError(ProcessRecord app, 9915 int condition, String activity, String shortMsg, String longMsg, String stackTrace) { 9916 ActivityManager.ProcessErrorStateInfo report = new ActivityManager.ProcessErrorStateInfo(); 9917 9918 report.condition = condition; 9919 report.processName = app.processName; 9920 report.pid = app.pid; 9921 report.uid = app.info.uid; 9922 report.tag = activity; 9923 report.shortMsg = shortMsg; 9924 report.longMsg = longMsg; 9925 report.stackTrace = stackTrace; 9926 9927 return report; 9928 } 9929 9930 void killAppAtUsersRequest(ProcessRecord app, Dialog fromDialog) { 9931 synchronized (this) { 9932 app.crashing = false; 9933 app.crashingReport = null; 9934 app.notResponding = false; 9935 app.notRespondingReport = null; 9936 if (app.anrDialog == fromDialog) { 9937 app.anrDialog = null; 9938 } 9939 if (app.waitDialog == fromDialog) { 9940 app.waitDialog = null; 9941 } 9942 if (app.pid > 0 && app.pid != MY_PID) { 9943 handleAppCrashLocked(app, null, null, null); 9944 killUnneededProcessLocked(app, "user request after error"); 9945 } 9946 } 9947 } 9948 9949 private boolean handleAppCrashLocked(ProcessRecord app, String shortMsg, String longMsg, 9950 String stackTrace) { 9951 long now = SystemClock.uptimeMillis(); 9952 9953 Long crashTime; 9954 if (!app.isolated) { 9955 crashTime = mProcessCrashTimes.get(app.info.processName, app.uid); 9956 } else { 9957 crashTime = null; 9958 } 9959 if (crashTime != null && now < crashTime+ProcessList.MIN_CRASH_INTERVAL) { 9960 // This process loses! 9961 Slog.w(TAG, "Process " + app.info.processName 9962 + " has crashed too many times: killing!"); 9963 EventLog.writeEvent(EventLogTags.AM_PROCESS_CRASHED_TOO_MUCH, 9964 app.userId, app.info.processName, app.uid); 9965 mStackSupervisor.handleAppCrashLocked(app); 9966 if (!app.persistent) { 9967 // We don't want to start this process again until the user 9968 // explicitly does so... but for persistent process, we really 9969 // need to keep it running. If a persistent process is actually 9970 // repeatedly crashing, then badness for everyone. 9971 EventLog.writeEvent(EventLogTags.AM_PROC_BAD, app.userId, app.uid, 9972 app.info.processName); 9973 if (!app.isolated) { 9974 // XXX We don't have a way to mark isolated processes 9975 // as bad, since they don't have a peristent identity. 9976 mBadProcesses.put(app.info.processName, app.uid, 9977 new BadProcessInfo(now, shortMsg, longMsg, stackTrace)); 9978 mProcessCrashTimes.remove(app.info.processName, app.uid); 9979 } 9980 app.bad = true; 9981 app.removed = true; 9982 // Don't let services in this process be restarted and potentially 9983 // annoy the user repeatedly. Unless it is persistent, since those 9984 // processes run critical code. 9985 removeProcessLocked(app, false, false, "crash"); 9986 mStackSupervisor.resumeTopActivitiesLocked(); 9987 return false; 9988 } 9989 mStackSupervisor.resumeTopActivitiesLocked(); 9990 } else { 9991 mStackSupervisor.finishTopRunningActivityLocked(app); 9992 } 9993 9994 // Bump up the crash count of any services currently running in the proc. 9995 for (int i=app.services.size()-1; i>=0; i--) { 9996 // Any services running in the application need to be placed 9997 // back in the pending list. 9998 ServiceRecord sr = app.services.valueAt(i); 9999 sr.crashCount++; 10000 } 10001 10002 // If the crashing process is what we consider to be the "home process" and it has been 10003 // replaced by a third-party app, clear the package preferred activities from packages 10004 // with a home activity running in the process to prevent a repeatedly crashing app 10005 // from blocking the user to manually clear the list. 10006 final ArrayList<ActivityRecord> activities = app.activities; 10007 if (app == mHomeProcess && activities.size() > 0 10008 && (mHomeProcess.info.flags & ApplicationInfo.FLAG_SYSTEM) == 0) { 10009 for (int activityNdx = activities.size() - 1; activityNdx >= 0; --activityNdx) { 10010 final ActivityRecord r = activities.get(activityNdx); 10011 if (r.isHomeActivity()) { 10012 Log.i(TAG, "Clearing package preferred activities from " + r.packageName); 10013 try { 10014 ActivityThread.getPackageManager() 10015 .clearPackagePreferredActivities(r.packageName); 10016 } catch (RemoteException c) { 10017 // pm is in same process, this will never happen. 10018 } 10019 } 10020 } 10021 } 10022 10023 if (!app.isolated) { 10024 // XXX Can't keep track of crash times for isolated processes, 10025 // because they don't have a perisistent identity. 10026 mProcessCrashTimes.put(app.info.processName, app.uid, now); 10027 } 10028 10029 return true; 10030 } 10031 10032 void startAppProblemLocked(ProcessRecord app) { 10033 if (app.userId == mCurrentUserId) { 10034 app.errorReportReceiver = ApplicationErrorReport.getErrorReportReceiver( 10035 mContext, app.info.packageName, app.info.flags); 10036 } else { 10037 // If this app is not running under the current user, then we 10038 // can't give it a report button because that would require 10039 // launching the report UI under a different user. 10040 app.errorReportReceiver = null; 10041 } 10042 skipCurrentReceiverLocked(app); 10043 } 10044 10045 void skipCurrentReceiverLocked(ProcessRecord app) { 10046 for (BroadcastQueue queue : mBroadcastQueues) { 10047 queue.skipCurrentReceiverLocked(app); 10048 } 10049 } 10050 10051 /** 10052 * Used by {@link com.android.internal.os.RuntimeInit} to report when an application crashes. 10053 * The application process will exit immediately after this call returns. 10054 * @param app object of the crashing app, null for the system server 10055 * @param crashInfo describing the exception 10056 */ 10057 public void handleApplicationCrash(IBinder app, ApplicationErrorReport.CrashInfo crashInfo) { 10058 ProcessRecord r = findAppProcess(app, "Crash"); 10059 final String processName = app == null ? "system_server" 10060 : (r == null ? "unknown" : r.processName); 10061 10062 handleApplicationCrashInner("crash", r, processName, crashInfo); 10063 } 10064 10065 /* Native crash reporting uses this inner version because it needs to be somewhat 10066 * decoupled from the AM-managed cleanup lifecycle 10067 */ 10068 void handleApplicationCrashInner(String eventType, ProcessRecord r, String processName, 10069 ApplicationErrorReport.CrashInfo crashInfo) { 10070 EventLog.writeEvent(EventLogTags.AM_CRASH, Binder.getCallingPid(), 10071 UserHandle.getUserId(Binder.getCallingUid()), processName, 10072 r == null ? -1 : r.info.flags, 10073 crashInfo.exceptionClassName, 10074 crashInfo.exceptionMessage, 10075 crashInfo.throwFileName, 10076 crashInfo.throwLineNumber); 10077 10078 addErrorToDropBox(eventType, r, processName, null, null, null, null, null, crashInfo); 10079 10080 crashApplication(r, crashInfo); 10081 } 10082 10083 public void handleApplicationStrictModeViolation( 10084 IBinder app, 10085 int violationMask, 10086 StrictMode.ViolationInfo info) { 10087 ProcessRecord r = findAppProcess(app, "StrictMode"); 10088 if (r == null) { 10089 return; 10090 } 10091 10092 if ((violationMask & StrictMode.PENALTY_DROPBOX) != 0) { 10093 Integer stackFingerprint = info.hashCode(); 10094 boolean logIt = true; 10095 synchronized (mAlreadyLoggedViolatedStacks) { 10096 if (mAlreadyLoggedViolatedStacks.contains(stackFingerprint)) { 10097 logIt = false; 10098 // TODO: sub-sample into EventLog for these, with 10099 // the info.durationMillis? Then we'd get 10100 // the relative pain numbers, without logging all 10101 // the stack traces repeatedly. We'd want to do 10102 // likewise in the client code, which also does 10103 // dup suppression, before the Binder call. 10104 } else { 10105 if (mAlreadyLoggedViolatedStacks.size() >= MAX_DUP_SUPPRESSED_STACKS) { 10106 mAlreadyLoggedViolatedStacks.clear(); 10107 } 10108 mAlreadyLoggedViolatedStacks.add(stackFingerprint); 10109 } 10110 } 10111 if (logIt) { 10112 logStrictModeViolationToDropBox(r, info); 10113 } 10114 } 10115 10116 if ((violationMask & StrictMode.PENALTY_DIALOG) != 0) { 10117 AppErrorResult result = new AppErrorResult(); 10118 synchronized (this) { 10119 final long origId = Binder.clearCallingIdentity(); 10120 10121 Message msg = Message.obtain(); 10122 msg.what = SHOW_STRICT_MODE_VIOLATION_MSG; 10123 HashMap<String, Object> data = new HashMap<String, Object>(); 10124 data.put("result", result); 10125 data.put("app", r); 10126 data.put("violationMask", violationMask); 10127 data.put("info", info); 10128 msg.obj = data; 10129 mHandler.sendMessage(msg); 10130 10131 Binder.restoreCallingIdentity(origId); 10132 } 10133 int res = result.get(); 10134 Slog.w(TAG, "handleApplicationStrictModeViolation; res=" + res); 10135 } 10136 } 10137 10138 // Depending on the policy in effect, there could be a bunch of 10139 // these in quick succession so we try to batch these together to 10140 // minimize disk writes, number of dropbox entries, and maximize 10141 // compression, by having more fewer, larger records. 10142 private void logStrictModeViolationToDropBox( 10143 ProcessRecord process, 10144 StrictMode.ViolationInfo info) { 10145 if (info == null) { 10146 return; 10147 } 10148 final boolean isSystemApp = process == null || 10149 (process.info.flags & (ApplicationInfo.FLAG_SYSTEM | 10150 ApplicationInfo.FLAG_UPDATED_SYSTEM_APP)) != 0; 10151 final String processName = process == null ? "unknown" : process.processName; 10152 final String dropboxTag = isSystemApp ? "system_app_strictmode" : "data_app_strictmode"; 10153 final DropBoxManager dbox = (DropBoxManager) 10154 mContext.getSystemService(Context.DROPBOX_SERVICE); 10155 10156 // Exit early if the dropbox isn't configured to accept this report type. 10157 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 10158 10159 boolean bufferWasEmpty; 10160 boolean needsFlush; 10161 final StringBuilder sb = isSystemApp ? mStrictModeBuffer : new StringBuilder(1024); 10162 synchronized (sb) { 10163 bufferWasEmpty = sb.length() == 0; 10164 appendDropBoxProcessHeaders(process, processName, sb); 10165 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 10166 sb.append("System-App: ").append(isSystemApp).append("\n"); 10167 sb.append("Uptime-Millis: ").append(info.violationUptimeMillis).append("\n"); 10168 if (info.violationNumThisLoop != 0) { 10169 sb.append("Loop-Violation-Number: ").append(info.violationNumThisLoop).append("\n"); 10170 } 10171 if (info.numAnimationsRunning != 0) { 10172 sb.append("Animations-Running: ").append(info.numAnimationsRunning).append("\n"); 10173 } 10174 if (info.broadcastIntentAction != null) { 10175 sb.append("Broadcast-Intent-Action: ").append(info.broadcastIntentAction).append("\n"); 10176 } 10177 if (info.durationMillis != -1) { 10178 sb.append("Duration-Millis: ").append(info.durationMillis).append("\n"); 10179 } 10180 if (info.numInstances != -1) { 10181 sb.append("Instance-Count: ").append(info.numInstances).append("\n"); 10182 } 10183 if (info.tags != null) { 10184 for (String tag : info.tags) { 10185 sb.append("Span-Tag: ").append(tag).append("\n"); 10186 } 10187 } 10188 sb.append("\n"); 10189 if (info.crashInfo != null && info.crashInfo.stackTrace != null) { 10190 sb.append(info.crashInfo.stackTrace); 10191 } 10192 sb.append("\n"); 10193 10194 // Only buffer up to ~64k. Various logging bits truncate 10195 // things at 128k. 10196 needsFlush = (sb.length() > 64 * 1024); 10197 } 10198 10199 // Flush immediately if the buffer's grown too large, or this 10200 // is a non-system app. Non-system apps are isolated with a 10201 // different tag & policy and not batched. 10202 // 10203 // Batching is useful during internal testing with 10204 // StrictMode settings turned up high. Without batching, 10205 // thousands of separate files could be created on boot. 10206 if (!isSystemApp || needsFlush) { 10207 new Thread("Error dump: " + dropboxTag) { 10208 @Override 10209 public void run() { 10210 String report; 10211 synchronized (sb) { 10212 report = sb.toString(); 10213 sb.delete(0, sb.length()); 10214 sb.trimToSize(); 10215 } 10216 if (report.length() != 0) { 10217 dbox.addText(dropboxTag, report); 10218 } 10219 } 10220 }.start(); 10221 return; 10222 } 10223 10224 // System app batching: 10225 if (!bufferWasEmpty) { 10226 // An existing dropbox-writing thread is outstanding, so 10227 // we don't need to start it up. The existing thread will 10228 // catch the buffer appends we just did. 10229 return; 10230 } 10231 10232 // Worker thread to both batch writes and to avoid blocking the caller on I/O. 10233 // (After this point, we shouldn't access AMS internal data structures.) 10234 new Thread("Error dump: " + dropboxTag) { 10235 @Override 10236 public void run() { 10237 // 5 second sleep to let stacks arrive and be batched together 10238 try { 10239 Thread.sleep(5000); // 5 seconds 10240 } catch (InterruptedException e) {} 10241 10242 String errorReport; 10243 synchronized (mStrictModeBuffer) { 10244 errorReport = mStrictModeBuffer.toString(); 10245 if (errorReport.length() == 0) { 10246 return; 10247 } 10248 mStrictModeBuffer.delete(0, mStrictModeBuffer.length()); 10249 mStrictModeBuffer.trimToSize(); 10250 } 10251 dbox.addText(dropboxTag, errorReport); 10252 } 10253 }.start(); 10254 } 10255 10256 /** 10257 * Used by {@link Log} via {@link com.android.internal.os.RuntimeInit} to report serious errors. 10258 * @param app object of the crashing app, null for the system server 10259 * @param tag reported by the caller 10260 * @param crashInfo describing the context of the error 10261 * @return true if the process should exit immediately (WTF is fatal) 10262 */ 10263 public boolean handleApplicationWtf(IBinder app, String tag, 10264 ApplicationErrorReport.CrashInfo crashInfo) { 10265 ProcessRecord r = findAppProcess(app, "WTF"); 10266 final String processName = app == null ? "system_server" 10267 : (r == null ? "unknown" : r.processName); 10268 10269 EventLog.writeEvent(EventLogTags.AM_WTF, 10270 UserHandle.getUserId(Binder.getCallingUid()), Binder.getCallingPid(), 10271 processName, 10272 r == null ? -1 : r.info.flags, 10273 tag, crashInfo.exceptionMessage); 10274 10275 addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, crashInfo); 10276 10277 if (r != null && r.pid != Process.myPid() && 10278 Settings.Global.getInt(mContext.getContentResolver(), 10279 Settings.Global.WTF_IS_FATAL, 0) != 0) { 10280 crashApplication(r, crashInfo); 10281 return true; 10282 } else { 10283 return false; 10284 } 10285 } 10286 10287 /** 10288 * @param app object of some object (as stored in {@link com.android.internal.os.RuntimeInit}) 10289 * @return the corresponding {@link ProcessRecord} object, or null if none could be found 10290 */ 10291 private ProcessRecord findAppProcess(IBinder app, String reason) { 10292 if (app == null) { 10293 return null; 10294 } 10295 10296 synchronized (this) { 10297 final int NP = mProcessNames.getMap().size(); 10298 for (int ip=0; ip<NP; ip++) { 10299 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 10300 final int NA = apps.size(); 10301 for (int ia=0; ia<NA; ia++) { 10302 ProcessRecord p = apps.valueAt(ia); 10303 if (p.thread != null && p.thread.asBinder() == app) { 10304 return p; 10305 } 10306 } 10307 } 10308 10309 Slog.w(TAG, "Can't find mystery application for " + reason 10310 + " from pid=" + Binder.getCallingPid() 10311 + " uid=" + Binder.getCallingUid() + ": " + app); 10312 return null; 10313 } 10314 } 10315 10316 /** 10317 * Utility function for addErrorToDropBox and handleStrictModeViolation's logging 10318 * to append various headers to the dropbox log text. 10319 */ 10320 private void appendDropBoxProcessHeaders(ProcessRecord process, String processName, 10321 StringBuilder sb) { 10322 // Watchdog thread ends up invoking this function (with 10323 // a null ProcessRecord) to add the stack file to dropbox. 10324 // Do not acquire a lock on this (am) in such cases, as it 10325 // could cause a potential deadlock, if and when watchdog 10326 // is invoked due to unavailability of lock on am and it 10327 // would prevent watchdog from killing system_server. 10328 if (process == null) { 10329 sb.append("Process: ").append(processName).append("\n"); 10330 return; 10331 } 10332 // Note: ProcessRecord 'process' is guarded by the service 10333 // instance. (notably process.pkgList, which could otherwise change 10334 // concurrently during execution of this method) 10335 synchronized (this) { 10336 sb.append("Process: ").append(processName).append("\n"); 10337 int flags = process.info.flags; 10338 IPackageManager pm = AppGlobals.getPackageManager(); 10339 sb.append("Flags: 0x").append(Integer.toString(flags, 16)).append("\n"); 10340 for (int ip=0; ip<process.pkgList.size(); ip++) { 10341 String pkg = process.pkgList.keyAt(ip); 10342 sb.append("Package: ").append(pkg); 10343 try { 10344 PackageInfo pi = pm.getPackageInfo(pkg, 0, UserHandle.getCallingUserId()); 10345 if (pi != null) { 10346 sb.append(" v").append(pi.versionCode); 10347 if (pi.versionName != null) { 10348 sb.append(" (").append(pi.versionName).append(")"); 10349 } 10350 } 10351 } catch (RemoteException e) { 10352 Slog.e(TAG, "Error getting package info: " + pkg, e); 10353 } 10354 sb.append("\n"); 10355 } 10356 } 10357 } 10358 10359 private static String processClass(ProcessRecord process) { 10360 if (process == null || process.pid == MY_PID) { 10361 return "system_server"; 10362 } else if ((process.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 10363 return "system_app"; 10364 } else { 10365 return "data_app"; 10366 } 10367 } 10368 10369 /** 10370 * Write a description of an error (crash, WTF, ANR) to the drop box. 10371 * @param eventType to include in the drop box tag ("crash", "wtf", etc.) 10372 * @param process which caused the error, null means the system server 10373 * @param activity which triggered the error, null if unknown 10374 * @param parent activity related to the error, null if unknown 10375 * @param subject line related to the error, null if absent 10376 * @param report in long form describing the error, null if absent 10377 * @param logFile to include in the report, null if none 10378 * @param crashInfo giving an application stack trace, null if absent 10379 */ 10380 public void addErrorToDropBox(String eventType, 10381 ProcessRecord process, String processName, ActivityRecord activity, 10382 ActivityRecord parent, String subject, 10383 final String report, final File logFile, 10384 final ApplicationErrorReport.CrashInfo crashInfo) { 10385 // NOTE -- this must never acquire the ActivityManagerService lock, 10386 // otherwise the watchdog may be prevented from resetting the system. 10387 10388 final String dropboxTag = processClass(process) + "_" + eventType; 10389 final DropBoxManager dbox = (DropBoxManager) 10390 mContext.getSystemService(Context.DROPBOX_SERVICE); 10391 10392 // Exit early if the dropbox isn't configured to accept this report type. 10393 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 10394 10395 final StringBuilder sb = new StringBuilder(1024); 10396 appendDropBoxProcessHeaders(process, processName, sb); 10397 if (activity != null) { 10398 sb.append("Activity: ").append(activity.shortComponentName).append("\n"); 10399 } 10400 if (parent != null && parent.app != null && parent.app.pid != process.pid) { 10401 sb.append("Parent-Process: ").append(parent.app.processName).append("\n"); 10402 } 10403 if (parent != null && parent != activity) { 10404 sb.append("Parent-Activity: ").append(parent.shortComponentName).append("\n"); 10405 } 10406 if (subject != null) { 10407 sb.append("Subject: ").append(subject).append("\n"); 10408 } 10409 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 10410 if (Debug.isDebuggerConnected()) { 10411 sb.append("Debugger: Connected\n"); 10412 } 10413 sb.append("\n"); 10414 10415 // Do the rest in a worker thread to avoid blocking the caller on I/O 10416 // (After this point, we shouldn't access AMS internal data structures.) 10417 Thread worker = new Thread("Error dump: " + dropboxTag) { 10418 @Override 10419 public void run() { 10420 if (report != null) { 10421 sb.append(report); 10422 } 10423 if (logFile != null) { 10424 try { 10425 sb.append(FileUtils.readTextFile(logFile, DROPBOX_MAX_SIZE, 10426 "\n\n[[TRUNCATED]]")); 10427 } catch (IOException e) { 10428 Slog.e(TAG, "Error reading " + logFile, e); 10429 } 10430 } 10431 if (crashInfo != null && crashInfo.stackTrace != null) { 10432 sb.append(crashInfo.stackTrace); 10433 } 10434 10435 String setting = Settings.Global.ERROR_LOGCAT_PREFIX + dropboxTag; 10436 int lines = Settings.Global.getInt(mContext.getContentResolver(), setting, 0); 10437 if (lines > 0) { 10438 sb.append("\n"); 10439 10440 // Merge several logcat streams, and take the last N lines 10441 InputStreamReader input = null; 10442 try { 10443 java.lang.Process logcat = new ProcessBuilder("/system/bin/logcat", 10444 "-v", "time", "-b", "events", "-b", "system", "-b", "main", 10445 "-t", String.valueOf(lines)).redirectErrorStream(true).start(); 10446 10447 try { logcat.getOutputStream().close(); } catch (IOException e) {} 10448 try { logcat.getErrorStream().close(); } catch (IOException e) {} 10449 input = new InputStreamReader(logcat.getInputStream()); 10450 10451 int num; 10452 char[] buf = new char[8192]; 10453 while ((num = input.read(buf)) > 0) sb.append(buf, 0, num); 10454 } catch (IOException e) { 10455 Slog.e(TAG, "Error running logcat", e); 10456 } finally { 10457 if (input != null) try { input.close(); } catch (IOException e) {} 10458 } 10459 } 10460 10461 dbox.addText(dropboxTag, sb.toString()); 10462 } 10463 }; 10464 10465 if (process == null) { 10466 // If process is null, we are being called from some internal code 10467 // and may be about to die -- run this synchronously. 10468 worker.run(); 10469 } else { 10470 worker.start(); 10471 } 10472 } 10473 10474 /** 10475 * Bring up the "unexpected error" dialog box for a crashing app. 10476 * Deal with edge cases (intercepts from instrumented applications, 10477 * ActivityController, error intent receivers, that sort of thing). 10478 * @param r the application crashing 10479 * @param crashInfo describing the failure 10480 */ 10481 private void crashApplication(ProcessRecord r, ApplicationErrorReport.CrashInfo crashInfo) { 10482 long timeMillis = System.currentTimeMillis(); 10483 String shortMsg = crashInfo.exceptionClassName; 10484 String longMsg = crashInfo.exceptionMessage; 10485 String stackTrace = crashInfo.stackTrace; 10486 if (shortMsg != null && longMsg != null) { 10487 longMsg = shortMsg + ": " + longMsg; 10488 } else if (shortMsg != null) { 10489 longMsg = shortMsg; 10490 } 10491 10492 AppErrorResult result = new AppErrorResult(); 10493 synchronized (this) { 10494 if (mController != null) { 10495 try { 10496 String name = r != null ? r.processName : null; 10497 int pid = r != null ? r.pid : Binder.getCallingPid(); 10498 if (!mController.appCrashed(name, pid, 10499 shortMsg, longMsg, timeMillis, crashInfo.stackTrace)) { 10500 Slog.w(TAG, "Force-killing crashed app " + name 10501 + " at watcher's request"); 10502 Process.killProcess(pid); 10503 return; 10504 } 10505 } catch (RemoteException e) { 10506 mController = null; 10507 Watchdog.getInstance().setActivityController(null); 10508 } 10509 } 10510 10511 final long origId = Binder.clearCallingIdentity(); 10512 10513 // If this process is running instrumentation, finish it. 10514 if (r != null && r.instrumentationClass != null) { 10515 Slog.w(TAG, "Error in app " + r.processName 10516 + " running instrumentation " + r.instrumentationClass + ":"); 10517 if (shortMsg != null) Slog.w(TAG, " " + shortMsg); 10518 if (longMsg != null) Slog.w(TAG, " " + longMsg); 10519 Bundle info = new Bundle(); 10520 info.putString("shortMsg", shortMsg); 10521 info.putString("longMsg", longMsg); 10522 finishInstrumentationLocked(r, Activity.RESULT_CANCELED, info); 10523 Binder.restoreCallingIdentity(origId); 10524 return; 10525 } 10526 10527 // If we can't identify the process or it's already exceeded its crash quota, 10528 // quit right away without showing a crash dialog. 10529 if (r == null || !makeAppCrashingLocked(r, shortMsg, longMsg, stackTrace)) { 10530 Binder.restoreCallingIdentity(origId); 10531 return; 10532 } 10533 10534 Message msg = Message.obtain(); 10535 msg.what = SHOW_ERROR_MSG; 10536 HashMap data = new HashMap(); 10537 data.put("result", result); 10538 data.put("app", r); 10539 msg.obj = data; 10540 mHandler.sendMessage(msg); 10541 10542 Binder.restoreCallingIdentity(origId); 10543 } 10544 10545 int res = result.get(); 10546 10547 Intent appErrorIntent = null; 10548 synchronized (this) { 10549 if (r != null && !r.isolated) { 10550 // XXX Can't keep track of crash time for isolated processes, 10551 // since they don't have a persistent identity. 10552 mProcessCrashTimes.put(r.info.processName, r.uid, 10553 SystemClock.uptimeMillis()); 10554 } 10555 if (res == AppErrorDialog.FORCE_QUIT_AND_REPORT) { 10556 appErrorIntent = createAppErrorIntentLocked(r, timeMillis, crashInfo); 10557 } 10558 } 10559 10560 if (appErrorIntent != null) { 10561 try { 10562 mContext.startActivityAsUser(appErrorIntent, new UserHandle(r.userId)); 10563 } catch (ActivityNotFoundException e) { 10564 Slog.w(TAG, "bug report receiver dissappeared", e); 10565 } 10566 } 10567 } 10568 10569 Intent createAppErrorIntentLocked(ProcessRecord r, 10570 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 10571 ApplicationErrorReport report = createAppErrorReportLocked(r, timeMillis, crashInfo); 10572 if (report == null) { 10573 return null; 10574 } 10575 Intent result = new Intent(Intent.ACTION_APP_ERROR); 10576 result.setComponent(r.errorReportReceiver); 10577 result.putExtra(Intent.EXTRA_BUG_REPORT, report); 10578 result.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 10579 return result; 10580 } 10581 10582 private ApplicationErrorReport createAppErrorReportLocked(ProcessRecord r, 10583 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 10584 if (r.errorReportReceiver == null) { 10585 return null; 10586 } 10587 10588 if (!r.crashing && !r.notResponding && !r.forceCrashReport) { 10589 return null; 10590 } 10591 10592 ApplicationErrorReport report = new ApplicationErrorReport(); 10593 report.packageName = r.info.packageName; 10594 report.installerPackageName = r.errorReportReceiver.getPackageName(); 10595 report.processName = r.processName; 10596 report.time = timeMillis; 10597 report.systemApp = (r.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0; 10598 10599 if (r.crashing || r.forceCrashReport) { 10600 report.type = ApplicationErrorReport.TYPE_CRASH; 10601 report.crashInfo = crashInfo; 10602 } else if (r.notResponding) { 10603 report.type = ApplicationErrorReport.TYPE_ANR; 10604 report.anrInfo = new ApplicationErrorReport.AnrInfo(); 10605 10606 report.anrInfo.activity = r.notRespondingReport.tag; 10607 report.anrInfo.cause = r.notRespondingReport.shortMsg; 10608 report.anrInfo.info = r.notRespondingReport.longMsg; 10609 } 10610 10611 return report; 10612 } 10613 10614 public List<ActivityManager.ProcessErrorStateInfo> getProcessesInErrorState() { 10615 enforceNotIsolatedCaller("getProcessesInErrorState"); 10616 // assume our apps are happy - lazy create the list 10617 List<ActivityManager.ProcessErrorStateInfo> errList = null; 10618 10619 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 10620 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 10621 int userId = UserHandle.getUserId(Binder.getCallingUid()); 10622 10623 synchronized (this) { 10624 10625 // iterate across all processes 10626 for (int i=mLruProcesses.size()-1; i>=0; i--) { 10627 ProcessRecord app = mLruProcesses.get(i); 10628 if (!allUsers && app.userId != userId) { 10629 continue; 10630 } 10631 if ((app.thread != null) && (app.crashing || app.notResponding)) { 10632 // This one's in trouble, so we'll generate a report for it 10633 // crashes are higher priority (in case there's a crash *and* an anr) 10634 ActivityManager.ProcessErrorStateInfo report = null; 10635 if (app.crashing) { 10636 report = app.crashingReport; 10637 } else if (app.notResponding) { 10638 report = app.notRespondingReport; 10639 } 10640 10641 if (report != null) { 10642 if (errList == null) { 10643 errList = new ArrayList<ActivityManager.ProcessErrorStateInfo>(1); 10644 } 10645 errList.add(report); 10646 } else { 10647 Slog.w(TAG, "Missing app error report, app = " + app.processName + 10648 " crashing = " + app.crashing + 10649 " notResponding = " + app.notResponding); 10650 } 10651 } 10652 } 10653 } 10654 10655 return errList; 10656 } 10657 10658 static int oomAdjToImportance(int adj, ActivityManager.RunningAppProcessInfo currApp) { 10659 if (adj >= ProcessList.CACHED_APP_MIN_ADJ) { 10660 if (currApp != null) { 10661 currApp.lru = adj - ProcessList.CACHED_APP_MIN_ADJ + 1; 10662 } 10663 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND; 10664 } else if (adj >= ProcessList.SERVICE_B_ADJ) { 10665 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_SERVICE; 10666 } else if (adj >= ProcessList.HOME_APP_ADJ) { 10667 if (currApp != null) { 10668 currApp.lru = 0; 10669 } 10670 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND; 10671 } else if (adj >= ProcessList.SERVICE_ADJ) { 10672 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_SERVICE; 10673 } else if (adj >= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 10674 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_CANT_SAVE_STATE; 10675 } else if (adj >= ProcessList.PERCEPTIBLE_APP_ADJ) { 10676 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_PERCEPTIBLE; 10677 } else if (adj >= ProcessList.VISIBLE_APP_ADJ) { 10678 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_VISIBLE; 10679 } else { 10680 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND; 10681 } 10682 } 10683 10684 private void fillInProcMemInfo(ProcessRecord app, 10685 ActivityManager.RunningAppProcessInfo outInfo) { 10686 outInfo.pid = app.pid; 10687 outInfo.uid = app.info.uid; 10688 if (mHeavyWeightProcess == app) { 10689 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_CANT_SAVE_STATE; 10690 } 10691 if (app.persistent) { 10692 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_PERSISTENT; 10693 } 10694 if (app.activities.size() > 0) { 10695 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_HAS_ACTIVITIES; 10696 } 10697 outInfo.lastTrimLevel = app.trimMemoryLevel; 10698 int adj = app.curAdj; 10699 outInfo.importance = oomAdjToImportance(adj, outInfo); 10700 outInfo.importanceReasonCode = app.adjTypeCode; 10701 outInfo.processState = app.curProcState; 10702 } 10703 10704 public List<ActivityManager.RunningAppProcessInfo> getRunningAppProcesses() { 10705 enforceNotIsolatedCaller("getRunningAppProcesses"); 10706 // Lazy instantiation of list 10707 List<ActivityManager.RunningAppProcessInfo> runList = null; 10708 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 10709 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 10710 int userId = UserHandle.getUserId(Binder.getCallingUid()); 10711 synchronized (this) { 10712 // Iterate across all processes 10713 for (int i=mLruProcesses.size()-1; i>=0; i--) { 10714 ProcessRecord app = mLruProcesses.get(i); 10715 if (!allUsers && app.userId != userId) { 10716 continue; 10717 } 10718 if ((app.thread != null) && (!app.crashing && !app.notResponding)) { 10719 // Generate process state info for running application 10720 ActivityManager.RunningAppProcessInfo currApp = 10721 new ActivityManager.RunningAppProcessInfo(app.processName, 10722 app.pid, app.getPackageList()); 10723 fillInProcMemInfo(app, currApp); 10724 if (app.adjSource instanceof ProcessRecord) { 10725 currApp.importanceReasonPid = ((ProcessRecord)app.adjSource).pid; 10726 currApp.importanceReasonImportance = oomAdjToImportance( 10727 app.adjSourceOom, null); 10728 } else if (app.adjSource instanceof ActivityRecord) { 10729 ActivityRecord r = (ActivityRecord)app.adjSource; 10730 if (r.app != null) currApp.importanceReasonPid = r.app.pid; 10731 } 10732 if (app.adjTarget instanceof ComponentName) { 10733 currApp.importanceReasonComponent = (ComponentName)app.adjTarget; 10734 } 10735 //Slog.v(TAG, "Proc " + app.processName + ": imp=" + currApp.importance 10736 // + " lru=" + currApp.lru); 10737 if (runList == null) { 10738 runList = new ArrayList<ActivityManager.RunningAppProcessInfo>(); 10739 } 10740 runList.add(currApp); 10741 } 10742 } 10743 } 10744 return runList; 10745 } 10746 10747 public List<ApplicationInfo> getRunningExternalApplications() { 10748 enforceNotIsolatedCaller("getRunningExternalApplications"); 10749 List<ActivityManager.RunningAppProcessInfo> runningApps = getRunningAppProcesses(); 10750 List<ApplicationInfo> retList = new ArrayList<ApplicationInfo>(); 10751 if (runningApps != null && runningApps.size() > 0) { 10752 Set<String> extList = new HashSet<String>(); 10753 for (ActivityManager.RunningAppProcessInfo app : runningApps) { 10754 if (app.pkgList != null) { 10755 for (String pkg : app.pkgList) { 10756 extList.add(pkg); 10757 } 10758 } 10759 } 10760 IPackageManager pm = AppGlobals.getPackageManager(); 10761 for (String pkg : extList) { 10762 try { 10763 ApplicationInfo info = pm.getApplicationInfo(pkg, 0, UserHandle.getCallingUserId()); 10764 if ((info.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0) { 10765 retList.add(info); 10766 } 10767 } catch (RemoteException e) { 10768 } 10769 } 10770 } 10771 return retList; 10772 } 10773 10774 @Override 10775 public void getMyMemoryState(ActivityManager.RunningAppProcessInfo outInfo) { 10776 enforceNotIsolatedCaller("getMyMemoryState"); 10777 synchronized (this) { 10778 ProcessRecord proc; 10779 synchronized (mPidsSelfLocked) { 10780 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 10781 } 10782 fillInProcMemInfo(proc, outInfo); 10783 } 10784 } 10785 10786 @Override 10787 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 10788 if (checkCallingPermission(android.Manifest.permission.DUMP) 10789 != PackageManager.PERMISSION_GRANTED) { 10790 pw.println("Permission Denial: can't dump ActivityManager from from pid=" 10791 + Binder.getCallingPid() 10792 + ", uid=" + Binder.getCallingUid() 10793 + " without permission " 10794 + android.Manifest.permission.DUMP); 10795 return; 10796 } 10797 10798 boolean dumpAll = false; 10799 boolean dumpClient = false; 10800 String dumpPackage = null; 10801 10802 int opti = 0; 10803 while (opti < args.length) { 10804 String opt = args[opti]; 10805 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 10806 break; 10807 } 10808 opti++; 10809 if ("-a".equals(opt)) { 10810 dumpAll = true; 10811 } else if ("-c".equals(opt)) { 10812 dumpClient = true; 10813 } else if ("-h".equals(opt)) { 10814 pw.println("Activity manager dump options:"); 10815 pw.println(" [-a] [-c] [-h] [cmd] ..."); 10816 pw.println(" cmd may be one of:"); 10817 pw.println(" a[ctivities]: activity stack state"); 10818 pw.println(" b[roadcasts] [PACKAGE_NAME] [history [-s]]: broadcast state"); 10819 pw.println(" i[ntents] [PACKAGE_NAME]: pending intent state"); 10820 pw.println(" p[rocesses] [PACKAGE_NAME]: process state"); 10821 pw.println(" o[om]: out of memory management"); 10822 pw.println(" prov[iders] [COMP_SPEC ...]: content provider state"); 10823 pw.println(" provider [COMP_SPEC]: provider client-side state"); 10824 pw.println(" s[ervices] [COMP_SPEC ...]: service state"); 10825 pw.println(" service [COMP_SPEC]: service client-side state"); 10826 pw.println(" package [PACKAGE_NAME]: all state related to given package"); 10827 pw.println(" all: dump all activities"); 10828 pw.println(" top: dump the top activity"); 10829 pw.println(" cmd may also be a COMP_SPEC to dump activities."); 10830 pw.println(" COMP_SPEC may be a component name (com.foo/.myApp),"); 10831 pw.println(" a partial substring in a component name, a"); 10832 pw.println(" hex object identifier."); 10833 pw.println(" -a: include all available server state."); 10834 pw.println(" -c: include client state."); 10835 return; 10836 } else { 10837 pw.println("Unknown argument: " + opt + "; use -h for help"); 10838 } 10839 } 10840 10841 long origId = Binder.clearCallingIdentity(); 10842 boolean more = false; 10843 // Is the caller requesting to dump a particular piece of data? 10844 if (opti < args.length) { 10845 String cmd = args[opti]; 10846 opti++; 10847 if ("activities".equals(cmd) || "a".equals(cmd)) { 10848 synchronized (this) { 10849 dumpActivitiesLocked(fd, pw, args, opti, true, dumpClient, null); 10850 } 10851 } else if ("broadcasts".equals(cmd) || "b".equals(cmd)) { 10852 String[] newArgs; 10853 String name; 10854 if (opti >= args.length) { 10855 name = null; 10856 newArgs = EMPTY_STRING_ARRAY; 10857 } else { 10858 name = args[opti]; 10859 opti++; 10860 newArgs = new String[args.length - opti]; 10861 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 10862 args.length - opti); 10863 } 10864 synchronized (this) { 10865 dumpBroadcastsLocked(fd, pw, args, opti, true, name); 10866 } 10867 } else if ("intents".equals(cmd) || "i".equals(cmd)) { 10868 String[] newArgs; 10869 String name; 10870 if (opti >= args.length) { 10871 name = null; 10872 newArgs = EMPTY_STRING_ARRAY; 10873 } else { 10874 name = args[opti]; 10875 opti++; 10876 newArgs = new String[args.length - opti]; 10877 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 10878 args.length - opti); 10879 } 10880 synchronized (this) { 10881 dumpPendingIntentsLocked(fd, pw, args, opti, true, name); 10882 } 10883 } else if ("processes".equals(cmd) || "p".equals(cmd)) { 10884 String[] newArgs; 10885 String name; 10886 if (opti >= args.length) { 10887 name = null; 10888 newArgs = EMPTY_STRING_ARRAY; 10889 } else { 10890 name = args[opti]; 10891 opti++; 10892 newArgs = new String[args.length - opti]; 10893 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 10894 args.length - opti); 10895 } 10896 synchronized (this) { 10897 dumpProcessesLocked(fd, pw, args, opti, true, name); 10898 } 10899 } else if ("oom".equals(cmd) || "o".equals(cmd)) { 10900 synchronized (this) { 10901 dumpOomLocked(fd, pw, args, opti, true); 10902 } 10903 } else if ("provider".equals(cmd)) { 10904 String[] newArgs; 10905 String name; 10906 if (opti >= args.length) { 10907 name = null; 10908 newArgs = EMPTY_STRING_ARRAY; 10909 } else { 10910 name = args[opti]; 10911 opti++; 10912 newArgs = new String[args.length - opti]; 10913 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, args.length - opti); 10914 } 10915 if (!dumpProvider(fd, pw, name, newArgs, 0, dumpAll)) { 10916 pw.println("No providers match: " + name); 10917 pw.println("Use -h for help."); 10918 } 10919 } else if ("providers".equals(cmd) || "prov".equals(cmd)) { 10920 synchronized (this) { 10921 dumpProvidersLocked(fd, pw, args, opti, true, null); 10922 } 10923 } else if ("service".equals(cmd)) { 10924 String[] newArgs; 10925 String name; 10926 if (opti >= args.length) { 10927 name = null; 10928 newArgs = EMPTY_STRING_ARRAY; 10929 } else { 10930 name = args[opti]; 10931 opti++; 10932 newArgs = new String[args.length - opti]; 10933 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 10934 args.length - opti); 10935 } 10936 if (!mServices.dumpService(fd, pw, name, newArgs, 0, dumpAll)) { 10937 pw.println("No services match: " + name); 10938 pw.println("Use -h for help."); 10939 } 10940 } else if ("package".equals(cmd)) { 10941 String[] newArgs; 10942 if (opti >= args.length) { 10943 pw.println("package: no package name specified"); 10944 pw.println("Use -h for help."); 10945 } else { 10946 dumpPackage = args[opti]; 10947 opti++; 10948 newArgs = new String[args.length - opti]; 10949 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 10950 args.length - opti); 10951 args = newArgs; 10952 opti = 0; 10953 more = true; 10954 } 10955 } else if ("services".equals(cmd) || "s".equals(cmd)) { 10956 synchronized (this) { 10957 mServices.dumpServicesLocked(fd, pw, args, opti, true, dumpClient, null); 10958 } 10959 } else { 10960 // Dumping a single activity? 10961 if (!dumpActivity(fd, pw, cmd, args, opti, dumpAll)) { 10962 pw.println("Bad activity command, or no activities match: " + cmd); 10963 pw.println("Use -h for help."); 10964 } 10965 } 10966 if (!more) { 10967 Binder.restoreCallingIdentity(origId); 10968 return; 10969 } 10970 } 10971 10972 // No piece of data specified, dump everything. 10973 synchronized (this) { 10974 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 10975 pw.println(); 10976 if (dumpAll) { 10977 pw.println("-------------------------------------------------------------------------------"); 10978 } 10979 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 10980 pw.println(); 10981 if (dumpAll) { 10982 pw.println("-------------------------------------------------------------------------------"); 10983 } 10984 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage); 10985 pw.println(); 10986 if (dumpAll) { 10987 pw.println("-------------------------------------------------------------------------------"); 10988 } 10989 mServices.dumpServicesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 10990 pw.println(); 10991 if (dumpAll) { 10992 pw.println("-------------------------------------------------------------------------------"); 10993 } 10994 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 10995 pw.println(); 10996 if (dumpAll) { 10997 pw.println("-------------------------------------------------------------------------------"); 10998 } 10999 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11000 } 11001 Binder.restoreCallingIdentity(origId); 11002 } 11003 11004 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11005 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) { 11006 pw.println("ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)"); 11007 11008 boolean printedAnything = mStackSupervisor.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient, 11009 dumpPackage); 11010 boolean needSep = printedAnything; 11011 11012 boolean printed = ActivityStackSupervisor.printThisActivity(pw, mFocusedActivity, 11013 dumpPackage, needSep, " mFocusedActivity: "); 11014 if (printed) { 11015 printedAnything = true; 11016 needSep = false; 11017 } 11018 11019 if (dumpPackage == null) { 11020 if (needSep) { 11021 pw.println(); 11022 } 11023 needSep = true; 11024 printedAnything = true; 11025 mStackSupervisor.dump(pw, " "); 11026 } 11027 11028 if (mRecentTasks.size() > 0) { 11029 boolean printedHeader = false; 11030 11031 final int N = mRecentTasks.size(); 11032 for (int i=0; i<N; i++) { 11033 TaskRecord tr = mRecentTasks.get(i); 11034 if (dumpPackage != null) { 11035 if (tr.realActivity == null || 11036 !dumpPackage.equals(tr.realActivity)) { 11037 continue; 11038 } 11039 } 11040 if (!printedHeader) { 11041 if (needSep) { 11042 pw.println(); 11043 } 11044 pw.println(" Recent tasks:"); 11045 printedHeader = true; 11046 printedAnything = true; 11047 } 11048 pw.print(" * Recent #"); pw.print(i); pw.print(": "); 11049 pw.println(tr); 11050 if (dumpAll) { 11051 mRecentTasks.get(i).dump(pw, " "); 11052 } 11053 } 11054 } 11055 11056 if (!printedAnything) { 11057 pw.println(" (nothing)"); 11058 } 11059 } 11060 11061 void dumpProcessesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11062 int opti, boolean dumpAll, String dumpPackage) { 11063 boolean needSep = false; 11064 boolean printedAnything = false; 11065 int numPers = 0; 11066 11067 pw.println("ACTIVITY MANAGER RUNNING PROCESSES (dumpsys activity processes)"); 11068 11069 if (dumpAll) { 11070 final int NP = mProcessNames.getMap().size(); 11071 for (int ip=0; ip<NP; ip++) { 11072 SparseArray<ProcessRecord> procs = mProcessNames.getMap().valueAt(ip); 11073 final int NA = procs.size(); 11074 for (int ia=0; ia<NA; ia++) { 11075 ProcessRecord r = procs.valueAt(ia); 11076 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11077 continue; 11078 } 11079 if (!needSep) { 11080 pw.println(" All known processes:"); 11081 needSep = true; 11082 printedAnything = true; 11083 } 11084 pw.print(r.persistent ? " *PERS*" : " *APP*"); 11085 pw.print(" UID "); pw.print(procs.keyAt(ia)); 11086 pw.print(" "); pw.println(r); 11087 r.dump(pw, " "); 11088 if (r.persistent) { 11089 numPers++; 11090 } 11091 } 11092 } 11093 } 11094 11095 if (mIsolatedProcesses.size() > 0) { 11096 boolean printed = false; 11097 for (int i=0; i<mIsolatedProcesses.size(); i++) { 11098 ProcessRecord r = mIsolatedProcesses.valueAt(i); 11099 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11100 continue; 11101 } 11102 if (!printed) { 11103 if (needSep) { 11104 pw.println(); 11105 } 11106 pw.println(" Isolated process list (sorted by uid):"); 11107 printedAnything = true; 11108 printed = true; 11109 needSep = true; 11110 } 11111 pw.println(String.format("%sIsolated #%2d: %s", 11112 " ", i, r.toString())); 11113 } 11114 } 11115 11116 if (mLruProcesses.size() > 0) { 11117 if (needSep) { 11118 pw.println(); 11119 } 11120 pw.print(" Process LRU list (sorted by oom_adj, "); pw.print(mLruProcesses.size()); 11121 pw.print(" total, non-act at "); 11122 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 11123 pw.print(", non-svc at "); 11124 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 11125 pw.println("):"); 11126 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", false, dumpPackage); 11127 needSep = true; 11128 printedAnything = true; 11129 } 11130 11131 if (dumpAll || dumpPackage != null) { 11132 synchronized (mPidsSelfLocked) { 11133 boolean printed = false; 11134 for (int i=0; i<mPidsSelfLocked.size(); i++) { 11135 ProcessRecord r = mPidsSelfLocked.valueAt(i); 11136 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11137 continue; 11138 } 11139 if (!printed) { 11140 if (needSep) pw.println(); 11141 needSep = true; 11142 pw.println(" PID mappings:"); 11143 printed = true; 11144 printedAnything = true; 11145 } 11146 pw.print(" PID #"); pw.print(mPidsSelfLocked.keyAt(i)); 11147 pw.print(": "); pw.println(mPidsSelfLocked.valueAt(i)); 11148 } 11149 } 11150 } 11151 11152 if (mForegroundProcesses.size() > 0) { 11153 synchronized (mPidsSelfLocked) { 11154 boolean printed = false; 11155 for (int i=0; i<mForegroundProcesses.size(); i++) { 11156 ProcessRecord r = mPidsSelfLocked.get( 11157 mForegroundProcesses.valueAt(i).pid); 11158 if (dumpPackage != null && (r == null 11159 || !r.pkgList.containsKey(dumpPackage))) { 11160 continue; 11161 } 11162 if (!printed) { 11163 if (needSep) pw.println(); 11164 needSep = true; 11165 pw.println(" Foreground Processes:"); 11166 printed = true; 11167 printedAnything = true; 11168 } 11169 pw.print(" PID #"); pw.print(mForegroundProcesses.keyAt(i)); 11170 pw.print(": "); pw.println(mForegroundProcesses.valueAt(i)); 11171 } 11172 } 11173 } 11174 11175 if (mPersistentStartingProcesses.size() > 0) { 11176 if (needSep) pw.println(); 11177 needSep = true; 11178 printedAnything = true; 11179 pw.println(" Persisent processes that are starting:"); 11180 dumpProcessList(pw, this, mPersistentStartingProcesses, " ", 11181 "Starting Norm", "Restarting PERS", dumpPackage); 11182 } 11183 11184 if (mRemovedProcesses.size() > 0) { 11185 if (needSep) pw.println(); 11186 needSep = true; 11187 printedAnything = true; 11188 pw.println(" Processes that are being removed:"); 11189 dumpProcessList(pw, this, mRemovedProcesses, " ", 11190 "Removed Norm", "Removed PERS", dumpPackage); 11191 } 11192 11193 if (mProcessesOnHold.size() > 0) { 11194 if (needSep) pw.println(); 11195 needSep = true; 11196 printedAnything = true; 11197 pw.println(" Processes that are on old until the system is ready:"); 11198 dumpProcessList(pw, this, mProcessesOnHold, " ", 11199 "OnHold Norm", "OnHold PERS", dumpPackage); 11200 } 11201 11202 needSep = dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, dumpPackage); 11203 11204 if (mProcessCrashTimes.getMap().size() > 0) { 11205 boolean printed = false; 11206 long now = SystemClock.uptimeMillis(); 11207 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 11208 final int NP = pmap.size(); 11209 for (int ip=0; ip<NP; ip++) { 11210 String pname = pmap.keyAt(ip); 11211 SparseArray<Long> uids = pmap.valueAt(ip); 11212 final int N = uids.size(); 11213 for (int i=0; i<N; i++) { 11214 int puid = uids.keyAt(i); 11215 ProcessRecord r = mProcessNames.get(pname, puid); 11216 if (dumpPackage != null && (r == null 11217 || !r.pkgList.containsKey(dumpPackage))) { 11218 continue; 11219 } 11220 if (!printed) { 11221 if (needSep) pw.println(); 11222 needSep = true; 11223 pw.println(" Time since processes crashed:"); 11224 printed = true; 11225 printedAnything = true; 11226 } 11227 pw.print(" Process "); pw.print(pname); 11228 pw.print(" uid "); pw.print(puid); 11229 pw.print(": last crashed "); 11230 TimeUtils.formatDuration(now-uids.valueAt(i), pw); 11231 pw.println(" ago"); 11232 } 11233 } 11234 } 11235 11236 if (mBadProcesses.getMap().size() > 0) { 11237 boolean printed = false; 11238 final ArrayMap<String, SparseArray<BadProcessInfo>> pmap = mBadProcesses.getMap(); 11239 final int NP = pmap.size(); 11240 for (int ip=0; ip<NP; ip++) { 11241 String pname = pmap.keyAt(ip); 11242 SparseArray<BadProcessInfo> uids = pmap.valueAt(ip); 11243 final int N = uids.size(); 11244 for (int i=0; i<N; i++) { 11245 int puid = uids.keyAt(i); 11246 ProcessRecord r = mProcessNames.get(pname, puid); 11247 if (dumpPackage != null && (r == null 11248 || !r.pkgList.containsKey(dumpPackage))) { 11249 continue; 11250 } 11251 if (!printed) { 11252 if (needSep) pw.println(); 11253 needSep = true; 11254 pw.println(" Bad processes:"); 11255 printedAnything = true; 11256 } 11257 BadProcessInfo info = uids.valueAt(i); 11258 pw.print(" Bad process "); pw.print(pname); 11259 pw.print(" uid "); pw.print(puid); 11260 pw.print(": crashed at time "); pw.println(info.time); 11261 if (info.shortMsg != null) { 11262 pw.print(" Short msg: "); pw.println(info.shortMsg); 11263 } 11264 if (info.longMsg != null) { 11265 pw.print(" Long msg: "); pw.println(info.longMsg); 11266 } 11267 if (info.stack != null) { 11268 pw.println(" Stack:"); 11269 int lastPos = 0; 11270 for (int pos=0; pos<info.stack.length(); pos++) { 11271 if (info.stack.charAt(pos) == '\n') { 11272 pw.print(" "); 11273 pw.write(info.stack, lastPos, pos-lastPos); 11274 pw.println(); 11275 lastPos = pos+1; 11276 } 11277 } 11278 if (lastPos < info.stack.length()) { 11279 pw.print(" "); 11280 pw.write(info.stack, lastPos, info.stack.length()-lastPos); 11281 pw.println(); 11282 } 11283 } 11284 } 11285 } 11286 } 11287 11288 if (dumpPackage == null) { 11289 pw.println(); 11290 needSep = false; 11291 pw.println(" mStartedUsers:"); 11292 for (int i=0; i<mStartedUsers.size(); i++) { 11293 UserStartedState uss = mStartedUsers.valueAt(i); 11294 pw.print(" User #"); pw.print(uss.mHandle.getIdentifier()); 11295 pw.print(": "); uss.dump("", pw); 11296 } 11297 pw.print(" mStartedUserArray: ["); 11298 for (int i=0; i<mStartedUserArray.length; i++) { 11299 if (i > 0) pw.print(", "); 11300 pw.print(mStartedUserArray[i]); 11301 } 11302 pw.println("]"); 11303 pw.print(" mUserLru: ["); 11304 for (int i=0; i<mUserLru.size(); i++) { 11305 if (i > 0) pw.print(", "); 11306 pw.print(mUserLru.get(i)); 11307 } 11308 pw.println("]"); 11309 if (dumpAll) { 11310 pw.print(" mStartedUserArray: "); pw.println(Arrays.toString(mStartedUserArray)); 11311 } 11312 } 11313 if (mHomeProcess != null && (dumpPackage == null 11314 || mHomeProcess.pkgList.containsKey(dumpPackage))) { 11315 if (needSep) { 11316 pw.println(); 11317 needSep = false; 11318 } 11319 pw.println(" mHomeProcess: " + mHomeProcess); 11320 } 11321 if (mPreviousProcess != null && (dumpPackage == null 11322 || mPreviousProcess.pkgList.containsKey(dumpPackage))) { 11323 if (needSep) { 11324 pw.println(); 11325 needSep = false; 11326 } 11327 pw.println(" mPreviousProcess: " + mPreviousProcess); 11328 } 11329 if (dumpAll) { 11330 StringBuilder sb = new StringBuilder(128); 11331 sb.append(" mPreviousProcessVisibleTime: "); 11332 TimeUtils.formatDuration(mPreviousProcessVisibleTime, sb); 11333 pw.println(sb); 11334 } 11335 if (mHeavyWeightProcess != null && (dumpPackage == null 11336 || mHeavyWeightProcess.pkgList.containsKey(dumpPackage))) { 11337 if (needSep) { 11338 pw.println(); 11339 needSep = false; 11340 } 11341 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 11342 } 11343 if (dumpPackage == null) { 11344 pw.println(" mConfiguration: " + mConfiguration); 11345 } 11346 if (dumpAll) { 11347 pw.println(" mConfigWillChange: " + getFocusedStack().mConfigWillChange); 11348 if (mCompatModePackages.getPackages().size() > 0) { 11349 boolean printed = false; 11350 for (Map.Entry<String, Integer> entry 11351 : mCompatModePackages.getPackages().entrySet()) { 11352 String pkg = entry.getKey(); 11353 int mode = entry.getValue(); 11354 if (dumpPackage != null && !dumpPackage.equals(pkg)) { 11355 continue; 11356 } 11357 if (!printed) { 11358 pw.println(" mScreenCompatPackages:"); 11359 printed = true; 11360 } 11361 pw.print(" "); pw.print(pkg); pw.print(": "); 11362 pw.print(mode); pw.println(); 11363 } 11364 } 11365 } 11366 if (dumpPackage == null) { 11367 if (mSleeping || mWentToSleep || mLockScreenShown) { 11368 pw.println(" mSleeping=" + mSleeping + " mWentToSleep=" + mWentToSleep 11369 + " mLockScreenShown " + mLockScreenShown); 11370 } 11371 if (mShuttingDown || mRunningVoice) { 11372 pw.print(" mShuttingDown=" + mShuttingDown + " mRunningVoice=" + mRunningVoice); 11373 } 11374 } 11375 if (mDebugApp != null || mOrigDebugApp != null || mDebugTransient 11376 || mOrigWaitForDebugger) { 11377 if (dumpPackage == null || dumpPackage.equals(mDebugApp) 11378 || dumpPackage.equals(mOrigDebugApp)) { 11379 if (needSep) { 11380 pw.println(); 11381 needSep = false; 11382 } 11383 pw.println(" mDebugApp=" + mDebugApp + "/orig=" + mOrigDebugApp 11384 + " mDebugTransient=" + mDebugTransient 11385 + " mOrigWaitForDebugger=" + mOrigWaitForDebugger); 11386 } 11387 } 11388 if (mOpenGlTraceApp != null) { 11389 if (dumpPackage == null || dumpPackage.equals(mOpenGlTraceApp)) { 11390 if (needSep) { 11391 pw.println(); 11392 needSep = false; 11393 } 11394 pw.println(" mOpenGlTraceApp=" + mOpenGlTraceApp); 11395 } 11396 } 11397 if (mProfileApp != null || mProfileProc != null || mProfileFile != null 11398 || mProfileFd != null) { 11399 if (dumpPackage == null || dumpPackage.equals(mProfileApp)) { 11400 if (needSep) { 11401 pw.println(); 11402 needSep = false; 11403 } 11404 pw.println(" mProfileApp=" + mProfileApp + " mProfileProc=" + mProfileProc); 11405 pw.println(" mProfileFile=" + mProfileFile + " mProfileFd=" + mProfileFd); 11406 pw.println(" mProfileType=" + mProfileType + " mAutoStopProfiler=" 11407 + mAutoStopProfiler); 11408 } 11409 } 11410 if (dumpPackage == null) { 11411 if (mAlwaysFinishActivities || mController != null) { 11412 pw.println(" mAlwaysFinishActivities=" + mAlwaysFinishActivities 11413 + " mController=" + mController); 11414 } 11415 if (dumpAll) { 11416 pw.println(" Total persistent processes: " + numPers); 11417 pw.println(" mProcessesReady=" + mProcessesReady 11418 + " mSystemReady=" + mSystemReady); 11419 pw.println(" mBooting=" + mBooting 11420 + " mBooted=" + mBooted 11421 + " mFactoryTest=" + mFactoryTest); 11422 pw.print(" mLastPowerCheckRealtime="); 11423 TimeUtils.formatDuration(mLastPowerCheckRealtime, pw); 11424 pw.println(""); 11425 pw.print(" mLastPowerCheckUptime="); 11426 TimeUtils.formatDuration(mLastPowerCheckUptime, pw); 11427 pw.println(""); 11428 pw.println(" mGoingToSleep=" + mStackSupervisor.mGoingToSleep); 11429 pw.println(" mLaunchingActivity=" + mStackSupervisor.mLaunchingActivity); 11430 pw.println(" mAdjSeq=" + mAdjSeq + " mLruSeq=" + mLruSeq); 11431 pw.println(" mNumNonCachedProcs=" + mNumNonCachedProcs 11432 + " (" + mLruProcesses.size() + " total)" 11433 + " mNumCachedHiddenProcs=" + mNumCachedHiddenProcs 11434 + " mNumServiceProcs=" + mNumServiceProcs 11435 + " mNewNumServiceProcs=" + mNewNumServiceProcs); 11436 pw.println(" mAllowLowerMemLevel=" + mAllowLowerMemLevel 11437 + " mLastMemoryLevel" + mLastMemoryLevel 11438 + " mLastNumProcesses" + mLastNumProcesses); 11439 long now = SystemClock.uptimeMillis(); 11440 pw.print(" mLastIdleTime="); 11441 TimeUtils.formatDuration(now, mLastIdleTime, pw); 11442 pw.print(" mLowRamSinceLastIdle="); 11443 TimeUtils.formatDuration(getLowRamTimeSinceIdle(now), pw); 11444 pw.println(); 11445 } 11446 } 11447 11448 if (!printedAnything) { 11449 pw.println(" (nothing)"); 11450 } 11451 } 11452 11453 boolean dumpProcessesToGc(FileDescriptor fd, PrintWriter pw, String[] args, 11454 int opti, boolean needSep, boolean dumpAll, String dumpPackage) { 11455 if (mProcessesToGc.size() > 0) { 11456 boolean printed = false; 11457 long now = SystemClock.uptimeMillis(); 11458 for (int i=0; i<mProcessesToGc.size(); i++) { 11459 ProcessRecord proc = mProcessesToGc.get(i); 11460 if (dumpPackage != null && !dumpPackage.equals(proc.info.packageName)) { 11461 continue; 11462 } 11463 if (!printed) { 11464 if (needSep) pw.println(); 11465 needSep = true; 11466 pw.println(" Processes that are waiting to GC:"); 11467 printed = true; 11468 } 11469 pw.print(" Process "); pw.println(proc); 11470 pw.print(" lowMem="); pw.print(proc.reportLowMemory); 11471 pw.print(", last gced="); 11472 pw.print(now-proc.lastRequestedGc); 11473 pw.print(" ms ago, last lowMem="); 11474 pw.print(now-proc.lastLowMemory); 11475 pw.println(" ms ago"); 11476 11477 } 11478 } 11479 return needSep; 11480 } 11481 11482 void printOomLevel(PrintWriter pw, String name, int adj) { 11483 pw.print(" "); 11484 if (adj >= 0) { 11485 pw.print(' '); 11486 if (adj < 10) pw.print(' '); 11487 } else { 11488 if (adj > -10) pw.print(' '); 11489 } 11490 pw.print(adj); 11491 pw.print(": "); 11492 pw.print(name); 11493 pw.print(" ("); 11494 pw.print(mProcessList.getMemLevel(adj)/1024); 11495 pw.println(" kB)"); 11496 } 11497 11498 boolean dumpOomLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11499 int opti, boolean dumpAll) { 11500 boolean needSep = false; 11501 11502 if (mLruProcesses.size() > 0) { 11503 if (needSep) pw.println(); 11504 needSep = true; 11505 pw.println(" OOM levels:"); 11506 printOomLevel(pw, "SYSTEM_ADJ", ProcessList.SYSTEM_ADJ); 11507 printOomLevel(pw, "PERSISTENT_PROC_ADJ", ProcessList.PERSISTENT_PROC_ADJ); 11508 printOomLevel(pw, "FOREGROUND_APP_ADJ", ProcessList.FOREGROUND_APP_ADJ); 11509 printOomLevel(pw, "VISIBLE_APP_ADJ", ProcessList.VISIBLE_APP_ADJ); 11510 printOomLevel(pw, "PERCEPTIBLE_APP_ADJ", ProcessList.PERCEPTIBLE_APP_ADJ); 11511 printOomLevel(pw, "BACKUP_APP_ADJ", ProcessList.BACKUP_APP_ADJ); 11512 printOomLevel(pw, "HEAVY_WEIGHT_APP_ADJ", ProcessList.HEAVY_WEIGHT_APP_ADJ); 11513 printOomLevel(pw, "SERVICE_ADJ", ProcessList.SERVICE_ADJ); 11514 printOomLevel(pw, "HOME_APP_ADJ", ProcessList.HOME_APP_ADJ); 11515 printOomLevel(pw, "PREVIOUS_APP_ADJ", ProcessList.PREVIOUS_APP_ADJ); 11516 printOomLevel(pw, "SERVICE_B_ADJ", ProcessList.SERVICE_B_ADJ); 11517 printOomLevel(pw, "CACHED_APP_MIN_ADJ", ProcessList.CACHED_APP_MIN_ADJ); 11518 printOomLevel(pw, "CACHED_APP_MAX_ADJ", ProcessList.CACHED_APP_MAX_ADJ); 11519 11520 if (needSep) pw.println(); 11521 pw.print(" Process OOM control ("); pw.print(mLruProcesses.size()); 11522 pw.print(" total, non-act at "); 11523 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 11524 pw.print(", non-svc at "); 11525 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 11526 pw.println("):"); 11527 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", true, null); 11528 needSep = true; 11529 } 11530 11531 dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, null); 11532 11533 pw.println(); 11534 pw.println(" mHomeProcess: " + mHomeProcess); 11535 pw.println(" mPreviousProcess: " + mPreviousProcess); 11536 if (mHeavyWeightProcess != null) { 11537 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 11538 } 11539 11540 return true; 11541 } 11542 11543 /** 11544 * There are three ways to call this: 11545 * - no provider specified: dump all the providers 11546 * - a flattened component name that matched an existing provider was specified as the 11547 * first arg: dump that one provider 11548 * - the first arg isn't the flattened component name of an existing provider: 11549 * dump all providers whose component contains the first arg as a substring 11550 */ 11551 protected boolean dumpProvider(FileDescriptor fd, PrintWriter pw, String name, String[] args, 11552 int opti, boolean dumpAll) { 11553 return mProviderMap.dumpProvider(fd, pw, name, args, opti, dumpAll); 11554 } 11555 11556 static class ItemMatcher { 11557 ArrayList<ComponentName> components; 11558 ArrayList<String> strings; 11559 ArrayList<Integer> objects; 11560 boolean all; 11561 11562 ItemMatcher() { 11563 all = true; 11564 } 11565 11566 void build(String name) { 11567 ComponentName componentName = ComponentName.unflattenFromString(name); 11568 if (componentName != null) { 11569 if (components == null) { 11570 components = new ArrayList<ComponentName>(); 11571 } 11572 components.add(componentName); 11573 all = false; 11574 } else { 11575 int objectId = 0; 11576 // Not a '/' separated full component name; maybe an object ID? 11577 try { 11578 objectId = Integer.parseInt(name, 16); 11579 if (objects == null) { 11580 objects = new ArrayList<Integer>(); 11581 } 11582 objects.add(objectId); 11583 all = false; 11584 } catch (RuntimeException e) { 11585 // Not an integer; just do string match. 11586 if (strings == null) { 11587 strings = new ArrayList<String>(); 11588 } 11589 strings.add(name); 11590 all = false; 11591 } 11592 } 11593 } 11594 11595 int build(String[] args, int opti) { 11596 for (; opti<args.length; opti++) { 11597 String name = args[opti]; 11598 if ("--".equals(name)) { 11599 return opti+1; 11600 } 11601 build(name); 11602 } 11603 return opti; 11604 } 11605 11606 boolean match(Object object, ComponentName comp) { 11607 if (all) { 11608 return true; 11609 } 11610 if (components != null) { 11611 for (int i=0; i<components.size(); i++) { 11612 if (components.get(i).equals(comp)) { 11613 return true; 11614 } 11615 } 11616 } 11617 if (objects != null) { 11618 for (int i=0; i<objects.size(); i++) { 11619 if (System.identityHashCode(object) == objects.get(i)) { 11620 return true; 11621 } 11622 } 11623 } 11624 if (strings != null) { 11625 String flat = comp.flattenToString(); 11626 for (int i=0; i<strings.size(); i++) { 11627 if (flat.contains(strings.get(i))) { 11628 return true; 11629 } 11630 } 11631 } 11632 return false; 11633 } 11634 } 11635 11636 /** 11637 * There are three things that cmd can be: 11638 * - a flattened component name that matches an existing activity 11639 * - the cmd arg isn't the flattened component name of an existing activity: 11640 * dump all activity whose component contains the cmd as a substring 11641 * - A hex number of the ActivityRecord object instance. 11642 */ 11643 protected boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name, String[] args, 11644 int opti, boolean dumpAll) { 11645 ArrayList<ActivityRecord> activities; 11646 11647 synchronized (this) { 11648 activities = mStackSupervisor.getDumpActivitiesLocked(name); 11649 } 11650 11651 if (activities.size() <= 0) { 11652 return false; 11653 } 11654 11655 String[] newArgs = new String[args.length - opti]; 11656 System.arraycopy(args, opti, newArgs, 0, args.length - opti); 11657 11658 TaskRecord lastTask = null; 11659 boolean needSep = false; 11660 for (int i=activities.size()-1; i>=0; i--) { 11661 ActivityRecord r = activities.get(i); 11662 if (needSep) { 11663 pw.println(); 11664 } 11665 needSep = true; 11666 synchronized (this) { 11667 if (lastTask != r.task) { 11668 lastTask = r.task; 11669 pw.print("TASK "); pw.print(lastTask.affinity); 11670 pw.print(" id="); pw.println(lastTask.taskId); 11671 if (dumpAll) { 11672 lastTask.dump(pw, " "); 11673 } 11674 } 11675 } 11676 dumpActivity(" ", fd, pw, activities.get(i), newArgs, dumpAll); 11677 } 11678 return true; 11679 } 11680 11681 /** 11682 * Invokes IApplicationThread.dumpActivity() on the thread of the specified activity if 11683 * there is a thread associated with the activity. 11684 */ 11685 private void dumpActivity(String prefix, FileDescriptor fd, PrintWriter pw, 11686 final ActivityRecord r, String[] args, boolean dumpAll) { 11687 String innerPrefix = prefix + " "; 11688 synchronized (this) { 11689 pw.print(prefix); pw.print("ACTIVITY "); pw.print(r.shortComponentName); 11690 pw.print(" "); pw.print(Integer.toHexString(System.identityHashCode(r))); 11691 pw.print(" pid="); 11692 if (r.app != null) pw.println(r.app.pid); 11693 else pw.println("(not running)"); 11694 if (dumpAll) { 11695 r.dump(pw, innerPrefix); 11696 } 11697 } 11698 if (r.app != null && r.app.thread != null) { 11699 // flush anything that is already in the PrintWriter since the thread is going 11700 // to write to the file descriptor directly 11701 pw.flush(); 11702 try { 11703 TransferPipe tp = new TransferPipe(); 11704 try { 11705 r.app.thread.dumpActivity(tp.getWriteFd().getFileDescriptor(), 11706 r.appToken, innerPrefix, args); 11707 tp.go(fd); 11708 } finally { 11709 tp.kill(); 11710 } 11711 } catch (IOException e) { 11712 pw.println(innerPrefix + "Failure while dumping the activity: " + e); 11713 } catch (RemoteException e) { 11714 pw.println(innerPrefix + "Got a RemoteException while dumping the activity"); 11715 } 11716 } 11717 } 11718 11719 void dumpBroadcastsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11720 int opti, boolean dumpAll, String dumpPackage) { 11721 boolean needSep = false; 11722 boolean onlyHistory = false; 11723 boolean printedAnything = false; 11724 11725 if ("history".equals(dumpPackage)) { 11726 if (opti < args.length && "-s".equals(args[opti])) { 11727 dumpAll = false; 11728 } 11729 onlyHistory = true; 11730 dumpPackage = null; 11731 } 11732 11733 pw.println("ACTIVITY MANAGER BROADCAST STATE (dumpsys activity broadcasts)"); 11734 if (!onlyHistory && dumpAll) { 11735 if (mRegisteredReceivers.size() > 0) { 11736 boolean printed = false; 11737 Iterator it = mRegisteredReceivers.values().iterator(); 11738 while (it.hasNext()) { 11739 ReceiverList r = (ReceiverList)it.next(); 11740 if (dumpPackage != null && (r.app == null || 11741 !dumpPackage.equals(r.app.info.packageName))) { 11742 continue; 11743 } 11744 if (!printed) { 11745 pw.println(" Registered Receivers:"); 11746 needSep = true; 11747 printed = true; 11748 printedAnything = true; 11749 } 11750 pw.print(" * "); pw.println(r); 11751 r.dump(pw, " "); 11752 } 11753 } 11754 11755 if (mReceiverResolver.dump(pw, needSep ? 11756 "\n Receiver Resolver Table:" : " Receiver Resolver Table:", 11757 " ", dumpPackage, false)) { 11758 needSep = true; 11759 printedAnything = true; 11760 } 11761 } 11762 11763 for (BroadcastQueue q : mBroadcastQueues) { 11764 needSep = q.dumpLocked(fd, pw, args, opti, dumpAll, dumpPackage, needSep); 11765 printedAnything |= needSep; 11766 } 11767 11768 needSep = true; 11769 11770 if (!onlyHistory && mStickyBroadcasts != null && dumpPackage == null) { 11771 for (int user=0; user<mStickyBroadcasts.size(); user++) { 11772 if (needSep) { 11773 pw.println(); 11774 } 11775 needSep = true; 11776 printedAnything = true; 11777 pw.print(" Sticky broadcasts for user "); 11778 pw.print(mStickyBroadcasts.keyAt(user)); pw.println(":"); 11779 StringBuilder sb = new StringBuilder(128); 11780 for (Map.Entry<String, ArrayList<Intent>> ent 11781 : mStickyBroadcasts.valueAt(user).entrySet()) { 11782 pw.print(" * Sticky action "); pw.print(ent.getKey()); 11783 if (dumpAll) { 11784 pw.println(":"); 11785 ArrayList<Intent> intents = ent.getValue(); 11786 final int N = intents.size(); 11787 for (int i=0; i<N; i++) { 11788 sb.setLength(0); 11789 sb.append(" Intent: "); 11790 intents.get(i).toShortString(sb, false, true, false, false); 11791 pw.println(sb.toString()); 11792 Bundle bundle = intents.get(i).getExtras(); 11793 if (bundle != null) { 11794 pw.print(" "); 11795 pw.println(bundle.toString()); 11796 } 11797 } 11798 } else { 11799 pw.println(""); 11800 } 11801 } 11802 } 11803 } 11804 11805 if (!onlyHistory && dumpAll) { 11806 pw.println(); 11807 for (BroadcastQueue queue : mBroadcastQueues) { 11808 pw.println(" mBroadcastsScheduled [" + queue.mQueueName + "]=" 11809 + queue.mBroadcastsScheduled); 11810 } 11811 pw.println(" mHandler:"); 11812 mHandler.dump(new PrintWriterPrinter(pw), " "); 11813 needSep = true; 11814 printedAnything = true; 11815 } 11816 11817 if (!printedAnything) { 11818 pw.println(" (nothing)"); 11819 } 11820 } 11821 11822 void dumpProvidersLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11823 int opti, boolean dumpAll, String dumpPackage) { 11824 boolean needSep; 11825 boolean printedAnything = false; 11826 11827 ItemMatcher matcher = new ItemMatcher(); 11828 matcher.build(args, opti); 11829 11830 pw.println("ACTIVITY MANAGER CONTENT PROVIDERS (dumpsys activity providers)"); 11831 11832 needSep = mProviderMap.dumpProvidersLocked(pw, dumpAll, dumpPackage); 11833 printedAnything |= needSep; 11834 11835 if (mLaunchingProviders.size() > 0) { 11836 boolean printed = false; 11837 for (int i=mLaunchingProviders.size()-1; i>=0; i--) { 11838 ContentProviderRecord r = mLaunchingProviders.get(i); 11839 if (dumpPackage != null && !dumpPackage.equals(r.name.getPackageName())) { 11840 continue; 11841 } 11842 if (!printed) { 11843 if (needSep) pw.println(); 11844 needSep = true; 11845 pw.println(" Launching content providers:"); 11846 printed = true; 11847 printedAnything = true; 11848 } 11849 pw.print(" Launching #"); pw.print(i); pw.print(": "); 11850 pw.println(r); 11851 } 11852 } 11853 11854 if (mGrantedUriPermissions.size() > 0) { 11855 boolean printed = false; 11856 int dumpUid = -2; 11857 if (dumpPackage != null) { 11858 try { 11859 dumpUid = mContext.getPackageManager().getPackageUid(dumpPackage, 0); 11860 } catch (NameNotFoundException e) { 11861 dumpUid = -1; 11862 } 11863 } 11864 for (int i=0; i<mGrantedUriPermissions.size(); i++) { 11865 int uid = mGrantedUriPermissions.keyAt(i); 11866 if (dumpUid >= -1 && UserHandle.getAppId(uid) != dumpUid) { 11867 continue; 11868 } 11869 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 11870 if (!printed) { 11871 if (needSep) pw.println(); 11872 needSep = true; 11873 pw.println(" Granted Uri Permissions:"); 11874 printed = true; 11875 printedAnything = true; 11876 } 11877 pw.print(" * UID "); pw.print(uid); pw.println(" holds:"); 11878 for (UriPermission perm : perms.values()) { 11879 pw.print(" "); pw.println(perm); 11880 if (dumpAll) { 11881 perm.dump(pw, " "); 11882 } 11883 } 11884 } 11885 } 11886 11887 if (!printedAnything) { 11888 pw.println(" (nothing)"); 11889 } 11890 } 11891 11892 void dumpPendingIntentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11893 int opti, boolean dumpAll, String dumpPackage) { 11894 boolean printed = false; 11895 11896 pw.println("ACTIVITY MANAGER PENDING INTENTS (dumpsys activity intents)"); 11897 11898 if (mIntentSenderRecords.size() > 0) { 11899 Iterator<WeakReference<PendingIntentRecord>> it 11900 = mIntentSenderRecords.values().iterator(); 11901 while (it.hasNext()) { 11902 WeakReference<PendingIntentRecord> ref = it.next(); 11903 PendingIntentRecord rec = ref != null ? ref.get(): null; 11904 if (dumpPackage != null && (rec == null 11905 || !dumpPackage.equals(rec.key.packageName))) { 11906 continue; 11907 } 11908 printed = true; 11909 if (rec != null) { 11910 pw.print(" * "); pw.println(rec); 11911 if (dumpAll) { 11912 rec.dump(pw, " "); 11913 } 11914 } else { 11915 pw.print(" * "); pw.println(ref); 11916 } 11917 } 11918 } 11919 11920 if (!printed) { 11921 pw.println(" (nothing)"); 11922 } 11923 } 11924 11925 private static final int dumpProcessList(PrintWriter pw, 11926 ActivityManagerService service, List list, 11927 String prefix, String normalLabel, String persistentLabel, 11928 String dumpPackage) { 11929 int numPers = 0; 11930 final int N = list.size()-1; 11931 for (int i=N; i>=0; i--) { 11932 ProcessRecord r = (ProcessRecord)list.get(i); 11933 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 11934 continue; 11935 } 11936 pw.println(String.format("%s%s #%2d: %s", 11937 prefix, (r.persistent ? persistentLabel : normalLabel), 11938 i, r.toString())); 11939 if (r.persistent) { 11940 numPers++; 11941 } 11942 } 11943 return numPers; 11944 } 11945 11946 private static final boolean dumpProcessOomList(PrintWriter pw, 11947 ActivityManagerService service, List<ProcessRecord> origList, 11948 String prefix, String normalLabel, String persistentLabel, 11949 boolean inclDetails, String dumpPackage) { 11950 11951 ArrayList<Pair<ProcessRecord, Integer>> list 11952 = new ArrayList<Pair<ProcessRecord, Integer>>(origList.size()); 11953 for (int i=0; i<origList.size(); i++) { 11954 ProcessRecord r = origList.get(i); 11955 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11956 continue; 11957 } 11958 list.add(new Pair<ProcessRecord, Integer>(origList.get(i), i)); 11959 } 11960 11961 if (list.size() <= 0) { 11962 return false; 11963 } 11964 11965 Comparator<Pair<ProcessRecord, Integer>> comparator 11966 = new Comparator<Pair<ProcessRecord, Integer>>() { 11967 @Override 11968 public int compare(Pair<ProcessRecord, Integer> object1, 11969 Pair<ProcessRecord, Integer> object2) { 11970 if (object1.first.setAdj != object2.first.setAdj) { 11971 return object1.first.setAdj > object2.first.setAdj ? -1 : 1; 11972 } 11973 if (object1.second.intValue() != object2.second.intValue()) { 11974 return object1.second.intValue() > object2.second.intValue() ? -1 : 1; 11975 } 11976 return 0; 11977 } 11978 }; 11979 11980 Collections.sort(list, comparator); 11981 11982 final long curRealtime = SystemClock.elapsedRealtime(); 11983 final long realtimeSince = curRealtime - service.mLastPowerCheckRealtime; 11984 final long curUptime = SystemClock.uptimeMillis(); 11985 final long uptimeSince = curUptime - service.mLastPowerCheckUptime; 11986 11987 for (int i=list.size()-1; i>=0; i--) { 11988 ProcessRecord r = list.get(i).first; 11989 String oomAdj = ProcessList.makeOomAdjString(r.setAdj); 11990 char schedGroup; 11991 switch (r.setSchedGroup) { 11992 case Process.THREAD_GROUP_BG_NONINTERACTIVE: 11993 schedGroup = 'B'; 11994 break; 11995 case Process.THREAD_GROUP_DEFAULT: 11996 schedGroup = 'F'; 11997 break; 11998 default: 11999 schedGroup = '?'; 12000 break; 12001 } 12002 char foreground; 12003 if (r.foregroundActivities) { 12004 foreground = 'A'; 12005 } else if (r.foregroundServices) { 12006 foreground = 'S'; 12007 } else { 12008 foreground = ' '; 12009 } 12010 String procState = ProcessList.makeProcStateString(r.curProcState); 12011 pw.print(prefix); 12012 pw.print(r.persistent ? persistentLabel : normalLabel); 12013 pw.print(" #"); 12014 int num = (origList.size()-1)-list.get(i).second; 12015 if (num < 10) pw.print(' '); 12016 pw.print(num); 12017 pw.print(": "); 12018 pw.print(oomAdj); 12019 pw.print(' '); 12020 pw.print(schedGroup); 12021 pw.print('/'); 12022 pw.print(foreground); 12023 pw.print('/'); 12024 pw.print(procState); 12025 pw.print(" trm:"); 12026 if (r.trimMemoryLevel < 10) pw.print(' '); 12027 pw.print(r.trimMemoryLevel); 12028 pw.print(' '); 12029 pw.print(r.toShortString()); 12030 pw.print(" ("); 12031 pw.print(r.adjType); 12032 pw.println(')'); 12033 if (r.adjSource != null || r.adjTarget != null) { 12034 pw.print(prefix); 12035 pw.print(" "); 12036 if (r.adjTarget instanceof ComponentName) { 12037 pw.print(((ComponentName)r.adjTarget).flattenToShortString()); 12038 } else if (r.adjTarget != null) { 12039 pw.print(r.adjTarget.toString()); 12040 } else { 12041 pw.print("{null}"); 12042 } 12043 pw.print("<="); 12044 if (r.adjSource instanceof ProcessRecord) { 12045 pw.print("Proc{"); 12046 pw.print(((ProcessRecord)r.adjSource).toShortString()); 12047 pw.println("}"); 12048 } else if (r.adjSource != null) { 12049 pw.println(r.adjSource.toString()); 12050 } else { 12051 pw.println("{null}"); 12052 } 12053 } 12054 if (inclDetails) { 12055 pw.print(prefix); 12056 pw.print(" "); 12057 pw.print("oom: max="); pw.print(r.maxAdj); 12058 pw.print(" curRaw="); pw.print(r.curRawAdj); 12059 pw.print(" setRaw="); pw.print(r.setRawAdj); 12060 pw.print(" cur="); pw.print(r.curAdj); 12061 pw.print(" set="); pw.println(r.setAdj); 12062 pw.print(prefix); 12063 pw.print(" "); 12064 pw.print("state: cur="); pw.print(ProcessList.makeProcStateString(r.curProcState)); 12065 pw.print(" set="); pw.print(ProcessList.makeProcStateString(r.setProcState)); 12066 pw.print(" lastPss="); pw.print(r.lastPss); 12067 pw.print(" lastCachedPss="); pw.println(r.lastCachedPss); 12068 pw.print(prefix); 12069 pw.print(" "); 12070 pw.print("keeping="); pw.print(r.keeping); 12071 pw.print(" cached="); pw.print(r.cached); 12072 pw.print(" empty="); pw.print(r.empty); 12073 pw.print(" hasAboveClient="); pw.println(r.hasAboveClient); 12074 12075 if (!r.keeping) { 12076 if (r.lastWakeTime != 0) { 12077 long wtime; 12078 BatteryStatsImpl stats = service.mBatteryStatsService.getActiveStatistics(); 12079 synchronized (stats) { 12080 wtime = stats.getProcessWakeTime(r.info.uid, 12081 r.pid, curRealtime); 12082 } 12083 long timeUsed = wtime - r.lastWakeTime; 12084 pw.print(prefix); 12085 pw.print(" "); 12086 pw.print("keep awake over "); 12087 TimeUtils.formatDuration(realtimeSince, pw); 12088 pw.print(" used "); 12089 TimeUtils.formatDuration(timeUsed, pw); 12090 pw.print(" ("); 12091 pw.print((timeUsed*100)/realtimeSince); 12092 pw.println("%)"); 12093 } 12094 if (r.lastCpuTime != 0) { 12095 long timeUsed = r.curCpuTime - r.lastCpuTime; 12096 pw.print(prefix); 12097 pw.print(" "); 12098 pw.print("run cpu over "); 12099 TimeUtils.formatDuration(uptimeSince, pw); 12100 pw.print(" used "); 12101 TimeUtils.formatDuration(timeUsed, pw); 12102 pw.print(" ("); 12103 pw.print((timeUsed*100)/uptimeSince); 12104 pw.println("%)"); 12105 } 12106 } 12107 } 12108 } 12109 return true; 12110 } 12111 12112 ArrayList<ProcessRecord> collectProcesses(PrintWriter pw, int start, String[] args) { 12113 ArrayList<ProcessRecord> procs; 12114 synchronized (this) { 12115 if (args != null && args.length > start 12116 && args[start].charAt(0) != '-') { 12117 procs = new ArrayList<ProcessRecord>(); 12118 int pid = -1; 12119 try { 12120 pid = Integer.parseInt(args[start]); 12121 } catch (NumberFormatException e) { 12122 } 12123 for (int i=mLruProcesses.size()-1; i>=0; i--) { 12124 ProcessRecord proc = mLruProcesses.get(i); 12125 if (proc.pid == pid) { 12126 procs.add(proc); 12127 } else if (proc.processName.equals(args[start])) { 12128 procs.add(proc); 12129 } 12130 } 12131 if (procs.size() <= 0) { 12132 return null; 12133 } 12134 } else { 12135 procs = new ArrayList<ProcessRecord>(mLruProcesses); 12136 } 12137 } 12138 return procs; 12139 } 12140 12141 final void dumpGraphicsHardwareUsage(FileDescriptor fd, 12142 PrintWriter pw, String[] args) { 12143 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 12144 if (procs == null) { 12145 pw.println("No process found for: " + args[0]); 12146 return; 12147 } 12148 12149 long uptime = SystemClock.uptimeMillis(); 12150 long realtime = SystemClock.elapsedRealtime(); 12151 pw.println("Applications Graphics Acceleration Info:"); 12152 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 12153 12154 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12155 ProcessRecord r = procs.get(i); 12156 if (r.thread != null) { 12157 pw.println("\n** Graphics info for pid " + r.pid + " [" + r.processName + "] **"); 12158 pw.flush(); 12159 try { 12160 TransferPipe tp = new TransferPipe(); 12161 try { 12162 r.thread.dumpGfxInfo(tp.getWriteFd().getFileDescriptor(), args); 12163 tp.go(fd); 12164 } finally { 12165 tp.kill(); 12166 } 12167 } catch (IOException e) { 12168 pw.println("Failure while dumping the app: " + r); 12169 pw.flush(); 12170 } catch (RemoteException e) { 12171 pw.println("Got a RemoteException while dumping the app " + r); 12172 pw.flush(); 12173 } 12174 } 12175 } 12176 } 12177 12178 final void dumpDbInfo(FileDescriptor fd, PrintWriter pw, String[] args) { 12179 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 12180 if (procs == null) { 12181 pw.println("No process found for: " + args[0]); 12182 return; 12183 } 12184 12185 pw.println("Applications Database Info:"); 12186 12187 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12188 ProcessRecord r = procs.get(i); 12189 if (r.thread != null) { 12190 pw.println("\n** Database info for pid " + r.pid + " [" + r.processName + "] **"); 12191 pw.flush(); 12192 try { 12193 TransferPipe tp = new TransferPipe(); 12194 try { 12195 r.thread.dumpDbInfo(tp.getWriteFd().getFileDescriptor(), args); 12196 tp.go(fd); 12197 } finally { 12198 tp.kill(); 12199 } 12200 } catch (IOException e) { 12201 pw.println("Failure while dumping the app: " + r); 12202 pw.flush(); 12203 } catch (RemoteException e) { 12204 pw.println("Got a RemoteException while dumping the app " + r); 12205 pw.flush(); 12206 } 12207 } 12208 } 12209 } 12210 12211 final static class MemItem { 12212 final boolean isProc; 12213 final String label; 12214 final String shortLabel; 12215 final long pss; 12216 final int id; 12217 final boolean hasActivities; 12218 ArrayList<MemItem> subitems; 12219 12220 public MemItem(String _label, String _shortLabel, long _pss, int _id, 12221 boolean _hasActivities) { 12222 isProc = true; 12223 label = _label; 12224 shortLabel = _shortLabel; 12225 pss = _pss; 12226 id = _id; 12227 hasActivities = _hasActivities; 12228 } 12229 12230 public MemItem(String _label, String _shortLabel, long _pss, int _id) { 12231 isProc = false; 12232 label = _label; 12233 shortLabel = _shortLabel; 12234 pss = _pss; 12235 id = _id; 12236 hasActivities = false; 12237 } 12238 } 12239 12240 static final void dumpMemItems(PrintWriter pw, String prefix, String tag, 12241 ArrayList<MemItem> items, boolean sort, boolean isCompact) { 12242 if (sort && !isCompact) { 12243 Collections.sort(items, new Comparator<MemItem>() { 12244 @Override 12245 public int compare(MemItem lhs, MemItem rhs) { 12246 if (lhs.pss < rhs.pss) { 12247 return 1; 12248 } else if (lhs.pss > rhs.pss) { 12249 return -1; 12250 } 12251 return 0; 12252 } 12253 }); 12254 } 12255 12256 for (int i=0; i<items.size(); i++) { 12257 MemItem mi = items.get(i); 12258 if (!isCompact) { 12259 pw.print(prefix); pw.printf("%7d kB: ", mi.pss); pw.println(mi.label); 12260 } else if (mi.isProc) { 12261 pw.print("proc,"); pw.print(tag); pw.print(","); pw.print(mi.shortLabel); 12262 pw.print(","); pw.print(mi.id); pw.print(","); pw.print(mi.pss); 12263 pw.println(mi.hasActivities ? ",a" : ",e"); 12264 } else { 12265 pw.print(tag); pw.print(","); pw.print(mi.shortLabel); pw.print(","); 12266 pw.println(mi.pss); 12267 } 12268 if (mi.subitems != null) { 12269 dumpMemItems(pw, prefix + " ", mi.shortLabel, mi.subitems, 12270 true, isCompact); 12271 } 12272 } 12273 } 12274 12275 // These are in KB. 12276 static final long[] DUMP_MEM_BUCKETS = new long[] { 12277 5*1024, 7*1024, 10*1024, 15*1024, 20*1024, 30*1024, 40*1024, 80*1024, 12278 120*1024, 160*1024, 200*1024, 12279 250*1024, 300*1024, 350*1024, 400*1024, 500*1024, 600*1024, 800*1024, 12280 1*1024*1024, 2*1024*1024, 5*1024*1024, 10*1024*1024, 20*1024*1024 12281 }; 12282 12283 static final void appendMemBucket(StringBuilder out, long memKB, String label, 12284 boolean stackLike) { 12285 int start = label.lastIndexOf('.'); 12286 if (start >= 0) start++; 12287 else start = 0; 12288 int end = label.length(); 12289 for (int i=0; i<DUMP_MEM_BUCKETS.length; i++) { 12290 if (DUMP_MEM_BUCKETS[i] >= memKB) { 12291 long bucket = DUMP_MEM_BUCKETS[i]/1024; 12292 out.append(bucket); 12293 out.append(stackLike ? "MB." : "MB "); 12294 out.append(label, start, end); 12295 return; 12296 } 12297 } 12298 out.append(memKB/1024); 12299 out.append(stackLike ? "MB." : "MB "); 12300 out.append(label, start, end); 12301 } 12302 12303 static final int[] DUMP_MEM_OOM_ADJ = new int[] { 12304 ProcessList.NATIVE_ADJ, 12305 ProcessList.SYSTEM_ADJ, ProcessList.PERSISTENT_PROC_ADJ, ProcessList.FOREGROUND_APP_ADJ, 12306 ProcessList.VISIBLE_APP_ADJ, ProcessList.PERCEPTIBLE_APP_ADJ, 12307 ProcessList.BACKUP_APP_ADJ, ProcessList.HEAVY_WEIGHT_APP_ADJ, 12308 ProcessList.SERVICE_ADJ, ProcessList.HOME_APP_ADJ, 12309 ProcessList.PREVIOUS_APP_ADJ, ProcessList.SERVICE_B_ADJ, ProcessList.CACHED_APP_MAX_ADJ 12310 }; 12311 static final String[] DUMP_MEM_OOM_LABEL = new String[] { 12312 "Native", 12313 "System", "Persistent", "Foreground", 12314 "Visible", "Perceptible", 12315 "Heavy Weight", "Backup", 12316 "A Services", "Home", 12317 "Previous", "B Services", "Cached" 12318 }; 12319 static final String[] DUMP_MEM_OOM_COMPACT_LABEL = new String[] { 12320 "native", 12321 "sys", "pers", "fore", 12322 "vis", "percept", 12323 "heavy", "backup", 12324 "servicea", "home", 12325 "prev", "serviceb", "cached" 12326 }; 12327 12328 private final void dumpApplicationMemoryUsageHeader(PrintWriter pw, long uptime, 12329 long realtime, boolean isCheckinRequest, boolean isCompact) { 12330 if (isCheckinRequest || isCompact) { 12331 // short checkin version 12332 pw.print("time,"); pw.print(uptime); pw.print(","); pw.println(realtime); 12333 } else { 12334 pw.println("Applications Memory Usage (kB):"); 12335 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 12336 } 12337 } 12338 12339 final void dumpApplicationMemoryUsage(FileDescriptor fd, 12340 PrintWriter pw, String prefix, String[] args, boolean brief, PrintWriter categoryPw) { 12341 boolean dumpDetails = false; 12342 boolean dumpFullDetails = false; 12343 boolean dumpDalvik = false; 12344 boolean oomOnly = false; 12345 boolean isCompact = false; 12346 boolean localOnly = false; 12347 12348 int opti = 0; 12349 while (opti < args.length) { 12350 String opt = args[opti]; 12351 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 12352 break; 12353 } 12354 opti++; 12355 if ("-a".equals(opt)) { 12356 dumpDetails = true; 12357 dumpFullDetails = true; 12358 dumpDalvik = true; 12359 } else if ("-d".equals(opt)) { 12360 dumpDalvik = true; 12361 } else if ("-c".equals(opt)) { 12362 isCompact = true; 12363 } else if ("--oom".equals(opt)) { 12364 oomOnly = true; 12365 } else if ("--local".equals(opt)) { 12366 localOnly = true; 12367 } else if ("-h".equals(opt)) { 12368 pw.println("meminfo dump options: [-a] [-d] [-c] [--oom] [process]"); 12369 pw.println(" -a: include all available information for each process."); 12370 pw.println(" -d: include dalvik details when dumping process details."); 12371 pw.println(" -c: dump in a compact machine-parseable representation."); 12372 pw.println(" --oom: only show processes organized by oom adj."); 12373 pw.println(" --local: only collect details locally, don't call process."); 12374 pw.println("If [process] is specified it can be the name or "); 12375 pw.println("pid of a specific process to dump."); 12376 return; 12377 } else { 12378 pw.println("Unknown argument: " + opt + "; use -h for help"); 12379 } 12380 } 12381 12382 final boolean isCheckinRequest = scanArgs(args, "--checkin"); 12383 long uptime = SystemClock.uptimeMillis(); 12384 long realtime = SystemClock.elapsedRealtime(); 12385 final long[] tmpLong = new long[1]; 12386 12387 ArrayList<ProcessRecord> procs = collectProcesses(pw, opti, args); 12388 if (procs == null) { 12389 // No Java processes. Maybe they want to print a native process. 12390 if (args != null && args.length > opti 12391 && args[opti].charAt(0) != '-') { 12392 ArrayList<ProcessCpuTracker.Stats> nativeProcs 12393 = new ArrayList<ProcessCpuTracker.Stats>(); 12394 updateCpuStatsNow(); 12395 int findPid = -1; 12396 try { 12397 findPid = Integer.parseInt(args[opti]); 12398 } catch (NumberFormatException e) { 12399 } 12400 synchronized (mProcessCpuThread) { 12401 final int N = mProcessCpuTracker.countStats(); 12402 for (int i=0; i<N; i++) { 12403 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 12404 if (st.pid == findPid || (st.baseName != null 12405 && st.baseName.equals(args[opti]))) { 12406 nativeProcs.add(st); 12407 } 12408 } 12409 } 12410 if (nativeProcs.size() > 0) { 12411 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, 12412 isCompact); 12413 Debug.MemoryInfo mi = null; 12414 for (int i = nativeProcs.size() - 1 ; i >= 0 ; i--) { 12415 final ProcessCpuTracker.Stats r = nativeProcs.get(i); 12416 final int pid = r.pid; 12417 if (!isCheckinRequest && dumpDetails) { 12418 pw.println("\n** MEMINFO in pid " + pid + " [" + r.baseName + "] **"); 12419 } 12420 if (mi == null) { 12421 mi = new Debug.MemoryInfo(); 12422 } 12423 if (dumpDetails || (!brief && !oomOnly)) { 12424 Debug.getMemoryInfo(pid, mi); 12425 } else { 12426 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 12427 mi.dalvikPrivateDirty = (int)tmpLong[0]; 12428 } 12429 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 12430 dumpDalvik, pid, r.baseName, 0, 0, 0, 0, 0, 0); 12431 if (isCheckinRequest) { 12432 pw.println(); 12433 } 12434 } 12435 return; 12436 } 12437 } 12438 pw.println("No process found for: " + args[opti]); 12439 return; 12440 } 12441 12442 if (!brief && !oomOnly && (procs.size() == 1 || isCheckinRequest)) { 12443 dumpDetails = true; 12444 } 12445 12446 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, isCompact); 12447 12448 String[] innerArgs = new String[args.length-opti]; 12449 System.arraycopy(args, opti, innerArgs, 0, args.length-opti); 12450 12451 ArrayList<MemItem> procMems = new ArrayList<MemItem>(); 12452 final SparseArray<MemItem> procMemsMap = new SparseArray<MemItem>(); 12453 long nativePss=0, dalvikPss=0, otherPss=0; 12454 long[] miscPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 12455 12456 long oomPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 12457 ArrayList<MemItem>[] oomProcs = (ArrayList<MemItem>[]) 12458 new ArrayList[DUMP_MEM_OOM_LABEL.length]; 12459 12460 long totalPss = 0; 12461 long cachedPss = 0; 12462 12463 Debug.MemoryInfo mi = null; 12464 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12465 final ProcessRecord r = procs.get(i); 12466 final IApplicationThread thread; 12467 final int pid; 12468 final int oomAdj; 12469 final boolean hasActivities; 12470 synchronized (this) { 12471 thread = r.thread; 12472 pid = r.pid; 12473 oomAdj = r.getSetAdjWithServices(); 12474 hasActivities = r.activities.size() > 0; 12475 } 12476 if (thread != null) { 12477 if (!isCheckinRequest && dumpDetails) { 12478 pw.println("\n** MEMINFO in pid " + pid + " [" + r.processName + "] **"); 12479 } 12480 if (mi == null) { 12481 mi = new Debug.MemoryInfo(); 12482 } 12483 if (dumpDetails || (!brief && !oomOnly)) { 12484 Debug.getMemoryInfo(pid, mi); 12485 } else { 12486 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 12487 mi.dalvikPrivateDirty = (int)tmpLong[0]; 12488 } 12489 if (dumpDetails) { 12490 if (localOnly) { 12491 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 12492 dumpDalvik, pid, r.processName, 0, 0, 0, 0, 0, 0); 12493 if (isCheckinRequest) { 12494 pw.println(); 12495 } 12496 } else { 12497 try { 12498 pw.flush(); 12499 thread.dumpMemInfo(fd, mi, isCheckinRequest, dumpFullDetails, 12500 dumpDalvik, innerArgs); 12501 } catch (RemoteException e) { 12502 if (!isCheckinRequest) { 12503 pw.println("Got RemoteException!"); 12504 pw.flush(); 12505 } 12506 } 12507 } 12508 } 12509 12510 final long myTotalPss = mi.getTotalPss(); 12511 final long myTotalUss = mi.getTotalUss(); 12512 12513 synchronized (this) { 12514 if (r.thread != null && oomAdj == r.getSetAdjWithServices()) { 12515 // Record this for posterity if the process has been stable. 12516 r.baseProcessTracker.addPss(myTotalPss, myTotalUss, true, r.pkgList); 12517 } 12518 } 12519 12520 if (!isCheckinRequest && mi != null) { 12521 totalPss += myTotalPss; 12522 MemItem pssItem = new MemItem(r.processName + " (pid " + pid + 12523 (hasActivities ? " / activities)" : ")"), 12524 r.processName, myTotalPss, pid, hasActivities); 12525 procMems.add(pssItem); 12526 procMemsMap.put(pid, pssItem); 12527 12528 nativePss += mi.nativePss; 12529 dalvikPss += mi.dalvikPss; 12530 otherPss += mi.otherPss; 12531 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 12532 long mem = mi.getOtherPss(j); 12533 miscPss[j] += mem; 12534 otherPss -= mem; 12535 } 12536 12537 if (oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 12538 cachedPss += myTotalPss; 12539 } 12540 12541 for (int oomIndex=0; oomIndex<oomPss.length; oomIndex++) { 12542 if (oomAdj <= DUMP_MEM_OOM_ADJ[oomIndex] 12543 || oomIndex == (oomPss.length-1)) { 12544 oomPss[oomIndex] += myTotalPss; 12545 if (oomProcs[oomIndex] == null) { 12546 oomProcs[oomIndex] = new ArrayList<MemItem>(); 12547 } 12548 oomProcs[oomIndex].add(pssItem); 12549 break; 12550 } 12551 } 12552 } 12553 } 12554 } 12555 12556 if (!isCheckinRequest && procs.size() > 1) { 12557 // If we are showing aggregations, also look for native processes to 12558 // include so that our aggregations are more accurate. 12559 updateCpuStatsNow(); 12560 synchronized (mProcessCpuThread) { 12561 final int N = mProcessCpuTracker.countStats(); 12562 for (int i=0; i<N; i++) { 12563 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 12564 if (st.vsize > 0 && procMemsMap.indexOfKey(st.pid) < 0) { 12565 if (mi == null) { 12566 mi = new Debug.MemoryInfo(); 12567 } 12568 if (!brief && !oomOnly) { 12569 Debug.getMemoryInfo(st.pid, mi); 12570 } else { 12571 mi.nativePss = (int)Debug.getPss(st.pid, tmpLong); 12572 mi.nativePrivateDirty = (int)tmpLong[0]; 12573 } 12574 12575 final long myTotalPss = mi.getTotalPss(); 12576 totalPss += myTotalPss; 12577 12578 MemItem pssItem = new MemItem(st.name + " (pid " + st.pid + ")", 12579 st.name, myTotalPss, st.pid, false); 12580 procMems.add(pssItem); 12581 12582 nativePss += mi.nativePss; 12583 dalvikPss += mi.dalvikPss; 12584 otherPss += mi.otherPss; 12585 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 12586 long mem = mi.getOtherPss(j); 12587 miscPss[j] += mem; 12588 otherPss -= mem; 12589 } 12590 oomPss[0] += myTotalPss; 12591 if (oomProcs[0] == null) { 12592 oomProcs[0] = new ArrayList<MemItem>(); 12593 } 12594 oomProcs[0].add(pssItem); 12595 } 12596 } 12597 } 12598 12599 ArrayList<MemItem> catMems = new ArrayList<MemItem>(); 12600 12601 catMems.add(new MemItem("Native", "Native", nativePss, -1)); 12602 catMems.add(new MemItem("Dalvik", "Dalvik", dalvikPss, -2)); 12603 catMems.add(new MemItem("Unknown", "Unknown", otherPss, -3)); 12604 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 12605 String label = Debug.MemoryInfo.getOtherLabel(j); 12606 catMems.add(new MemItem(label, label, miscPss[j], j)); 12607 } 12608 12609 ArrayList<MemItem> oomMems = new ArrayList<MemItem>(); 12610 for (int j=0; j<oomPss.length; j++) { 12611 if (oomPss[j] != 0) { 12612 String label = isCompact ? DUMP_MEM_OOM_COMPACT_LABEL[j] 12613 : DUMP_MEM_OOM_LABEL[j]; 12614 MemItem item = new MemItem(label, label, oomPss[j], 12615 DUMP_MEM_OOM_ADJ[j]); 12616 item.subitems = oomProcs[j]; 12617 oomMems.add(item); 12618 } 12619 } 12620 12621 if (!brief && !oomOnly && !isCompact) { 12622 pw.println(); 12623 pw.println("Total PSS by process:"); 12624 dumpMemItems(pw, " ", "proc", procMems, true, isCompact); 12625 pw.println(); 12626 } 12627 if (!isCompact) { 12628 pw.println("Total PSS by OOM adjustment:"); 12629 } 12630 dumpMemItems(pw, " ", "oom", oomMems, false, isCompact); 12631 if (!brief && !oomOnly) { 12632 PrintWriter out = categoryPw != null ? categoryPw : pw; 12633 if (!isCompact) { 12634 out.println(); 12635 out.println("Total PSS by category:"); 12636 } 12637 dumpMemItems(out, " ", "cat", catMems, true, isCompact); 12638 } 12639 if (!isCompact) { 12640 pw.println(); 12641 } 12642 MemInfoReader memInfo = new MemInfoReader(); 12643 memInfo.readMemInfo(); 12644 if (!brief) { 12645 if (!isCompact) { 12646 pw.print("Total RAM: "); pw.print(memInfo.getTotalSizeKb()); 12647 pw.print(" kB (status "); 12648 switch (mLastMemoryLevel) { 12649 case ProcessStats.ADJ_MEM_FACTOR_NORMAL: 12650 pw.println("normal)"); 12651 break; 12652 case ProcessStats.ADJ_MEM_FACTOR_MODERATE: 12653 pw.println("moderate)"); 12654 break; 12655 case ProcessStats.ADJ_MEM_FACTOR_LOW: 12656 pw.println("low)"); 12657 break; 12658 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 12659 pw.println("critical)"); 12660 break; 12661 default: 12662 pw.print(mLastMemoryLevel); 12663 pw.println(")"); 12664 break; 12665 } 12666 pw.print(" Free RAM: "); pw.print(cachedPss + memInfo.getCachedSizeKb() 12667 + memInfo.getFreeSizeKb()); pw.print(" kB ("); 12668 pw.print(cachedPss); pw.print(" cached pss + "); 12669 pw.print(memInfo.getCachedSizeKb()); pw.print(" cached + "); 12670 pw.print(memInfo.getFreeSizeKb()); pw.println(" free)"); 12671 } else { 12672 pw.print("ram,"); pw.print(memInfo.getTotalSizeKb()); pw.print(","); 12673 pw.print(cachedPss + memInfo.getCachedSizeKb() 12674 + memInfo.getFreeSizeKb()); pw.print(","); 12675 pw.println(totalPss - cachedPss); 12676 } 12677 } 12678 if (!isCompact) { 12679 pw.print(" Used RAM: "); pw.print(totalPss - cachedPss 12680 + memInfo.getBuffersSizeKb() + memInfo.getShmemSizeKb() 12681 + memInfo.getSlabSizeKb()); pw.print(" kB ("); 12682 pw.print(totalPss - cachedPss); pw.print(" used pss + "); 12683 pw.print(memInfo.getBuffersSizeKb()); pw.print(" buffers + "); 12684 pw.print(memInfo.getShmemSizeKb()); pw.print(" shmem + "); 12685 pw.print(memInfo.getSlabSizeKb()); pw.println(" slab)"); 12686 pw.print(" Lost RAM: "); pw.print(memInfo.getTotalSizeKb() 12687 - totalPss - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 12688 - memInfo.getBuffersSizeKb() - memInfo.getShmemSizeKb() 12689 - memInfo.getSlabSizeKb()); pw.println(" kB"); 12690 } 12691 if (!brief) { 12692 if (memInfo.getZramTotalSizeKb() != 0) { 12693 if (!isCompact) { 12694 pw.print(" ZRAM: "); pw.print(memInfo.getZramTotalSizeKb()); 12695 pw.print(" kB physical used for "); 12696 pw.print(memInfo.getSwapTotalSizeKb() 12697 - memInfo.getSwapFreeSizeKb()); 12698 pw.print(" kB in swap ("); 12699 pw.print(memInfo.getSwapTotalSizeKb()); 12700 pw.println(" kB total swap)"); 12701 } else { 12702 pw.print("zram,"); pw.print(memInfo.getZramTotalSizeKb()); pw.print(","); 12703 pw.print(memInfo.getSwapTotalSizeKb()); pw.print(","); 12704 pw.println(memInfo.getSwapFreeSizeKb()); 12705 } 12706 } 12707 final int[] SINGLE_LONG_FORMAT = new int[] { 12708 Process.PROC_SPACE_TERM|Process.PROC_OUT_LONG 12709 }; 12710 long[] longOut = new long[1]; 12711 Process.readProcFile("/sys/kernel/mm/ksm/pages_shared", 12712 SINGLE_LONG_FORMAT, null, longOut, null); 12713 long shared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 12714 longOut[0] = 0; 12715 Process.readProcFile("/sys/kernel/mm/ksm/pages_sharing", 12716 SINGLE_LONG_FORMAT, null, longOut, null); 12717 long sharing = longOut[0] * ProcessList.PAGE_SIZE / 1024; 12718 longOut[0] = 0; 12719 Process.readProcFile("/sys/kernel/mm/ksm/pages_unshared", 12720 SINGLE_LONG_FORMAT, null, longOut, null); 12721 long unshared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 12722 longOut[0] = 0; 12723 Process.readProcFile("/sys/kernel/mm/ksm/pages_volatile", 12724 SINGLE_LONG_FORMAT, null, longOut, null); 12725 long voltile = longOut[0] * ProcessList.PAGE_SIZE / 1024; 12726 if (!isCompact) { 12727 if (sharing != 0 || shared != 0 || unshared != 0 || voltile != 0) { 12728 pw.print(" KSM: "); pw.print(sharing); 12729 pw.print(" kB saved from shared "); 12730 pw.print(shared); pw.println(" kB"); 12731 pw.print(" "); pw.print(unshared); pw.print(" kB unshared; "); 12732 pw.print(voltile); pw.println(" kB volatile"); 12733 } 12734 pw.print(" Tuning: "); 12735 pw.print(ActivityManager.staticGetMemoryClass()); 12736 pw.print(" (large "); 12737 pw.print(ActivityManager.staticGetLargeMemoryClass()); 12738 pw.print("), oom "); 12739 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 12740 pw.print(" kB"); 12741 pw.print(", restore limit "); 12742 pw.print(mProcessList.getCachedRestoreThresholdKb()); 12743 pw.print(" kB"); 12744 if (ActivityManager.isLowRamDeviceStatic()) { 12745 pw.print(" (low-ram)"); 12746 } 12747 if (ActivityManager.isHighEndGfx()) { 12748 pw.print(" (high-end-gfx)"); 12749 } 12750 pw.println(); 12751 } else { 12752 pw.print("ksm,"); pw.print(sharing); pw.print(","); 12753 pw.print(shared); pw.print(","); pw.print(unshared); pw.print(","); 12754 pw.println(voltile); 12755 pw.print("tuning,"); 12756 pw.print(ActivityManager.staticGetMemoryClass()); 12757 pw.print(','); 12758 pw.print(ActivityManager.staticGetLargeMemoryClass()); 12759 pw.print(','); 12760 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 12761 if (ActivityManager.isLowRamDeviceStatic()) { 12762 pw.print(",low-ram"); 12763 } 12764 if (ActivityManager.isHighEndGfx()) { 12765 pw.print(",high-end-gfx"); 12766 } 12767 pw.println(); 12768 } 12769 } 12770 } 12771 } 12772 12773 /** 12774 * Searches array of arguments for the specified string 12775 * @param args array of argument strings 12776 * @param value value to search for 12777 * @return true if the value is contained in the array 12778 */ 12779 private static boolean scanArgs(String[] args, String value) { 12780 if (args != null) { 12781 for (String arg : args) { 12782 if (value.equals(arg)) { 12783 return true; 12784 } 12785 } 12786 } 12787 return false; 12788 } 12789 12790 private final boolean removeDyingProviderLocked(ProcessRecord proc, 12791 ContentProviderRecord cpr, boolean always) { 12792 final boolean inLaunching = mLaunchingProviders.contains(cpr); 12793 12794 if (!inLaunching || always) { 12795 synchronized (cpr) { 12796 cpr.launchingApp = null; 12797 cpr.notifyAll(); 12798 } 12799 mProviderMap.removeProviderByClass(cpr.name, UserHandle.getUserId(cpr.uid)); 12800 String names[] = cpr.info.authority.split(";"); 12801 for (int j = 0; j < names.length; j++) { 12802 mProviderMap.removeProviderByName(names[j], UserHandle.getUserId(cpr.uid)); 12803 } 12804 } 12805 12806 for (int i=0; i<cpr.connections.size(); i++) { 12807 ContentProviderConnection conn = cpr.connections.get(i); 12808 if (conn.waiting) { 12809 // If this connection is waiting for the provider, then we don't 12810 // need to mess with its process unless we are always removing 12811 // or for some reason the provider is not currently launching. 12812 if (inLaunching && !always) { 12813 continue; 12814 } 12815 } 12816 ProcessRecord capp = conn.client; 12817 conn.dead = true; 12818 if (conn.stableCount > 0) { 12819 if (!capp.persistent && capp.thread != null 12820 && capp.pid != 0 12821 && capp.pid != MY_PID) { 12822 killUnneededProcessLocked(capp, "depends on provider " 12823 + cpr.name.flattenToShortString() 12824 + " in dying proc " + (proc != null ? proc.processName : "??")); 12825 } 12826 } else if (capp.thread != null && conn.provider.provider != null) { 12827 try { 12828 capp.thread.unstableProviderDied(conn.provider.provider.asBinder()); 12829 } catch (RemoteException e) { 12830 } 12831 // In the protocol here, we don't expect the client to correctly 12832 // clean up this connection, we'll just remove it. 12833 cpr.connections.remove(i); 12834 conn.client.conProviders.remove(conn); 12835 } 12836 } 12837 12838 if (inLaunching && always) { 12839 mLaunchingProviders.remove(cpr); 12840 } 12841 return inLaunching; 12842 } 12843 12844 /** 12845 * Main code for cleaning up a process when it has gone away. This is 12846 * called both as a result of the process dying, or directly when stopping 12847 * a process when running in single process mode. 12848 */ 12849 private final void cleanUpApplicationRecordLocked(ProcessRecord app, 12850 boolean restarting, boolean allowRestart, int index) { 12851 if (index >= 0) { 12852 removeLruProcessLocked(app); 12853 ProcessList.remove(app.pid); 12854 } 12855 12856 mProcessesToGc.remove(app); 12857 mPendingPssProcesses.remove(app); 12858 12859 // Dismiss any open dialogs. 12860 if (app.crashDialog != null && !app.forceCrashReport) { 12861 app.crashDialog.dismiss(); 12862 app.crashDialog = null; 12863 } 12864 if (app.anrDialog != null) { 12865 app.anrDialog.dismiss(); 12866 app.anrDialog = null; 12867 } 12868 if (app.waitDialog != null) { 12869 app.waitDialog.dismiss(); 12870 app.waitDialog = null; 12871 } 12872 12873 app.crashing = false; 12874 app.notResponding = false; 12875 12876 app.resetPackageList(mProcessStats); 12877 app.unlinkDeathRecipient(); 12878 app.makeInactive(mProcessStats); 12879 app.forcingToForeground = null; 12880 updateProcessForegroundLocked(app, false, false); 12881 app.foregroundActivities = false; 12882 app.hasShownUi = false; 12883 app.treatLikeActivity = false; 12884 app.hasAboveClient = false; 12885 app.hasClientActivities = false; 12886 12887 mServices.killServicesLocked(app, allowRestart); 12888 12889 boolean restart = false; 12890 12891 // Remove published content providers. 12892 for (int i=app.pubProviders.size()-1; i>=0; i--) { 12893 ContentProviderRecord cpr = app.pubProviders.valueAt(i); 12894 final boolean always = app.bad || !allowRestart; 12895 if (removeDyingProviderLocked(app, cpr, always) || always) { 12896 // We left the provider in the launching list, need to 12897 // restart it. 12898 restart = true; 12899 } 12900 12901 cpr.provider = null; 12902 cpr.proc = null; 12903 } 12904 app.pubProviders.clear(); 12905 12906 // Take care of any launching providers waiting for this process. 12907 if (checkAppInLaunchingProvidersLocked(app, false)) { 12908 restart = true; 12909 } 12910 12911 // Unregister from connected content providers. 12912 if (!app.conProviders.isEmpty()) { 12913 for (int i=0; i<app.conProviders.size(); i++) { 12914 ContentProviderConnection conn = app.conProviders.get(i); 12915 conn.provider.connections.remove(conn); 12916 } 12917 app.conProviders.clear(); 12918 } 12919 12920 // At this point there may be remaining entries in mLaunchingProviders 12921 // where we were the only one waiting, so they are no longer of use. 12922 // Look for these and clean up if found. 12923 // XXX Commented out for now. Trying to figure out a way to reproduce 12924 // the actual situation to identify what is actually going on. 12925 if (false) { 12926 for (int i=0; i<mLaunchingProviders.size(); i++) { 12927 ContentProviderRecord cpr = (ContentProviderRecord) 12928 mLaunchingProviders.get(i); 12929 if (cpr.connections.size() <= 0 && !cpr.hasExternalProcessHandles()) { 12930 synchronized (cpr) { 12931 cpr.launchingApp = null; 12932 cpr.notifyAll(); 12933 } 12934 } 12935 } 12936 } 12937 12938 skipCurrentReceiverLocked(app); 12939 12940 // Unregister any receivers. 12941 for (int i=app.receivers.size()-1; i>=0; i--) { 12942 removeReceiverLocked(app.receivers.valueAt(i)); 12943 } 12944 app.receivers.clear(); 12945 12946 // If the app is undergoing backup, tell the backup manager about it 12947 if (mBackupTarget != null && app.pid == mBackupTarget.app.pid) { 12948 if (DEBUG_BACKUP || DEBUG_CLEANUP) Slog.d(TAG, "App " 12949 + mBackupTarget.appInfo + " died during backup"); 12950 try { 12951 IBackupManager bm = IBackupManager.Stub.asInterface( 12952 ServiceManager.getService(Context.BACKUP_SERVICE)); 12953 bm.agentDisconnected(app.info.packageName); 12954 } catch (RemoteException e) { 12955 // can't happen; backup manager is local 12956 } 12957 } 12958 12959 for (int i = mPendingProcessChanges.size()-1; i>=0; i--) { 12960 ProcessChangeItem item = mPendingProcessChanges.get(i); 12961 if (item.pid == app.pid) { 12962 mPendingProcessChanges.remove(i); 12963 mAvailProcessChanges.add(item); 12964 } 12965 } 12966 mHandler.obtainMessage(DISPATCH_PROCESS_DIED, app.pid, app.info.uid, null).sendToTarget(); 12967 12968 // If the caller is restarting this app, then leave it in its 12969 // current lists and let the caller take care of it. 12970 if (restarting) { 12971 return; 12972 } 12973 12974 if (!app.persistent || app.isolated) { 12975 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, 12976 "Removing non-persistent process during cleanup: " + app); 12977 mProcessNames.remove(app.processName, app.uid); 12978 mIsolatedProcesses.remove(app.uid); 12979 if (mHeavyWeightProcess == app) { 12980 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 12981 mHeavyWeightProcess.userId, 0)); 12982 mHeavyWeightProcess = null; 12983 } 12984 } else if (!app.removed) { 12985 // This app is persistent, so we need to keep its record around. 12986 // If it is not already on the pending app list, add it there 12987 // and start a new process for it. 12988 if (mPersistentStartingProcesses.indexOf(app) < 0) { 12989 mPersistentStartingProcesses.add(app); 12990 restart = true; 12991 } 12992 } 12993 if ((DEBUG_PROCESSES || DEBUG_CLEANUP) && mProcessesOnHold.contains(app)) Slog.v(TAG, 12994 "Clean-up removing on hold: " + app); 12995 mProcessesOnHold.remove(app); 12996 12997 if (app == mHomeProcess) { 12998 mHomeProcess = null; 12999 } 13000 if (app == mPreviousProcess) { 13001 mPreviousProcess = null; 13002 } 13003 13004 if (restart && !app.isolated) { 13005 // We have components that still need to be running in the 13006 // process, so re-launch it. 13007 mProcessNames.put(app.processName, app.uid, app); 13008 startProcessLocked(app, "restart", app.processName, null /* ABI override */); 13009 } else if (app.pid > 0 && app.pid != MY_PID) { 13010 // Goodbye! 13011 boolean removed; 13012 synchronized (mPidsSelfLocked) { 13013 mPidsSelfLocked.remove(app.pid); 13014 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 13015 } 13016 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_PROC_FINISH, 13017 app.processName, app.info.uid); 13018 if (app.isolated) { 13019 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 13020 } 13021 app.setPid(0); 13022 } 13023 } 13024 13025 boolean checkAppInLaunchingProvidersLocked(ProcessRecord app, boolean alwaysBad) { 13026 // Look through the content providers we are waiting to have launched, 13027 // and if any run in this process then either schedule a restart of 13028 // the process or kill the client waiting for it if this process has 13029 // gone bad. 13030 int NL = mLaunchingProviders.size(); 13031 boolean restart = false; 13032 for (int i=0; i<NL; i++) { 13033 ContentProviderRecord cpr = mLaunchingProviders.get(i); 13034 if (cpr.launchingApp == app) { 13035 if (!alwaysBad && !app.bad) { 13036 restart = true; 13037 } else { 13038 removeDyingProviderLocked(app, cpr, true); 13039 // cpr should have been removed from mLaunchingProviders 13040 NL = mLaunchingProviders.size(); 13041 i--; 13042 } 13043 } 13044 } 13045 return restart; 13046 } 13047 13048 // ========================================================= 13049 // SERVICES 13050 // ========================================================= 13051 13052 public List<ActivityManager.RunningServiceInfo> getServices(int maxNum, 13053 int flags) { 13054 enforceNotIsolatedCaller("getServices"); 13055 synchronized (this) { 13056 return mServices.getRunningServiceInfoLocked(maxNum, flags); 13057 } 13058 } 13059 13060 public PendingIntent getRunningServiceControlPanel(ComponentName name) { 13061 enforceNotIsolatedCaller("getRunningServiceControlPanel"); 13062 synchronized (this) { 13063 return mServices.getRunningServiceControlPanelLocked(name); 13064 } 13065 } 13066 13067 public ComponentName startService(IApplicationThread caller, Intent service, 13068 String resolvedType, int userId) { 13069 enforceNotIsolatedCaller("startService"); 13070 // Refuse possible leaked file descriptors 13071 if (service != null && service.hasFileDescriptors() == true) { 13072 throw new IllegalArgumentException("File descriptors passed in Intent"); 13073 } 13074 13075 if (DEBUG_SERVICE) 13076 Slog.v(TAG, "startService: " + service + " type=" + resolvedType); 13077 synchronized(this) { 13078 final int callingPid = Binder.getCallingPid(); 13079 final int callingUid = Binder.getCallingUid(); 13080 final long origId = Binder.clearCallingIdentity(); 13081 ComponentName res = mServices.startServiceLocked(caller, service, 13082 resolvedType, callingPid, callingUid, userId); 13083 Binder.restoreCallingIdentity(origId); 13084 return res; 13085 } 13086 } 13087 13088 ComponentName startServiceInPackage(int uid, 13089 Intent service, String resolvedType, int userId) { 13090 synchronized(this) { 13091 if (DEBUG_SERVICE) 13092 Slog.v(TAG, "startServiceInPackage: " + service + " type=" + resolvedType); 13093 final long origId = Binder.clearCallingIdentity(); 13094 ComponentName res = mServices.startServiceLocked(null, service, 13095 resolvedType, -1, uid, userId); 13096 Binder.restoreCallingIdentity(origId); 13097 return res; 13098 } 13099 } 13100 13101 public int stopService(IApplicationThread caller, Intent service, 13102 String resolvedType, int userId) { 13103 enforceNotIsolatedCaller("stopService"); 13104 // Refuse possible leaked file descriptors 13105 if (service != null && service.hasFileDescriptors() == true) { 13106 throw new IllegalArgumentException("File descriptors passed in Intent"); 13107 } 13108 13109 synchronized(this) { 13110 return mServices.stopServiceLocked(caller, service, resolvedType, userId); 13111 } 13112 } 13113 13114 public IBinder peekService(Intent service, String resolvedType) { 13115 enforceNotIsolatedCaller("peekService"); 13116 // Refuse possible leaked file descriptors 13117 if (service != null && service.hasFileDescriptors() == true) { 13118 throw new IllegalArgumentException("File descriptors passed in Intent"); 13119 } 13120 synchronized(this) { 13121 return mServices.peekServiceLocked(service, resolvedType); 13122 } 13123 } 13124 13125 public boolean stopServiceToken(ComponentName className, IBinder token, 13126 int startId) { 13127 synchronized(this) { 13128 return mServices.stopServiceTokenLocked(className, token, startId); 13129 } 13130 } 13131 13132 public void setServiceForeground(ComponentName className, IBinder token, 13133 int id, Notification notification, boolean removeNotification) { 13134 synchronized(this) { 13135 mServices.setServiceForegroundLocked(className, token, id, notification, 13136 removeNotification); 13137 } 13138 } 13139 13140 public int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 13141 boolean requireFull, String name, String callerPackage) { 13142 final int callingUserId = UserHandle.getUserId(callingUid); 13143 if (callingUserId != userId) { 13144 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 13145 if ((requireFull || checkComponentPermission( 13146 android.Manifest.permission.INTERACT_ACROSS_USERS, 13147 callingPid, callingUid, -1, true) != PackageManager.PERMISSION_GRANTED) 13148 && checkComponentPermission(INTERACT_ACROSS_USERS_FULL, 13149 callingPid, callingUid, -1, true) 13150 != PackageManager.PERMISSION_GRANTED) { 13151 if (userId == UserHandle.USER_CURRENT_OR_SELF) { 13152 // In this case, they would like to just execute as their 13153 // owner user instead of failing. 13154 userId = callingUserId; 13155 } else { 13156 StringBuilder builder = new StringBuilder(128); 13157 builder.append("Permission Denial: "); 13158 builder.append(name); 13159 if (callerPackage != null) { 13160 builder.append(" from "); 13161 builder.append(callerPackage); 13162 } 13163 builder.append(" asks to run as user "); 13164 builder.append(userId); 13165 builder.append(" but is calling from user "); 13166 builder.append(UserHandle.getUserId(callingUid)); 13167 builder.append("; this requires "); 13168 builder.append(INTERACT_ACROSS_USERS_FULL); 13169 if (!requireFull) { 13170 builder.append(" or "); 13171 builder.append(android.Manifest.permission.INTERACT_ACROSS_USERS); 13172 } 13173 String msg = builder.toString(); 13174 Slog.w(TAG, msg); 13175 throw new SecurityException(msg); 13176 } 13177 } 13178 } 13179 if (userId == UserHandle.USER_CURRENT 13180 || userId == UserHandle.USER_CURRENT_OR_SELF) { 13181 // Note that we may be accessing this outside of a lock... 13182 // shouldn't be a big deal, if this is being called outside 13183 // of a locked context there is intrinsically a race with 13184 // the value the caller will receive and someone else changing it. 13185 userId = mCurrentUserId; 13186 } 13187 if (!allowAll && userId < 0) { 13188 throw new IllegalArgumentException( 13189 "Call does not support special user #" + userId); 13190 } 13191 } 13192 return userId; 13193 } 13194 13195 boolean isSingleton(String componentProcessName, ApplicationInfo aInfo, 13196 String className, int flags) { 13197 boolean result = false; 13198 // For apps that don't have pre-defined UIDs, check for permission 13199 if (UserHandle.getAppId(aInfo.uid) >= Process.FIRST_APPLICATION_UID) { 13200 if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 13201 if (ActivityManager.checkUidPermission( 13202 android.Manifest.permission.INTERACT_ACROSS_USERS, 13203 aInfo.uid) != PackageManager.PERMISSION_GRANTED) { 13204 ComponentName comp = new ComponentName(aInfo.packageName, className); 13205 String msg = "Permission Denial: Component " + comp.flattenToShortString() 13206 + " requests FLAG_SINGLE_USER, but app does not hold " 13207 + android.Manifest.permission.INTERACT_ACROSS_USERS; 13208 Slog.w(TAG, msg); 13209 throw new SecurityException(msg); 13210 } 13211 // Permission passed 13212 result = true; 13213 } 13214 } else if ("system".equals(componentProcessName)) { 13215 result = true; 13216 } else { 13217 // App with pre-defined UID, check if it's a persistent app 13218 result = (aInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0; 13219 } 13220 if (DEBUG_MU) { 13221 Slog.v(TAG, "isSingleton(" + componentProcessName + ", " + aInfo 13222 + ", " + className + ", 0x" + Integer.toHexString(flags) + ") = " + result); 13223 } 13224 return result; 13225 } 13226 13227 /** 13228 * Checks to see if the caller is in the same app as the singleton 13229 * component, or the component is in a special app. It allows special apps 13230 * to export singleton components but prevents exporting singleton 13231 * components for regular apps. 13232 */ 13233 boolean isValidSingletonCall(int callingUid, int componentUid) { 13234 int componentAppId = UserHandle.getAppId(componentUid); 13235 return UserHandle.isSameApp(callingUid, componentUid) 13236 || componentAppId == Process.SYSTEM_UID 13237 || componentAppId == Process.PHONE_UID 13238 || ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, componentUid) 13239 == PackageManager.PERMISSION_GRANTED; 13240 } 13241 13242 public int bindService(IApplicationThread caller, IBinder token, 13243 Intent service, String resolvedType, 13244 IServiceConnection connection, int flags, int userId) { 13245 enforceNotIsolatedCaller("bindService"); 13246 // Refuse possible leaked file descriptors 13247 if (service != null && service.hasFileDescriptors() == true) { 13248 throw new IllegalArgumentException("File descriptors passed in Intent"); 13249 } 13250 13251 synchronized(this) { 13252 return mServices.bindServiceLocked(caller, token, service, resolvedType, 13253 connection, flags, userId); 13254 } 13255 } 13256 13257 public boolean unbindService(IServiceConnection connection) { 13258 synchronized (this) { 13259 return mServices.unbindServiceLocked(connection); 13260 } 13261 } 13262 13263 public void publishService(IBinder token, Intent intent, IBinder service) { 13264 // Refuse possible leaked file descriptors 13265 if (intent != null && intent.hasFileDescriptors() == true) { 13266 throw new IllegalArgumentException("File descriptors passed in Intent"); 13267 } 13268 13269 synchronized(this) { 13270 if (!(token instanceof ServiceRecord)) { 13271 throw new IllegalArgumentException("Invalid service token"); 13272 } 13273 mServices.publishServiceLocked((ServiceRecord)token, intent, service); 13274 } 13275 } 13276 13277 public void unbindFinished(IBinder token, Intent intent, boolean doRebind) { 13278 // Refuse possible leaked file descriptors 13279 if (intent != null && intent.hasFileDescriptors() == true) { 13280 throw new IllegalArgumentException("File descriptors passed in Intent"); 13281 } 13282 13283 synchronized(this) { 13284 mServices.unbindFinishedLocked((ServiceRecord)token, intent, doRebind); 13285 } 13286 } 13287 13288 public void serviceDoneExecuting(IBinder token, int type, int startId, int res) { 13289 synchronized(this) { 13290 if (!(token instanceof ServiceRecord)) { 13291 throw new IllegalArgumentException("Invalid service token"); 13292 } 13293 mServices.serviceDoneExecutingLocked((ServiceRecord)token, type, startId, res); 13294 } 13295 } 13296 13297 // ========================================================= 13298 // BACKUP AND RESTORE 13299 // ========================================================= 13300 13301 // Cause the target app to be launched if necessary and its backup agent 13302 // instantiated. The backup agent will invoke backupAgentCreated() on the 13303 // activity manager to announce its creation. 13304 public boolean bindBackupAgent(ApplicationInfo app, int backupMode) { 13305 if (DEBUG_BACKUP) Slog.v(TAG, "bindBackupAgent: app=" + app + " mode=" + backupMode); 13306 enforceCallingPermission("android.permission.BACKUP", "bindBackupAgent"); 13307 13308 synchronized(this) { 13309 // !!! TODO: currently no check here that we're already bound 13310 BatteryStatsImpl.Uid.Pkg.Serv ss = null; 13311 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 13312 synchronized (stats) { 13313 ss = stats.getServiceStatsLocked(app.uid, app.packageName, app.name); 13314 } 13315 13316 // Backup agent is now in use, its package can't be stopped. 13317 try { 13318 AppGlobals.getPackageManager().setPackageStoppedState( 13319 app.packageName, false, UserHandle.getUserId(app.uid)); 13320 } catch (RemoteException e) { 13321 } catch (IllegalArgumentException e) { 13322 Slog.w(TAG, "Failed trying to unstop package " 13323 + app.packageName + ": " + e); 13324 } 13325 13326 BackupRecord r = new BackupRecord(ss, app, backupMode); 13327 ComponentName hostingName = (backupMode == IApplicationThread.BACKUP_MODE_INCREMENTAL) 13328 ? new ComponentName(app.packageName, app.backupAgentName) 13329 : new ComponentName("android", "FullBackupAgent"); 13330 // startProcessLocked() returns existing proc's record if it's already running 13331 ProcessRecord proc = startProcessLocked(app.processName, app, 13332 false, 0, "backup", hostingName, false, false, false); 13333 if (proc == null) { 13334 Slog.e(TAG, "Unable to start backup agent process " + r); 13335 return false; 13336 } 13337 13338 r.app = proc; 13339 mBackupTarget = r; 13340 mBackupAppName = app.packageName; 13341 13342 // Try not to kill the process during backup 13343 updateOomAdjLocked(proc); 13344 13345 // If the process is already attached, schedule the creation of the backup agent now. 13346 // If it is not yet live, this will be done when it attaches to the framework. 13347 if (proc.thread != null) { 13348 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc already running: " + proc); 13349 try { 13350 proc.thread.scheduleCreateBackupAgent(app, 13351 compatibilityInfoForPackageLocked(app), backupMode); 13352 } catch (RemoteException e) { 13353 // Will time out on the backup manager side 13354 } 13355 } else { 13356 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc not running, waiting for attach"); 13357 } 13358 // Invariants: at this point, the target app process exists and the application 13359 // is either already running or in the process of coming up. mBackupTarget and 13360 // mBackupAppName describe the app, so that when it binds back to the AM we 13361 // know that it's scheduled for a backup-agent operation. 13362 } 13363 13364 return true; 13365 } 13366 13367 @Override 13368 public void clearPendingBackup() { 13369 if (DEBUG_BACKUP) Slog.v(TAG, "clearPendingBackup"); 13370 enforceCallingPermission("android.permission.BACKUP", "clearPendingBackup"); 13371 13372 synchronized (this) { 13373 mBackupTarget = null; 13374 mBackupAppName = null; 13375 } 13376 } 13377 13378 // A backup agent has just come up 13379 public void backupAgentCreated(String agentPackageName, IBinder agent) { 13380 if (DEBUG_BACKUP) Slog.v(TAG, "backupAgentCreated: " + agentPackageName 13381 + " = " + agent); 13382 13383 synchronized(this) { 13384 if (!agentPackageName.equals(mBackupAppName)) { 13385 Slog.e(TAG, "Backup agent created for " + agentPackageName + " but not requested!"); 13386 return; 13387 } 13388 } 13389 13390 long oldIdent = Binder.clearCallingIdentity(); 13391 try { 13392 IBackupManager bm = IBackupManager.Stub.asInterface( 13393 ServiceManager.getService(Context.BACKUP_SERVICE)); 13394 bm.agentConnected(agentPackageName, agent); 13395 } catch (RemoteException e) { 13396 // can't happen; the backup manager service is local 13397 } catch (Exception e) { 13398 Slog.w(TAG, "Exception trying to deliver BackupAgent binding: "); 13399 e.printStackTrace(); 13400 } finally { 13401 Binder.restoreCallingIdentity(oldIdent); 13402 } 13403 } 13404 13405 // done with this agent 13406 public void unbindBackupAgent(ApplicationInfo appInfo) { 13407 if (DEBUG_BACKUP) Slog.v(TAG, "unbindBackupAgent: " + appInfo); 13408 if (appInfo == null) { 13409 Slog.w(TAG, "unbind backup agent for null app"); 13410 return; 13411 } 13412 13413 synchronized(this) { 13414 try { 13415 if (mBackupAppName == null) { 13416 Slog.w(TAG, "Unbinding backup agent with no active backup"); 13417 return; 13418 } 13419 13420 if (!mBackupAppName.equals(appInfo.packageName)) { 13421 Slog.e(TAG, "Unbind of " + appInfo + " but is not the current backup target"); 13422 return; 13423 } 13424 13425 // Not backing this app up any more; reset its OOM adjustment 13426 final ProcessRecord proc = mBackupTarget.app; 13427 updateOomAdjLocked(proc); 13428 13429 // If the app crashed during backup, 'thread' will be null here 13430 if (proc.thread != null) { 13431 try { 13432 proc.thread.scheduleDestroyBackupAgent(appInfo, 13433 compatibilityInfoForPackageLocked(appInfo)); 13434 } catch (Exception e) { 13435 Slog.e(TAG, "Exception when unbinding backup agent:"); 13436 e.printStackTrace(); 13437 } 13438 } 13439 } finally { 13440 mBackupTarget = null; 13441 mBackupAppName = null; 13442 } 13443 } 13444 } 13445 // ========================================================= 13446 // BROADCASTS 13447 // ========================================================= 13448 13449 private final List getStickiesLocked(String action, IntentFilter filter, 13450 List cur, int userId) { 13451 final ContentResolver resolver = mContext.getContentResolver(); 13452 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 13453 if (stickies == null) { 13454 return cur; 13455 } 13456 final ArrayList<Intent> list = stickies.get(action); 13457 if (list == null) { 13458 return cur; 13459 } 13460 int N = list.size(); 13461 for (int i=0; i<N; i++) { 13462 Intent intent = list.get(i); 13463 if (filter.match(resolver, intent, true, TAG) >= 0) { 13464 if (cur == null) { 13465 cur = new ArrayList<Intent>(); 13466 } 13467 cur.add(intent); 13468 } 13469 } 13470 return cur; 13471 } 13472 13473 boolean isPendingBroadcastProcessLocked(int pid) { 13474 return mFgBroadcastQueue.isPendingBroadcastProcessLocked(pid) 13475 || mBgBroadcastQueue.isPendingBroadcastProcessLocked(pid); 13476 } 13477 13478 void skipPendingBroadcastLocked(int pid) { 13479 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 13480 for (BroadcastQueue queue : mBroadcastQueues) { 13481 queue.skipPendingBroadcastLocked(pid); 13482 } 13483 } 13484 13485 // The app just attached; send any pending broadcasts that it should receive 13486 boolean sendPendingBroadcastsLocked(ProcessRecord app) { 13487 boolean didSomething = false; 13488 for (BroadcastQueue queue : mBroadcastQueues) { 13489 didSomething |= queue.sendPendingBroadcastsLocked(app); 13490 } 13491 return didSomething; 13492 } 13493 13494 public Intent registerReceiver(IApplicationThread caller, String callerPackage, 13495 IIntentReceiver receiver, IntentFilter filter, String permission, int userId) { 13496 enforceNotIsolatedCaller("registerReceiver"); 13497 int callingUid; 13498 int callingPid; 13499 synchronized(this) { 13500 ProcessRecord callerApp = null; 13501 if (caller != null) { 13502 callerApp = getRecordForAppLocked(caller); 13503 if (callerApp == null) { 13504 throw new SecurityException( 13505 "Unable to find app for caller " + caller 13506 + " (pid=" + Binder.getCallingPid() 13507 + ") when registering receiver " + receiver); 13508 } 13509 if (callerApp.info.uid != Process.SYSTEM_UID && 13510 !callerApp.pkgList.containsKey(callerPackage) && 13511 !"android".equals(callerPackage)) { 13512 throw new SecurityException("Given caller package " + callerPackage 13513 + " is not running in process " + callerApp); 13514 } 13515 callingUid = callerApp.info.uid; 13516 callingPid = callerApp.pid; 13517 } else { 13518 callerPackage = null; 13519 callingUid = Binder.getCallingUid(); 13520 callingPid = Binder.getCallingPid(); 13521 } 13522 13523 userId = this.handleIncomingUser(callingPid, callingUid, userId, 13524 true, true, "registerReceiver", callerPackage); 13525 13526 List allSticky = null; 13527 13528 // Look for any matching sticky broadcasts... 13529 Iterator actions = filter.actionsIterator(); 13530 if (actions != null) { 13531 while (actions.hasNext()) { 13532 String action = (String)actions.next(); 13533 allSticky = getStickiesLocked(action, filter, allSticky, 13534 UserHandle.USER_ALL); 13535 allSticky = getStickiesLocked(action, filter, allSticky, 13536 UserHandle.getUserId(callingUid)); 13537 } 13538 } else { 13539 allSticky = getStickiesLocked(null, filter, allSticky, 13540 UserHandle.USER_ALL); 13541 allSticky = getStickiesLocked(null, filter, allSticky, 13542 UserHandle.getUserId(callingUid)); 13543 } 13544 13545 // The first sticky in the list is returned directly back to 13546 // the client. 13547 Intent sticky = allSticky != null ? (Intent)allSticky.get(0) : null; 13548 13549 if (DEBUG_BROADCAST) Slog.v(TAG, "Register receiver " + filter 13550 + ": " + sticky); 13551 13552 if (receiver == null) { 13553 return sticky; 13554 } 13555 13556 ReceiverList rl 13557 = (ReceiverList)mRegisteredReceivers.get(receiver.asBinder()); 13558 if (rl == null) { 13559 rl = new ReceiverList(this, callerApp, callingPid, callingUid, 13560 userId, receiver); 13561 if (rl.app != null) { 13562 rl.app.receivers.add(rl); 13563 } else { 13564 try { 13565 receiver.asBinder().linkToDeath(rl, 0); 13566 } catch (RemoteException e) { 13567 return sticky; 13568 } 13569 rl.linkedToDeath = true; 13570 } 13571 mRegisteredReceivers.put(receiver.asBinder(), rl); 13572 } else if (rl.uid != callingUid) { 13573 throw new IllegalArgumentException( 13574 "Receiver requested to register for uid " + callingUid 13575 + " was previously registered for uid " + rl.uid); 13576 } else if (rl.pid != callingPid) { 13577 throw new IllegalArgumentException( 13578 "Receiver requested to register for pid " + callingPid 13579 + " was previously registered for pid " + rl.pid); 13580 } else if (rl.userId != userId) { 13581 throw new IllegalArgumentException( 13582 "Receiver requested to register for user " + userId 13583 + " was previously registered for user " + rl.userId); 13584 } 13585 BroadcastFilter bf = new BroadcastFilter(filter, rl, callerPackage, 13586 permission, callingUid, userId); 13587 rl.add(bf); 13588 if (!bf.debugCheck()) { 13589 Slog.w(TAG, "==> For Dynamic broadast"); 13590 } 13591 mReceiverResolver.addFilter(bf); 13592 13593 // Enqueue broadcasts for all existing stickies that match 13594 // this filter. 13595 if (allSticky != null) { 13596 ArrayList receivers = new ArrayList(); 13597 receivers.add(bf); 13598 13599 int N = allSticky.size(); 13600 for (int i=0; i<N; i++) { 13601 Intent intent = (Intent)allSticky.get(i); 13602 BroadcastQueue queue = broadcastQueueForIntent(intent); 13603 BroadcastRecord r = new BroadcastRecord(queue, intent, null, 13604 null, -1, -1, null, null, AppOpsManager.OP_NONE, receivers, null, 0, 13605 null, null, false, true, true, -1); 13606 queue.enqueueParallelBroadcastLocked(r); 13607 queue.scheduleBroadcastsLocked(); 13608 } 13609 } 13610 13611 return sticky; 13612 } 13613 } 13614 13615 public void unregisterReceiver(IIntentReceiver receiver) { 13616 if (DEBUG_BROADCAST) Slog.v(TAG, "Unregister receiver: " + receiver); 13617 13618 final long origId = Binder.clearCallingIdentity(); 13619 try { 13620 boolean doTrim = false; 13621 13622 synchronized(this) { 13623 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder()); 13624 if (rl != null) { 13625 if (rl.curBroadcast != null) { 13626 BroadcastRecord r = rl.curBroadcast; 13627 final boolean doNext = finishReceiverLocked( 13628 receiver.asBinder(), r.resultCode, r.resultData, 13629 r.resultExtras, r.resultAbort); 13630 if (doNext) { 13631 doTrim = true; 13632 r.queue.processNextBroadcast(false); 13633 } 13634 } 13635 13636 if (rl.app != null) { 13637 rl.app.receivers.remove(rl); 13638 } 13639 removeReceiverLocked(rl); 13640 if (rl.linkedToDeath) { 13641 rl.linkedToDeath = false; 13642 rl.receiver.asBinder().unlinkToDeath(rl, 0); 13643 } 13644 } 13645 } 13646 13647 // If we actually concluded any broadcasts, we might now be able 13648 // to trim the recipients' apps from our working set 13649 if (doTrim) { 13650 trimApplications(); 13651 return; 13652 } 13653 13654 } finally { 13655 Binder.restoreCallingIdentity(origId); 13656 } 13657 } 13658 13659 void removeReceiverLocked(ReceiverList rl) { 13660 mRegisteredReceivers.remove(rl.receiver.asBinder()); 13661 int N = rl.size(); 13662 for (int i=0; i<N; i++) { 13663 mReceiverResolver.removeFilter(rl.get(i)); 13664 } 13665 } 13666 13667 private final void sendPackageBroadcastLocked(int cmd, String[] packages, int userId) { 13668 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 13669 ProcessRecord r = mLruProcesses.get(i); 13670 if (r.thread != null && (userId == UserHandle.USER_ALL || r.userId == userId)) { 13671 try { 13672 r.thread.dispatchPackageBroadcast(cmd, packages); 13673 } catch (RemoteException ex) { 13674 } 13675 } 13676 } 13677 } 13678 13679 private List<ResolveInfo> collectReceiverComponents(Intent intent, String resolvedType, 13680 int[] users) { 13681 List<ResolveInfo> receivers = null; 13682 try { 13683 HashSet<ComponentName> singleUserReceivers = null; 13684 boolean scannedFirstReceivers = false; 13685 for (int user : users) { 13686 List<ResolveInfo> newReceivers = AppGlobals.getPackageManager() 13687 .queryIntentReceivers(intent, resolvedType, STOCK_PM_FLAGS, user); 13688 if (user != 0 && newReceivers != null) { 13689 // If this is not the primary user, we need to check for 13690 // any receivers that should be filtered out. 13691 for (int i=0; i<newReceivers.size(); i++) { 13692 ResolveInfo ri = newReceivers.get(i); 13693 if ((ri.activityInfo.flags&ActivityInfo.FLAG_PRIMARY_USER_ONLY) != 0) { 13694 newReceivers.remove(i); 13695 i--; 13696 } 13697 } 13698 } 13699 if (newReceivers != null && newReceivers.size() == 0) { 13700 newReceivers = null; 13701 } 13702 if (receivers == null) { 13703 receivers = newReceivers; 13704 } else if (newReceivers != null) { 13705 // We need to concatenate the additional receivers 13706 // found with what we have do far. This would be easy, 13707 // but we also need to de-dup any receivers that are 13708 // singleUser. 13709 if (!scannedFirstReceivers) { 13710 // Collect any single user receivers we had already retrieved. 13711 scannedFirstReceivers = true; 13712 for (int i=0; i<receivers.size(); i++) { 13713 ResolveInfo ri = receivers.get(i); 13714 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 13715 ComponentName cn = new ComponentName( 13716 ri.activityInfo.packageName, ri.activityInfo.name); 13717 if (singleUserReceivers == null) { 13718 singleUserReceivers = new HashSet<ComponentName>(); 13719 } 13720 singleUserReceivers.add(cn); 13721 } 13722 } 13723 } 13724 // Add the new results to the existing results, tracking 13725 // and de-dupping single user receivers. 13726 for (int i=0; i<newReceivers.size(); i++) { 13727 ResolveInfo ri = newReceivers.get(i); 13728 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 13729 ComponentName cn = new ComponentName( 13730 ri.activityInfo.packageName, ri.activityInfo.name); 13731 if (singleUserReceivers == null) { 13732 singleUserReceivers = new HashSet<ComponentName>(); 13733 } 13734 if (!singleUserReceivers.contains(cn)) { 13735 singleUserReceivers.add(cn); 13736 receivers.add(ri); 13737 } 13738 } else { 13739 receivers.add(ri); 13740 } 13741 } 13742 } 13743 } 13744 } catch (RemoteException ex) { 13745 // pm is in same process, this will never happen. 13746 } 13747 return receivers; 13748 } 13749 13750 private final int broadcastIntentLocked(ProcessRecord callerApp, 13751 String callerPackage, Intent intent, String resolvedType, 13752 IIntentReceiver resultTo, int resultCode, String resultData, 13753 Bundle map, String requiredPermission, int appOp, 13754 boolean ordered, boolean sticky, int callingPid, int callingUid, 13755 int userId) { 13756 intent = new Intent(intent); 13757 13758 // By default broadcasts do not go to stopped apps. 13759 intent.addFlags(Intent.FLAG_EXCLUDE_STOPPED_PACKAGES); 13760 13761 if (DEBUG_BROADCAST_LIGHT) Slog.v( 13762 TAG, (sticky ? "Broadcast sticky: ": "Broadcast: ") + intent 13763 + " ordered=" + ordered + " userid=" + userId); 13764 if ((resultTo != null) && !ordered) { 13765 Slog.w(TAG, "Broadcast " + intent + " not ordered but result callback requested!"); 13766 } 13767 13768 userId = handleIncomingUser(callingPid, callingUid, userId, 13769 true, false, "broadcast", callerPackage); 13770 13771 // Make sure that the user who is receiving this broadcast is started. 13772 // If not, we will just skip it. 13773 if (userId != UserHandle.USER_ALL && mStartedUsers.get(userId) == null) { 13774 if (callingUid != Process.SYSTEM_UID || (intent.getFlags() 13775 & Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) { 13776 Slog.w(TAG, "Skipping broadcast of " + intent 13777 + ": user " + userId + " is stopped"); 13778 return ActivityManager.BROADCAST_SUCCESS; 13779 } 13780 } 13781 13782 /* 13783 * Prevent non-system code (defined here to be non-persistent 13784 * processes) from sending protected broadcasts. 13785 */ 13786 int callingAppId = UserHandle.getAppId(callingUid); 13787 if (callingAppId == Process.SYSTEM_UID || callingAppId == Process.PHONE_UID 13788 || callingAppId == Process.SHELL_UID || callingAppId == Process.BLUETOOTH_UID 13789 || callingUid == 0) { 13790 // Always okay. 13791 } else if (callerApp == null || !callerApp.persistent) { 13792 try { 13793 if (AppGlobals.getPackageManager().isProtectedBroadcast( 13794 intent.getAction())) { 13795 String msg = "Permission Denial: not allowed to send broadcast " 13796 + intent.getAction() + " from pid=" 13797 + callingPid + ", uid=" + callingUid; 13798 Slog.w(TAG, msg); 13799 throw new SecurityException(msg); 13800 } else if (AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(intent.getAction())) { 13801 // Special case for compatibility: we don't want apps to send this, 13802 // but historically it has not been protected and apps may be using it 13803 // to poke their own app widget. So, instead of making it protected, 13804 // just limit it to the caller. 13805 if (callerApp == null) { 13806 String msg = "Permission Denial: not allowed to send broadcast " 13807 + intent.getAction() + " from unknown caller."; 13808 Slog.w(TAG, msg); 13809 throw new SecurityException(msg); 13810 } else if (intent.getComponent() != null) { 13811 // They are good enough to send to an explicit component... verify 13812 // it is being sent to the calling app. 13813 if (!intent.getComponent().getPackageName().equals( 13814 callerApp.info.packageName)) { 13815 String msg = "Permission Denial: not allowed to send broadcast " 13816 + intent.getAction() + " to " 13817 + intent.getComponent().getPackageName() + " from " 13818 + callerApp.info.packageName; 13819 Slog.w(TAG, msg); 13820 throw new SecurityException(msg); 13821 } 13822 } else { 13823 // Limit broadcast to their own package. 13824 intent.setPackage(callerApp.info.packageName); 13825 } 13826 } 13827 } catch (RemoteException e) { 13828 Slog.w(TAG, "Remote exception", e); 13829 return ActivityManager.BROADCAST_SUCCESS; 13830 } 13831 } 13832 13833 // Handle special intents: if this broadcast is from the package 13834 // manager about a package being removed, we need to remove all of 13835 // its activities from the history stack. 13836 final boolean uidRemoved = Intent.ACTION_UID_REMOVED.equals( 13837 intent.getAction()); 13838 if (Intent.ACTION_PACKAGE_REMOVED.equals(intent.getAction()) 13839 || Intent.ACTION_PACKAGE_CHANGED.equals(intent.getAction()) 13840 || Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction()) 13841 || uidRemoved) { 13842 if (checkComponentPermission( 13843 android.Manifest.permission.BROADCAST_PACKAGE_REMOVED, 13844 callingPid, callingUid, -1, true) 13845 == PackageManager.PERMISSION_GRANTED) { 13846 if (uidRemoved) { 13847 final Bundle intentExtras = intent.getExtras(); 13848 final int uid = intentExtras != null 13849 ? intentExtras.getInt(Intent.EXTRA_UID) : -1; 13850 if (uid >= 0) { 13851 BatteryStatsImpl bs = mBatteryStatsService.getActiveStatistics(); 13852 synchronized (bs) { 13853 bs.removeUidStatsLocked(uid); 13854 } 13855 mAppOpsService.uidRemoved(uid); 13856 } 13857 } else { 13858 // If resources are unavailable just force stop all 13859 // those packages and flush the attribute cache as well. 13860 if (Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction())) { 13861 String list[] = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 13862 if (list != null && (list.length > 0)) { 13863 for (String pkg : list) { 13864 forceStopPackageLocked(pkg, -1, false, true, true, false, false, userId, 13865 "storage unmount"); 13866 } 13867 sendPackageBroadcastLocked( 13868 IApplicationThread.EXTERNAL_STORAGE_UNAVAILABLE, list, userId); 13869 } 13870 } else { 13871 Uri data = intent.getData(); 13872 String ssp; 13873 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 13874 boolean removed = Intent.ACTION_PACKAGE_REMOVED.equals( 13875 intent.getAction()); 13876 boolean fullUninstall = removed && 13877 !intent.getBooleanExtra(Intent.EXTRA_REPLACING, false); 13878 if (!intent.getBooleanExtra(Intent.EXTRA_DONT_KILL_APP, false)) { 13879 forceStopPackageLocked(ssp, UserHandle.getAppId( 13880 intent.getIntExtra(Intent.EXTRA_UID, -1)), false, true, true, 13881 false, fullUninstall, userId, 13882 removed ? "pkg removed" : "pkg changed"); 13883 } 13884 if (removed) { 13885 sendPackageBroadcastLocked(IApplicationThread.PACKAGE_REMOVED, 13886 new String[] {ssp}, userId); 13887 if (!intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)) { 13888 mAppOpsService.packageRemoved( 13889 intent.getIntExtra(Intent.EXTRA_UID, -1), ssp); 13890 13891 // Remove all permissions granted from/to this package 13892 removeUriPermissionsForPackageLocked(ssp, userId, true); 13893 } 13894 } 13895 } 13896 } 13897 } 13898 } else { 13899 String msg = "Permission Denial: " + intent.getAction() 13900 + " broadcast from " + callerPackage + " (pid=" + callingPid 13901 + ", uid=" + callingUid + ")" 13902 + " requires " 13903 + android.Manifest.permission.BROADCAST_PACKAGE_REMOVED; 13904 Slog.w(TAG, msg); 13905 throw new SecurityException(msg); 13906 } 13907 13908 // Special case for adding a package: by default turn on compatibility 13909 // mode. 13910 } else if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction())) { 13911 Uri data = intent.getData(); 13912 String ssp; 13913 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 13914 mCompatModePackages.handlePackageAddedLocked(ssp, 13915 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)); 13916 } 13917 } 13918 13919 /* 13920 * If this is the time zone changed action, queue up a message that will reset the timezone 13921 * of all currently running processes. This message will get queued up before the broadcast 13922 * happens. 13923 */ 13924 if (Intent.ACTION_TIMEZONE_CHANGED.equals(intent.getAction())) { 13925 mHandler.sendEmptyMessage(UPDATE_TIME_ZONE); 13926 } 13927 13928 /* 13929 * If the user set the time, let all running processes know. 13930 */ 13931 if (Intent.ACTION_TIME_CHANGED.equals(intent.getAction())) { 13932 final int is24Hour = intent.getBooleanExtra( 13933 Intent.EXTRA_TIME_PREF_24_HOUR_FORMAT, false) ? 1 : 0; 13934 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_TIME, is24Hour, 0)); 13935 } 13936 13937 if (Intent.ACTION_CLEAR_DNS_CACHE.equals(intent.getAction())) { 13938 mHandler.sendEmptyMessage(CLEAR_DNS_CACHE_MSG); 13939 } 13940 13941 if (Proxy.PROXY_CHANGE_ACTION.equals(intent.getAction())) { 13942 ProxyInfo proxy = intent.getParcelableExtra(Proxy.EXTRA_PROXY_INFO); 13943 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_HTTP_PROXY_MSG, proxy)); 13944 } 13945 13946 // Add to the sticky list if requested. 13947 if (sticky) { 13948 if (checkPermission(android.Manifest.permission.BROADCAST_STICKY, 13949 callingPid, callingUid) 13950 != PackageManager.PERMISSION_GRANTED) { 13951 String msg = "Permission Denial: broadcastIntent() requesting a sticky broadcast from pid=" 13952 + callingPid + ", uid=" + callingUid 13953 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 13954 Slog.w(TAG, msg); 13955 throw new SecurityException(msg); 13956 } 13957 if (requiredPermission != null) { 13958 Slog.w(TAG, "Can't broadcast sticky intent " + intent 13959 + " and enforce permission " + requiredPermission); 13960 return ActivityManager.BROADCAST_STICKY_CANT_HAVE_PERMISSION; 13961 } 13962 if (intent.getComponent() != null) { 13963 throw new SecurityException( 13964 "Sticky broadcasts can't target a specific component"); 13965 } 13966 // We use userId directly here, since the "all" target is maintained 13967 // as a separate set of sticky broadcasts. 13968 if (userId != UserHandle.USER_ALL) { 13969 // But first, if this is not a broadcast to all users, then 13970 // make sure it doesn't conflict with an existing broadcast to 13971 // all users. 13972 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get( 13973 UserHandle.USER_ALL); 13974 if (stickies != null) { 13975 ArrayList<Intent> list = stickies.get(intent.getAction()); 13976 if (list != null) { 13977 int N = list.size(); 13978 int i; 13979 for (i=0; i<N; i++) { 13980 if (intent.filterEquals(list.get(i))) { 13981 throw new IllegalArgumentException( 13982 "Sticky broadcast " + intent + " for user " 13983 + userId + " conflicts with existing global broadcast"); 13984 } 13985 } 13986 } 13987 } 13988 } 13989 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 13990 if (stickies == null) { 13991 stickies = new ArrayMap<String, ArrayList<Intent>>(); 13992 mStickyBroadcasts.put(userId, stickies); 13993 } 13994 ArrayList<Intent> list = stickies.get(intent.getAction()); 13995 if (list == null) { 13996 list = new ArrayList<Intent>(); 13997 stickies.put(intent.getAction(), list); 13998 } 13999 int N = list.size(); 14000 int i; 14001 for (i=0; i<N; i++) { 14002 if (intent.filterEquals(list.get(i))) { 14003 // This sticky already exists, replace it. 14004 list.set(i, new Intent(intent)); 14005 break; 14006 } 14007 } 14008 if (i >= N) { 14009 list.add(new Intent(intent)); 14010 } 14011 } 14012 14013 int[] users; 14014 if (userId == UserHandle.USER_ALL) { 14015 // Caller wants broadcast to go to all started users. 14016 users = mStartedUserArray; 14017 } else { 14018 // Caller wants broadcast to go to one specific user. 14019 users = new int[] {userId}; 14020 } 14021 14022 // Figure out who all will receive this broadcast. 14023 List receivers = null; 14024 List<BroadcastFilter> registeredReceivers = null; 14025 // Need to resolve the intent to interested receivers... 14026 if ((intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) 14027 == 0) { 14028 receivers = collectReceiverComponents(intent, resolvedType, users); 14029 } 14030 if (intent.getComponent() == null) { 14031 registeredReceivers = mReceiverResolver.queryIntent(intent, 14032 resolvedType, false, userId); 14033 } 14034 14035 final boolean replacePending = 14036 (intent.getFlags()&Intent.FLAG_RECEIVER_REPLACE_PENDING) != 0; 14037 14038 if (DEBUG_BROADCAST) Slog.v(TAG, "Enqueing broadcast: " + intent.getAction() 14039 + " replacePending=" + replacePending); 14040 14041 int NR = registeredReceivers != null ? registeredReceivers.size() : 0; 14042 if (!ordered && NR > 0) { 14043 // If we are not serializing this broadcast, then send the 14044 // registered receivers separately so they don't wait for the 14045 // components to be launched. 14046 final BroadcastQueue queue = broadcastQueueForIntent(intent); 14047 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 14048 callerPackage, callingPid, callingUid, resolvedType, requiredPermission, 14049 appOp, registeredReceivers, resultTo, resultCode, resultData, map, 14050 ordered, sticky, false, userId); 14051 if (DEBUG_BROADCAST) Slog.v( 14052 TAG, "Enqueueing parallel broadcast " + r); 14053 final boolean replaced = replacePending && queue.replaceParallelBroadcastLocked(r); 14054 if (!replaced) { 14055 queue.enqueueParallelBroadcastLocked(r); 14056 queue.scheduleBroadcastsLocked(); 14057 } 14058 registeredReceivers = null; 14059 NR = 0; 14060 } 14061 14062 // Merge into one list. 14063 int ir = 0; 14064 if (receivers != null) { 14065 // A special case for PACKAGE_ADDED: do not allow the package 14066 // being added to see this broadcast. This prevents them from 14067 // using this as a back door to get run as soon as they are 14068 // installed. Maybe in the future we want to have a special install 14069 // broadcast or such for apps, but we'd like to deliberately make 14070 // this decision. 14071 String skipPackages[] = null; 14072 if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction()) 14073 || Intent.ACTION_PACKAGE_RESTARTED.equals(intent.getAction()) 14074 || Intent.ACTION_PACKAGE_DATA_CLEARED.equals(intent.getAction())) { 14075 Uri data = intent.getData(); 14076 if (data != null) { 14077 String pkgName = data.getSchemeSpecificPart(); 14078 if (pkgName != null) { 14079 skipPackages = new String[] { pkgName }; 14080 } 14081 } 14082 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction())) { 14083 skipPackages = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 14084 } 14085 if (skipPackages != null && (skipPackages.length > 0)) { 14086 for (String skipPackage : skipPackages) { 14087 if (skipPackage != null) { 14088 int NT = receivers.size(); 14089 for (int it=0; it<NT; it++) { 14090 ResolveInfo curt = (ResolveInfo)receivers.get(it); 14091 if (curt.activityInfo.packageName.equals(skipPackage)) { 14092 receivers.remove(it); 14093 it--; 14094 NT--; 14095 } 14096 } 14097 } 14098 } 14099 } 14100 14101 int NT = receivers != null ? receivers.size() : 0; 14102 int it = 0; 14103 ResolveInfo curt = null; 14104 BroadcastFilter curr = null; 14105 while (it < NT && ir < NR) { 14106 if (curt == null) { 14107 curt = (ResolveInfo)receivers.get(it); 14108 } 14109 if (curr == null) { 14110 curr = registeredReceivers.get(ir); 14111 } 14112 if (curr.getPriority() >= curt.priority) { 14113 // Insert this broadcast record into the final list. 14114 receivers.add(it, curr); 14115 ir++; 14116 curr = null; 14117 it++; 14118 NT++; 14119 } else { 14120 // Skip to the next ResolveInfo in the final list. 14121 it++; 14122 curt = null; 14123 } 14124 } 14125 } 14126 while (ir < NR) { 14127 if (receivers == null) { 14128 receivers = new ArrayList(); 14129 } 14130 receivers.add(registeredReceivers.get(ir)); 14131 ir++; 14132 } 14133 14134 if ((receivers != null && receivers.size() > 0) 14135 || resultTo != null) { 14136 BroadcastQueue queue = broadcastQueueForIntent(intent); 14137 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 14138 callerPackage, callingPid, callingUid, resolvedType, 14139 requiredPermission, appOp, receivers, resultTo, resultCode, 14140 resultData, map, ordered, sticky, false, userId); 14141 if (DEBUG_BROADCAST) Slog.v( 14142 TAG, "Enqueueing ordered broadcast " + r 14143 + ": prev had " + queue.mOrderedBroadcasts.size()); 14144 if (DEBUG_BROADCAST) { 14145 int seq = r.intent.getIntExtra("seq", -1); 14146 Slog.i(TAG, "Enqueueing broadcast " + r.intent.getAction() + " seq=" + seq); 14147 } 14148 boolean replaced = replacePending && queue.replaceOrderedBroadcastLocked(r); 14149 if (!replaced) { 14150 queue.enqueueOrderedBroadcastLocked(r); 14151 queue.scheduleBroadcastsLocked(); 14152 } 14153 } 14154 14155 return ActivityManager.BROADCAST_SUCCESS; 14156 } 14157 14158 final Intent verifyBroadcastLocked(Intent intent) { 14159 // Refuse possible leaked file descriptors 14160 if (intent != null && intent.hasFileDescriptors() == true) { 14161 throw new IllegalArgumentException("File descriptors passed in Intent"); 14162 } 14163 14164 int flags = intent.getFlags(); 14165 14166 if (!mProcessesReady) { 14167 // if the caller really truly claims to know what they're doing, go 14168 // ahead and allow the broadcast without launching any receivers 14169 if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT) != 0) { 14170 intent = new Intent(intent); 14171 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 14172 } else if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) { 14173 Slog.e(TAG, "Attempt to launch receivers of broadcast intent " + intent 14174 + " before boot completion"); 14175 throw new IllegalStateException("Cannot broadcast before boot completed"); 14176 } 14177 } 14178 14179 if ((flags&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 14180 throw new IllegalArgumentException( 14181 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 14182 } 14183 14184 return intent; 14185 } 14186 14187 public final int broadcastIntent(IApplicationThread caller, 14188 Intent intent, String resolvedType, IIntentReceiver resultTo, 14189 int resultCode, String resultData, Bundle map, 14190 String requiredPermission, int appOp, boolean serialized, boolean sticky, int userId) { 14191 enforceNotIsolatedCaller("broadcastIntent"); 14192 synchronized(this) { 14193 intent = verifyBroadcastLocked(intent); 14194 14195 final ProcessRecord callerApp = getRecordForAppLocked(caller); 14196 final int callingPid = Binder.getCallingPid(); 14197 final int callingUid = Binder.getCallingUid(); 14198 final long origId = Binder.clearCallingIdentity(); 14199 int res = broadcastIntentLocked(callerApp, 14200 callerApp != null ? callerApp.info.packageName : null, 14201 intent, resolvedType, resultTo, 14202 resultCode, resultData, map, requiredPermission, appOp, serialized, sticky, 14203 callingPid, callingUid, userId); 14204 Binder.restoreCallingIdentity(origId); 14205 return res; 14206 } 14207 } 14208 14209 int broadcastIntentInPackage(String packageName, int uid, 14210 Intent intent, String resolvedType, IIntentReceiver resultTo, 14211 int resultCode, String resultData, Bundle map, 14212 String requiredPermission, boolean serialized, boolean sticky, int userId) { 14213 synchronized(this) { 14214 intent = verifyBroadcastLocked(intent); 14215 14216 final long origId = Binder.clearCallingIdentity(); 14217 int res = broadcastIntentLocked(null, packageName, intent, resolvedType, 14218 resultTo, resultCode, resultData, map, requiredPermission, 14219 AppOpsManager.OP_NONE, serialized, sticky, -1, uid, userId); 14220 Binder.restoreCallingIdentity(origId); 14221 return res; 14222 } 14223 } 14224 14225 public final void unbroadcastIntent(IApplicationThread caller, Intent intent, int userId) { 14226 // Refuse possible leaked file descriptors 14227 if (intent != null && intent.hasFileDescriptors() == true) { 14228 throw new IllegalArgumentException("File descriptors passed in Intent"); 14229 } 14230 14231 userId = handleIncomingUser(Binder.getCallingPid(), 14232 Binder.getCallingUid(), userId, true, false, "removeStickyBroadcast", null); 14233 14234 synchronized(this) { 14235 if (checkCallingPermission(android.Manifest.permission.BROADCAST_STICKY) 14236 != PackageManager.PERMISSION_GRANTED) { 14237 String msg = "Permission Denial: unbroadcastIntent() from pid=" 14238 + Binder.getCallingPid() 14239 + ", uid=" + Binder.getCallingUid() 14240 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 14241 Slog.w(TAG, msg); 14242 throw new SecurityException(msg); 14243 } 14244 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 14245 if (stickies != null) { 14246 ArrayList<Intent> list = stickies.get(intent.getAction()); 14247 if (list != null) { 14248 int N = list.size(); 14249 int i; 14250 for (i=0; i<N; i++) { 14251 if (intent.filterEquals(list.get(i))) { 14252 list.remove(i); 14253 break; 14254 } 14255 } 14256 if (list.size() <= 0) { 14257 stickies.remove(intent.getAction()); 14258 } 14259 } 14260 if (stickies.size() <= 0) { 14261 mStickyBroadcasts.remove(userId); 14262 } 14263 } 14264 } 14265 } 14266 14267 private final boolean finishReceiverLocked(IBinder receiver, int resultCode, 14268 String resultData, Bundle resultExtras, boolean resultAbort) { 14269 final BroadcastRecord r = broadcastRecordForReceiverLocked(receiver); 14270 if (r == null) { 14271 Slog.w(TAG, "finishReceiver called but not found on queue"); 14272 return false; 14273 } 14274 14275 return r.queue.finishReceiverLocked(r, resultCode, resultData, resultExtras, resultAbort, false); 14276 } 14277 14278 void backgroundServicesFinishedLocked(int userId) { 14279 for (BroadcastQueue queue : mBroadcastQueues) { 14280 queue.backgroundServicesFinishedLocked(userId); 14281 } 14282 } 14283 14284 public void finishReceiver(IBinder who, int resultCode, String resultData, 14285 Bundle resultExtras, boolean resultAbort) { 14286 if (DEBUG_BROADCAST) Slog.v(TAG, "Finish receiver: " + who); 14287 14288 // Refuse possible leaked file descriptors 14289 if (resultExtras != null && resultExtras.hasFileDescriptors()) { 14290 throw new IllegalArgumentException("File descriptors passed in Bundle"); 14291 } 14292 14293 final long origId = Binder.clearCallingIdentity(); 14294 try { 14295 boolean doNext = false; 14296 BroadcastRecord r; 14297 14298 synchronized(this) { 14299 r = broadcastRecordForReceiverLocked(who); 14300 if (r != null) { 14301 doNext = r.queue.finishReceiverLocked(r, resultCode, 14302 resultData, resultExtras, resultAbort, true); 14303 } 14304 } 14305 14306 if (doNext) { 14307 r.queue.processNextBroadcast(false); 14308 } 14309 trimApplications(); 14310 } finally { 14311 Binder.restoreCallingIdentity(origId); 14312 } 14313 } 14314 14315 // ========================================================= 14316 // INSTRUMENTATION 14317 // ========================================================= 14318 14319 public boolean startInstrumentation(ComponentName className, 14320 String profileFile, int flags, Bundle arguments, 14321 IInstrumentationWatcher watcher, IUiAutomationConnection uiAutomationConnection, 14322 int userId, String abiOverride) { 14323 enforceNotIsolatedCaller("startInstrumentation"); 14324 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 14325 userId, false, true, "startInstrumentation", null); 14326 // Refuse possible leaked file descriptors 14327 if (arguments != null && arguments.hasFileDescriptors()) { 14328 throw new IllegalArgumentException("File descriptors passed in Bundle"); 14329 } 14330 14331 synchronized(this) { 14332 InstrumentationInfo ii = null; 14333 ApplicationInfo ai = null; 14334 try { 14335 ii = mContext.getPackageManager().getInstrumentationInfo( 14336 className, STOCK_PM_FLAGS); 14337 ai = AppGlobals.getPackageManager().getApplicationInfo( 14338 ii.targetPackage, STOCK_PM_FLAGS, userId); 14339 } catch (PackageManager.NameNotFoundException e) { 14340 } catch (RemoteException e) { 14341 } 14342 if (ii == null) { 14343 reportStartInstrumentationFailure(watcher, className, 14344 "Unable to find instrumentation info for: " + className); 14345 return false; 14346 } 14347 if (ai == null) { 14348 reportStartInstrumentationFailure(watcher, className, 14349 "Unable to find instrumentation target package: " + ii.targetPackage); 14350 return false; 14351 } 14352 14353 int match = mContext.getPackageManager().checkSignatures( 14354 ii.targetPackage, ii.packageName); 14355 if (match < 0 && match != PackageManager.SIGNATURE_FIRST_NOT_SIGNED) { 14356 String msg = "Permission Denial: starting instrumentation " 14357 + className + " from pid=" 14358 + Binder.getCallingPid() 14359 + ", uid=" + Binder.getCallingPid() 14360 + " not allowed because package " + ii.packageName 14361 + " does not have a signature matching the target " 14362 + ii.targetPackage; 14363 reportStartInstrumentationFailure(watcher, className, msg); 14364 throw new SecurityException(msg); 14365 } 14366 14367 final long origId = Binder.clearCallingIdentity(); 14368 // Instrumentation can kill and relaunch even persistent processes 14369 forceStopPackageLocked(ii.targetPackage, -1, true, false, true, true, false, userId, 14370 "start instr"); 14371 ProcessRecord app = addAppLocked(ai, false, abiOverride); 14372 app.instrumentationClass = className; 14373 app.instrumentationInfo = ai; 14374 app.instrumentationProfileFile = profileFile; 14375 app.instrumentationArguments = arguments; 14376 app.instrumentationWatcher = watcher; 14377 app.instrumentationUiAutomationConnection = uiAutomationConnection; 14378 app.instrumentationResultClass = className; 14379 Binder.restoreCallingIdentity(origId); 14380 } 14381 14382 return true; 14383 } 14384 14385 /** 14386 * Report errors that occur while attempting to start Instrumentation. Always writes the 14387 * error to the logs, but if somebody is watching, send the report there too. This enables 14388 * the "am" command to report errors with more information. 14389 * 14390 * @param watcher The IInstrumentationWatcher. Null if there isn't one. 14391 * @param cn The component name of the instrumentation. 14392 * @param report The error report. 14393 */ 14394 private void reportStartInstrumentationFailure(IInstrumentationWatcher watcher, 14395 ComponentName cn, String report) { 14396 Slog.w(TAG, report); 14397 try { 14398 if (watcher != null) { 14399 Bundle results = new Bundle(); 14400 results.putString(Instrumentation.REPORT_KEY_IDENTIFIER, "ActivityManagerService"); 14401 results.putString("Error", report); 14402 watcher.instrumentationStatus(cn, -1, results); 14403 } 14404 } catch (RemoteException e) { 14405 Slog.w(TAG, e); 14406 } 14407 } 14408 14409 void finishInstrumentationLocked(ProcessRecord app, int resultCode, Bundle results) { 14410 if (app.instrumentationWatcher != null) { 14411 try { 14412 // NOTE: IInstrumentationWatcher *must* be oneway here 14413 app.instrumentationWatcher.instrumentationFinished( 14414 app.instrumentationClass, 14415 resultCode, 14416 results); 14417 } catch (RemoteException e) { 14418 } 14419 } 14420 if (app.instrumentationUiAutomationConnection != null) { 14421 try { 14422 app.instrumentationUiAutomationConnection.shutdown(); 14423 } catch (RemoteException re) { 14424 /* ignore */ 14425 } 14426 // Only a UiAutomation can set this flag and now that 14427 // it is finished we make sure it is reset to its default. 14428 mUserIsMonkey = false; 14429 } 14430 app.instrumentationWatcher = null; 14431 app.instrumentationUiAutomationConnection = null; 14432 app.instrumentationClass = null; 14433 app.instrumentationInfo = null; 14434 app.instrumentationProfileFile = null; 14435 app.instrumentationArguments = null; 14436 14437 forceStopPackageLocked(app.info.packageName, -1, false, false, true, true, false, app.userId, 14438 "finished inst"); 14439 } 14440 14441 public void finishInstrumentation(IApplicationThread target, 14442 int resultCode, Bundle results) { 14443 int userId = UserHandle.getCallingUserId(); 14444 // Refuse possible leaked file descriptors 14445 if (results != null && results.hasFileDescriptors()) { 14446 throw new IllegalArgumentException("File descriptors passed in Intent"); 14447 } 14448 14449 synchronized(this) { 14450 ProcessRecord app = getRecordForAppLocked(target); 14451 if (app == null) { 14452 Slog.w(TAG, "finishInstrumentation: no app for " + target); 14453 return; 14454 } 14455 final long origId = Binder.clearCallingIdentity(); 14456 finishInstrumentationLocked(app, resultCode, results); 14457 Binder.restoreCallingIdentity(origId); 14458 } 14459 } 14460 14461 // ========================================================= 14462 // CONFIGURATION 14463 // ========================================================= 14464 14465 public ConfigurationInfo getDeviceConfigurationInfo() { 14466 ConfigurationInfo config = new ConfigurationInfo(); 14467 synchronized (this) { 14468 config.reqTouchScreen = mConfiguration.touchscreen; 14469 config.reqKeyboardType = mConfiguration.keyboard; 14470 config.reqNavigation = mConfiguration.navigation; 14471 if (mConfiguration.navigation == Configuration.NAVIGATION_DPAD 14472 || mConfiguration.navigation == Configuration.NAVIGATION_TRACKBALL) { 14473 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_FIVE_WAY_NAV; 14474 } 14475 if (mConfiguration.keyboard != Configuration.KEYBOARD_UNDEFINED 14476 && mConfiguration.keyboard != Configuration.KEYBOARD_NOKEYS) { 14477 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_HARD_KEYBOARD; 14478 } 14479 config.reqGlEsVersion = GL_ES_VERSION; 14480 } 14481 return config; 14482 } 14483 14484 ActivityStack getFocusedStack() { 14485 return mStackSupervisor.getFocusedStack(); 14486 } 14487 14488 public Configuration getConfiguration() { 14489 Configuration ci; 14490 synchronized(this) { 14491 ci = new Configuration(mConfiguration); 14492 } 14493 return ci; 14494 } 14495 14496 public void updatePersistentConfiguration(Configuration values) { 14497 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 14498 "updateConfiguration()"); 14499 enforceCallingPermission(android.Manifest.permission.WRITE_SETTINGS, 14500 "updateConfiguration()"); 14501 if (values == null) { 14502 throw new NullPointerException("Configuration must not be null"); 14503 } 14504 14505 synchronized(this) { 14506 final long origId = Binder.clearCallingIdentity(); 14507 updateConfigurationLocked(values, null, true, false); 14508 Binder.restoreCallingIdentity(origId); 14509 } 14510 } 14511 14512 public void updateConfiguration(Configuration values) { 14513 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 14514 "updateConfiguration()"); 14515 14516 synchronized(this) { 14517 if (values == null && mWindowManager != null) { 14518 // sentinel: fetch the current configuration from the window manager 14519 values = mWindowManager.computeNewConfiguration(); 14520 } 14521 14522 if (mWindowManager != null) { 14523 mProcessList.applyDisplaySize(mWindowManager); 14524 } 14525 14526 final long origId = Binder.clearCallingIdentity(); 14527 if (values != null) { 14528 Settings.System.clearConfiguration(values); 14529 } 14530 updateConfigurationLocked(values, null, false, false); 14531 Binder.restoreCallingIdentity(origId); 14532 } 14533 } 14534 14535 /** 14536 * Do either or both things: (1) change the current configuration, and (2) 14537 * make sure the given activity is running with the (now) current 14538 * configuration. Returns true if the activity has been left running, or 14539 * false if <var>starting</var> is being destroyed to match the new 14540 * configuration. 14541 * @param persistent TODO 14542 */ 14543 boolean updateConfigurationLocked(Configuration values, 14544 ActivityRecord starting, boolean persistent, boolean initLocale) { 14545 int changes = 0; 14546 14547 if (values != null) { 14548 Configuration newConfig = new Configuration(mConfiguration); 14549 changes = newConfig.updateFrom(values); 14550 if (changes != 0) { 14551 if (DEBUG_SWITCH || DEBUG_CONFIGURATION) { 14552 Slog.i(TAG, "Updating configuration to: " + values); 14553 } 14554 14555 EventLog.writeEvent(EventLogTags.CONFIGURATION_CHANGED, changes); 14556 14557 if (values.locale != null && !initLocale) { 14558 saveLocaleLocked(values.locale, 14559 !values.locale.equals(mConfiguration.locale), 14560 values.userSetLocale); 14561 } 14562 14563 mConfigurationSeq++; 14564 if (mConfigurationSeq <= 0) { 14565 mConfigurationSeq = 1; 14566 } 14567 newConfig.seq = mConfigurationSeq; 14568 mConfiguration = newConfig; 14569 Slog.i(TAG, "Config changes=" + Integer.toHexString(changes) + " " + newConfig); 14570 mUsageStatsService.noteStartConfig(newConfig); 14571 14572 final Configuration configCopy = new Configuration(mConfiguration); 14573 14574 // TODO: If our config changes, should we auto dismiss any currently 14575 // showing dialogs? 14576 mShowDialogs = shouldShowDialogs(newConfig); 14577 14578 AttributeCache ac = AttributeCache.instance(); 14579 if (ac != null) { 14580 ac.updateConfiguration(configCopy); 14581 } 14582 14583 // Make sure all resources in our process are updated 14584 // right now, so that anyone who is going to retrieve 14585 // resource values after we return will be sure to get 14586 // the new ones. This is especially important during 14587 // boot, where the first config change needs to guarantee 14588 // all resources have that config before following boot 14589 // code is executed. 14590 mSystemThread.applyConfigurationToResources(configCopy); 14591 14592 if (persistent && Settings.System.hasInterestingConfigurationChanges(changes)) { 14593 Message msg = mHandler.obtainMessage(UPDATE_CONFIGURATION_MSG); 14594 msg.obj = new Configuration(configCopy); 14595 mHandler.sendMessage(msg); 14596 } 14597 14598 for (int i=mLruProcesses.size()-1; i>=0; i--) { 14599 ProcessRecord app = mLruProcesses.get(i); 14600 try { 14601 if (app.thread != null) { 14602 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Sending to proc " 14603 + app.processName + " new config " + mConfiguration); 14604 app.thread.scheduleConfigurationChanged(configCopy); 14605 } 14606 } catch (Exception e) { 14607 } 14608 } 14609 Intent intent = new Intent(Intent.ACTION_CONFIGURATION_CHANGED); 14610 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 14611 | Intent.FLAG_RECEIVER_REPLACE_PENDING 14612 | Intent.FLAG_RECEIVER_FOREGROUND); 14613 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, 14614 null, AppOpsManager.OP_NONE, false, false, MY_PID, 14615 Process.SYSTEM_UID, UserHandle.USER_ALL); 14616 if ((changes&ActivityInfo.CONFIG_LOCALE) != 0) { 14617 intent = new Intent(Intent.ACTION_LOCALE_CHANGED); 14618 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 14619 broadcastIntentLocked(null, null, intent, 14620 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 14621 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 14622 } 14623 } 14624 } 14625 14626 boolean kept = true; 14627 final ActivityStack mainStack = mStackSupervisor.getFocusedStack(); 14628 // mainStack is null during startup. 14629 if (mainStack != null) { 14630 if (changes != 0 && starting == null) { 14631 // If the configuration changed, and the caller is not already 14632 // in the process of starting an activity, then find the top 14633 // activity to check if its configuration needs to change. 14634 starting = mainStack.topRunningActivityLocked(null); 14635 } 14636 14637 if (starting != null) { 14638 kept = mainStack.ensureActivityConfigurationLocked(starting, changes); 14639 // And we need to make sure at this point that all other activities 14640 // are made visible with the correct configuration. 14641 mStackSupervisor.ensureActivitiesVisibleLocked(starting, changes); 14642 } 14643 } 14644 14645 if (values != null && mWindowManager != null) { 14646 mWindowManager.setNewConfiguration(mConfiguration); 14647 } 14648 14649 return kept; 14650 } 14651 14652 /** 14653 * Decide based on the configuration whether we should shouw the ANR, 14654 * crash, etc dialogs. The idea is that if there is no affordnace to 14655 * press the on-screen buttons, we shouldn't show the dialog. 14656 * 14657 * A thought: SystemUI might also want to get told about this, the Power 14658 * dialog / global actions also might want different behaviors. 14659 */ 14660 private static final boolean shouldShowDialogs(Configuration config) { 14661 return !(config.keyboard == Configuration.KEYBOARD_NOKEYS 14662 && config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH); 14663 } 14664 14665 /** 14666 * Save the locale. You must be inside a synchronized (this) block. 14667 */ 14668 private void saveLocaleLocked(Locale l, boolean isDiff, boolean isPersist) { 14669 if(isDiff) { 14670 SystemProperties.set("user.language", l.getLanguage()); 14671 SystemProperties.set("user.region", l.getCountry()); 14672 } 14673 14674 if(isPersist) { 14675 SystemProperties.set("persist.sys.language", l.getLanguage()); 14676 SystemProperties.set("persist.sys.country", l.getCountry()); 14677 SystemProperties.set("persist.sys.localevar", l.getVariant()); 14678 } 14679 } 14680 14681 @Override 14682 public boolean targetTaskAffinityMatchesActivity(IBinder token, String destAffinity) { 14683 ActivityRecord srec = ActivityRecord.forToken(token); 14684 return srec != null && srec.task.affinity != null && 14685 srec.task.affinity.equals(destAffinity); 14686 } 14687 14688 public boolean navigateUpTo(IBinder token, Intent destIntent, int resultCode, 14689 Intent resultData) { 14690 14691 synchronized (this) { 14692 final ActivityStack stack = ActivityRecord.getStackLocked(token); 14693 if (stack != null) { 14694 return stack.navigateUpToLocked(token, destIntent, resultCode, resultData); 14695 } 14696 return false; 14697 } 14698 } 14699 14700 public int getLaunchedFromUid(IBinder activityToken) { 14701 ActivityRecord srec = ActivityRecord.forToken(activityToken); 14702 if (srec == null) { 14703 return -1; 14704 } 14705 return srec.launchedFromUid; 14706 } 14707 14708 public String getLaunchedFromPackage(IBinder activityToken) { 14709 ActivityRecord srec = ActivityRecord.forToken(activityToken); 14710 if (srec == null) { 14711 return null; 14712 } 14713 return srec.launchedFromPackage; 14714 } 14715 14716 // ========================================================= 14717 // LIFETIME MANAGEMENT 14718 // ========================================================= 14719 14720 // Returns which broadcast queue the app is the current [or imminent] receiver 14721 // on, or 'null' if the app is not an active broadcast recipient. 14722 private BroadcastQueue isReceivingBroadcast(ProcessRecord app) { 14723 BroadcastRecord r = app.curReceiver; 14724 if (r != null) { 14725 return r.queue; 14726 } 14727 14728 // It's not the current receiver, but it might be starting up to become one 14729 synchronized (this) { 14730 for (BroadcastQueue queue : mBroadcastQueues) { 14731 r = queue.mPendingBroadcast; 14732 if (r != null && r.curApp == app) { 14733 // found it; report which queue it's in 14734 return queue; 14735 } 14736 } 14737 } 14738 14739 return null; 14740 } 14741 14742 private final int computeOomAdjLocked(ProcessRecord app, int cachedAdj, ProcessRecord TOP_APP, 14743 boolean doingAll, long now) { 14744 if (mAdjSeq == app.adjSeq) { 14745 // This adjustment has already been computed. 14746 return app.curRawAdj; 14747 } 14748 14749 if (app.thread == null) { 14750 app.adjSeq = mAdjSeq; 14751 app.curSchedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 14752 app.curProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 14753 return (app.curAdj=app.curRawAdj=ProcessList.CACHED_APP_MAX_ADJ); 14754 } 14755 14756 app.adjTypeCode = ActivityManager.RunningAppProcessInfo.REASON_UNKNOWN; 14757 app.adjSource = null; 14758 app.adjTarget = null; 14759 app.empty = false; 14760 app.cached = false; 14761 14762 final int activitiesSize = app.activities.size(); 14763 14764 if (app.maxAdj <= ProcessList.FOREGROUND_APP_ADJ) { 14765 // The max adjustment doesn't allow this app to be anything 14766 // below foreground, so it is not worth doing work for it. 14767 app.adjType = "fixed"; 14768 app.adjSeq = mAdjSeq; 14769 app.curRawAdj = app.maxAdj; 14770 app.foregroundActivities = false; 14771 app.keeping = true; 14772 app.curSchedGroup = Process.THREAD_GROUP_DEFAULT; 14773 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT; 14774 // System processes can do UI, and when they do we want to have 14775 // them trim their memory after the user leaves the UI. To 14776 // facilitate this, here we need to determine whether or not it 14777 // is currently showing UI. 14778 app.systemNoUi = true; 14779 if (app == TOP_APP) { 14780 app.systemNoUi = false; 14781 } else if (activitiesSize > 0) { 14782 for (int j = 0; j < activitiesSize; j++) { 14783 final ActivityRecord r = app.activities.get(j); 14784 if (r.visible) { 14785 app.systemNoUi = false; 14786 } 14787 } 14788 } 14789 if (!app.systemNoUi) { 14790 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT_UI; 14791 } 14792 return (app.curAdj=app.maxAdj); 14793 } 14794 14795 app.keeping = false; 14796 app.systemNoUi = false; 14797 14798 // Determine the importance of the process, starting with most 14799 // important to least, and assign an appropriate OOM adjustment. 14800 int adj; 14801 int schedGroup; 14802 int procState; 14803 boolean foregroundActivities = false; 14804 boolean interesting = false; 14805 BroadcastQueue queue; 14806 if (app == TOP_APP) { 14807 // The last app on the list is the foreground app. 14808 adj = ProcessList.FOREGROUND_APP_ADJ; 14809 schedGroup = Process.THREAD_GROUP_DEFAULT; 14810 app.adjType = "top-activity"; 14811 foregroundActivities = true; 14812 interesting = true; 14813 procState = ActivityManager.PROCESS_STATE_TOP; 14814 } else if (app.instrumentationClass != null) { 14815 // Don't want to kill running instrumentation. 14816 adj = ProcessList.FOREGROUND_APP_ADJ; 14817 schedGroup = Process.THREAD_GROUP_DEFAULT; 14818 app.adjType = "instrumentation"; 14819 interesting = true; 14820 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 14821 } else if ((queue = isReceivingBroadcast(app)) != null) { 14822 // An app that is currently receiving a broadcast also 14823 // counts as being in the foreground for OOM killer purposes. 14824 // It's placed in a sched group based on the nature of the 14825 // broadcast as reflected by which queue it's active in. 14826 adj = ProcessList.FOREGROUND_APP_ADJ; 14827 schedGroup = (queue == mFgBroadcastQueue) 14828 ? Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 14829 app.adjType = "broadcast"; 14830 procState = ActivityManager.PROCESS_STATE_RECEIVER; 14831 } else if (app.executingServices.size() > 0) { 14832 // An app that is currently executing a service callback also 14833 // counts as being in the foreground. 14834 adj = ProcessList.FOREGROUND_APP_ADJ; 14835 schedGroup = app.execServicesFg ? 14836 Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 14837 app.adjType = "exec-service"; 14838 procState = ActivityManager.PROCESS_STATE_SERVICE; 14839 //Slog.i(TAG, "EXEC " + (app.execServicesFg ? "FG" : "BG") + ": " + app); 14840 } else { 14841 // As far as we know the process is empty. We may change our mind later. 14842 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 14843 // At this point we don't actually know the adjustment. Use the cached adj 14844 // value that the caller wants us to. 14845 adj = cachedAdj; 14846 procState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 14847 app.cached = true; 14848 app.empty = true; 14849 app.adjType = "cch-empty"; 14850 } 14851 14852 // Examine all activities if not already foreground. 14853 if (!foregroundActivities && activitiesSize > 0) { 14854 for (int j = 0; j < activitiesSize; j++) { 14855 final ActivityRecord r = app.activities.get(j); 14856 if (r.app != app) { 14857 Slog.w(TAG, "Wtf, activity " + r + " in proc activity list not using proc " 14858 + app + "?!?"); 14859 continue; 14860 } 14861 if (r.visible) { 14862 // App has a visible activity; only upgrade adjustment. 14863 if (adj > ProcessList.VISIBLE_APP_ADJ) { 14864 adj = ProcessList.VISIBLE_APP_ADJ; 14865 app.adjType = "visible"; 14866 } 14867 if (procState > ActivityManager.PROCESS_STATE_TOP) { 14868 procState = ActivityManager.PROCESS_STATE_TOP; 14869 } 14870 schedGroup = Process.THREAD_GROUP_DEFAULT; 14871 app.cached = false; 14872 app.empty = false; 14873 foregroundActivities = true; 14874 break; 14875 } else if (r.state == ActivityState.PAUSING || r.state == ActivityState.PAUSED) { 14876 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 14877 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 14878 app.adjType = "pausing"; 14879 } 14880 if (procState > ActivityManager.PROCESS_STATE_TOP) { 14881 procState = ActivityManager.PROCESS_STATE_TOP; 14882 } 14883 schedGroup = Process.THREAD_GROUP_DEFAULT; 14884 app.cached = false; 14885 app.empty = false; 14886 foregroundActivities = true; 14887 } else if (r.state == ActivityState.STOPPING) { 14888 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 14889 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 14890 app.adjType = "stopping"; 14891 } 14892 // For the process state, we will at this point consider the 14893 // process to be cached. It will be cached either as an activity 14894 // or empty depending on whether the activity is finishing. We do 14895 // this so that we can treat the process as cached for purposes of 14896 // memory trimming (determing current memory level, trim command to 14897 // send to process) since there can be an arbitrary number of stopping 14898 // processes and they should soon all go into the cached state. 14899 if (!r.finishing) { 14900 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 14901 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 14902 } 14903 } 14904 app.cached = false; 14905 app.empty = false; 14906 foregroundActivities = true; 14907 } else { 14908 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 14909 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 14910 app.adjType = "cch-act"; 14911 } 14912 } 14913 } 14914 } 14915 14916 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 14917 if (app.foregroundServices) { 14918 // The user is aware of this app, so make it visible. 14919 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 14920 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 14921 app.cached = false; 14922 app.adjType = "fg-service"; 14923 schedGroup = Process.THREAD_GROUP_DEFAULT; 14924 } else if (app.forcingToForeground != null) { 14925 // The user is aware of this app, so make it visible. 14926 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 14927 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 14928 app.cached = false; 14929 app.adjType = "force-fg"; 14930 app.adjSource = app.forcingToForeground; 14931 schedGroup = Process.THREAD_GROUP_DEFAULT; 14932 } 14933 } 14934 14935 if (app.foregroundServices) { 14936 interesting = true; 14937 } 14938 14939 if (app == mHeavyWeightProcess) { 14940 if (adj > ProcessList.HEAVY_WEIGHT_APP_ADJ) { 14941 // We don't want to kill the current heavy-weight process. 14942 adj = ProcessList.HEAVY_WEIGHT_APP_ADJ; 14943 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 14944 app.cached = false; 14945 app.adjType = "heavy"; 14946 } 14947 if (procState > ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 14948 procState = ActivityManager.PROCESS_STATE_HEAVY_WEIGHT; 14949 } 14950 } 14951 14952 if (app == mHomeProcess) { 14953 if (adj > ProcessList.HOME_APP_ADJ) { 14954 // This process is hosting what we currently consider to be the 14955 // home app, so we don't want to let it go into the background. 14956 adj = ProcessList.HOME_APP_ADJ; 14957 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 14958 app.cached = false; 14959 app.adjType = "home"; 14960 } 14961 if (procState > ActivityManager.PROCESS_STATE_HOME) { 14962 procState = ActivityManager.PROCESS_STATE_HOME; 14963 } 14964 } 14965 14966 if (app == mPreviousProcess && app.activities.size() > 0) { 14967 if (adj > ProcessList.PREVIOUS_APP_ADJ) { 14968 // This was the previous process that showed UI to the user. 14969 // We want to try to keep it around more aggressively, to give 14970 // a good experience around switching between two apps. 14971 adj = ProcessList.PREVIOUS_APP_ADJ; 14972 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 14973 app.cached = false; 14974 app.adjType = "previous"; 14975 } 14976 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 14977 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 14978 } 14979 } 14980 14981 if (false) Slog.i(TAG, "OOM " + app + ": initial adj=" + adj 14982 + " reason=" + app.adjType); 14983 14984 // By default, we use the computed adjustment. It may be changed if 14985 // there are applications dependent on our services or providers, but 14986 // this gives us a baseline and makes sure we don't get into an 14987 // infinite recursion. 14988 app.adjSeq = mAdjSeq; 14989 app.curRawAdj = adj; 14990 app.hasStartedServices = false; 14991 14992 if (mBackupTarget != null && app == mBackupTarget.app) { 14993 // If possible we want to avoid killing apps while they're being backed up 14994 if (adj > ProcessList.BACKUP_APP_ADJ) { 14995 if (DEBUG_BACKUP) Slog.v(TAG, "oom BACKUP_APP_ADJ for " + app); 14996 adj = ProcessList.BACKUP_APP_ADJ; 14997 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 14998 procState = ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 14999 } 15000 app.adjType = "backup"; 15001 app.cached = false; 15002 } 15003 if (procState > ActivityManager.PROCESS_STATE_BACKUP) { 15004 procState = ActivityManager.PROCESS_STATE_BACKUP; 15005 } 15006 } 15007 15008 boolean mayBeTop = false; 15009 15010 for (int is = app.services.size()-1; 15011 is >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15012 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15013 || procState > ActivityManager.PROCESS_STATE_TOP); 15014 is--) { 15015 ServiceRecord s = app.services.valueAt(is); 15016 if (s.startRequested) { 15017 app.hasStartedServices = true; 15018 if (procState > ActivityManager.PROCESS_STATE_SERVICE) { 15019 procState = ActivityManager.PROCESS_STATE_SERVICE; 15020 } 15021 if (app.hasShownUi && app != mHomeProcess) { 15022 // If this process has shown some UI, let it immediately 15023 // go to the LRU list because it may be pretty heavy with 15024 // UI stuff. We'll tag it with a label just to help 15025 // debug and understand what is going on. 15026 if (adj > ProcessList.SERVICE_ADJ) { 15027 app.adjType = "cch-started-ui-services"; 15028 } 15029 } else { 15030 if (now < (s.lastActivity + ActiveServices.MAX_SERVICE_INACTIVITY)) { 15031 // This service has seen some activity within 15032 // recent memory, so we will keep its process ahead 15033 // of the background processes. 15034 if (adj > ProcessList.SERVICE_ADJ) { 15035 adj = ProcessList.SERVICE_ADJ; 15036 app.adjType = "started-services"; 15037 app.cached = false; 15038 } 15039 } 15040 // If we have let the service slide into the background 15041 // state, still have some text describing what it is doing 15042 // even though the service no longer has an impact. 15043 if (adj > ProcessList.SERVICE_ADJ) { 15044 app.adjType = "cch-started-services"; 15045 } 15046 } 15047 // Don't kill this process because it is doing work; it 15048 // has said it is doing work. 15049 app.keeping = true; 15050 } 15051 for (int conni = s.connections.size()-1; 15052 conni >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15053 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15054 || procState > ActivityManager.PROCESS_STATE_TOP); 15055 conni--) { 15056 ArrayList<ConnectionRecord> clist = s.connections.valueAt(conni); 15057 for (int i = 0; 15058 i < clist.size() && (adj > ProcessList.FOREGROUND_APP_ADJ 15059 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15060 || procState > ActivityManager.PROCESS_STATE_TOP); 15061 i++) { 15062 // XXX should compute this based on the max of 15063 // all connected clients. 15064 ConnectionRecord cr = clist.get(i); 15065 if (cr.binding.client == app) { 15066 // Binding to ourself is not interesting. 15067 continue; 15068 } 15069 if ((cr.flags&Context.BIND_WAIVE_PRIORITY) == 0) { 15070 ProcessRecord client = cr.binding.client; 15071 int clientAdj = computeOomAdjLocked(client, cachedAdj, 15072 TOP_APP, doingAll, now); 15073 int clientProcState = client.curProcState; 15074 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15075 // If the other app is cached for any reason, for purposes here 15076 // we are going to consider it empty. The specific cached state 15077 // doesn't propagate except under certain conditions. 15078 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15079 } 15080 String adjType = null; 15081 if ((cr.flags&Context.BIND_ALLOW_OOM_MANAGEMENT) != 0) { 15082 // Not doing bind OOM management, so treat 15083 // this guy more like a started service. 15084 if (app.hasShownUi && app != mHomeProcess) { 15085 // If this process has shown some UI, let it immediately 15086 // go to the LRU list because it may be pretty heavy with 15087 // UI stuff. We'll tag it with a label just to help 15088 // debug and understand what is going on. 15089 if (adj > clientAdj) { 15090 adjType = "cch-bound-ui-services"; 15091 } 15092 app.cached = false; 15093 clientAdj = adj; 15094 clientProcState = procState; 15095 } else { 15096 if (now >= (s.lastActivity 15097 + ActiveServices.MAX_SERVICE_INACTIVITY)) { 15098 // This service has not seen activity within 15099 // recent memory, so allow it to drop to the 15100 // LRU list if there is no other reason to keep 15101 // it around. We'll also tag it with a label just 15102 // to help debug and undertand what is going on. 15103 if (adj > clientAdj) { 15104 adjType = "cch-bound-services"; 15105 } 15106 clientAdj = adj; 15107 } 15108 } 15109 } 15110 if (adj > clientAdj) { 15111 // If this process has recently shown UI, and 15112 // the process that is binding to it is less 15113 // important than being visible, then we don't 15114 // care about the binding as much as we care 15115 // about letting this process get into the LRU 15116 // list to be killed and restarted if needed for 15117 // memory. 15118 if (app.hasShownUi && app != mHomeProcess 15119 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15120 adjType = "cch-bound-ui-services"; 15121 } else { 15122 if ((cr.flags&(Context.BIND_ABOVE_CLIENT 15123 |Context.BIND_IMPORTANT)) != 0) { 15124 adj = clientAdj; 15125 } else if ((cr.flags&Context.BIND_NOT_VISIBLE) != 0 15126 && clientAdj < ProcessList.PERCEPTIBLE_APP_ADJ 15127 && adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15128 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15129 } else if (clientAdj > ProcessList.VISIBLE_APP_ADJ) { 15130 adj = clientAdj; 15131 } else { 15132 if (adj > ProcessList.VISIBLE_APP_ADJ) { 15133 adj = ProcessList.VISIBLE_APP_ADJ; 15134 } 15135 } 15136 if (!client.cached) { 15137 app.cached = false; 15138 } 15139 if (client.keeping) { 15140 app.keeping = true; 15141 } 15142 adjType = "service"; 15143 } 15144 } 15145 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 15146 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 15147 schedGroup = Process.THREAD_GROUP_DEFAULT; 15148 } 15149 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 15150 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 15151 // Special handling of clients who are in the top state. 15152 // We *may* want to consider this process to be in the 15153 // top state as well, but only if there is not another 15154 // reason for it to be running. Being on the top is a 15155 // special state, meaning you are specifically running 15156 // for the current top app. If the process is already 15157 // running in the background for some other reason, it 15158 // is more important to continue considering it to be 15159 // in the background state. 15160 mayBeTop = true; 15161 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15162 } else { 15163 // Special handling for above-top states (persistent 15164 // processes). These should not bring the current process 15165 // into the top state, since they are not on top. Instead 15166 // give them the best state after that. 15167 clientProcState = 15168 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15169 } 15170 } 15171 } else { 15172 if (clientProcState < 15173 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 15174 clientProcState = 15175 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 15176 } 15177 } 15178 if (procState > clientProcState) { 15179 procState = clientProcState; 15180 } 15181 if (procState < ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 15182 && (cr.flags&Context.BIND_SHOWING_UI) != 0) { 15183 app.pendingUiClean = true; 15184 } 15185 if (adjType != null) { 15186 app.adjType = adjType; 15187 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15188 .REASON_SERVICE_IN_USE; 15189 app.adjSource = cr.binding.client; 15190 app.adjSourceOom = clientAdj; 15191 app.adjTarget = s.name; 15192 } 15193 } 15194 if ((cr.flags&Context.BIND_TREAT_LIKE_ACTIVITY) != 0) { 15195 app.treatLikeActivity = true; 15196 } 15197 final ActivityRecord a = cr.activity; 15198 if ((cr.flags&Context.BIND_ADJUST_WITH_ACTIVITY) != 0) { 15199 if (a != null && adj > ProcessList.FOREGROUND_APP_ADJ && 15200 (a.visible || a.state == ActivityState.RESUMED 15201 || a.state == ActivityState.PAUSING)) { 15202 adj = ProcessList.FOREGROUND_APP_ADJ; 15203 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 15204 schedGroup = Process.THREAD_GROUP_DEFAULT; 15205 } 15206 app.cached = false; 15207 app.adjType = "service"; 15208 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15209 .REASON_SERVICE_IN_USE; 15210 app.adjSource = a; 15211 app.adjSourceOom = adj; 15212 app.adjTarget = s.name; 15213 } 15214 } 15215 } 15216 } 15217 } 15218 15219 for (int provi = app.pubProviders.size()-1; 15220 provi >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15221 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15222 || procState > ActivityManager.PROCESS_STATE_TOP); 15223 provi--) { 15224 ContentProviderRecord cpr = app.pubProviders.valueAt(provi); 15225 for (int i = cpr.connections.size()-1; 15226 i >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15227 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15228 || procState > ActivityManager.PROCESS_STATE_TOP); 15229 i--) { 15230 ContentProviderConnection conn = cpr.connections.get(i); 15231 ProcessRecord client = conn.client; 15232 if (client == app) { 15233 // Being our own client is not interesting. 15234 continue; 15235 } 15236 int clientAdj = computeOomAdjLocked(client, cachedAdj, TOP_APP, doingAll, now); 15237 int clientProcState = client.curProcState; 15238 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15239 // If the other app is cached for any reason, for purposes here 15240 // we are going to consider it empty. 15241 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15242 } 15243 if (adj > clientAdj) { 15244 if (app.hasShownUi && app != mHomeProcess 15245 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15246 app.adjType = "cch-ui-provider"; 15247 } else { 15248 adj = clientAdj > ProcessList.FOREGROUND_APP_ADJ 15249 ? clientAdj : ProcessList.FOREGROUND_APP_ADJ; 15250 app.adjType = "provider"; 15251 } 15252 app.cached &= client.cached; 15253 app.keeping |= client.keeping; 15254 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15255 .REASON_PROVIDER_IN_USE; 15256 app.adjSource = client; 15257 app.adjSourceOom = clientAdj; 15258 app.adjTarget = cpr.name; 15259 } 15260 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 15261 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 15262 // Special handling of clients who are in the top state. 15263 // We *may* want to consider this process to be in the 15264 // top state as well, but only if there is not another 15265 // reason for it to be running. Being on the top is a 15266 // special state, meaning you are specifically running 15267 // for the current top app. If the process is already 15268 // running in the background for some other reason, it 15269 // is more important to continue considering it to be 15270 // in the background state. 15271 mayBeTop = true; 15272 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15273 } else { 15274 // Special handling for above-top states (persistent 15275 // processes). These should not bring the current process 15276 // into the top state, since they are not on top. Instead 15277 // give them the best state after that. 15278 clientProcState = 15279 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15280 } 15281 } 15282 if (procState > clientProcState) { 15283 procState = clientProcState; 15284 } 15285 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 15286 schedGroup = Process.THREAD_GROUP_DEFAULT; 15287 } 15288 } 15289 // If the provider has external (non-framework) process 15290 // dependencies, ensure that its adjustment is at least 15291 // FOREGROUND_APP_ADJ. 15292 if (cpr.hasExternalProcessHandles()) { 15293 if (adj > ProcessList.FOREGROUND_APP_ADJ) { 15294 adj = ProcessList.FOREGROUND_APP_ADJ; 15295 schedGroup = Process.THREAD_GROUP_DEFAULT; 15296 app.cached = false; 15297 app.keeping = true; 15298 app.adjType = "provider"; 15299 app.adjTarget = cpr.name; 15300 } 15301 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) { 15302 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15303 } 15304 } 15305 } 15306 15307 if (mayBeTop && procState > ActivityManager.PROCESS_STATE_TOP) { 15308 // A client of one of our services or providers is in the top state. We 15309 // *may* want to be in the top state, but not if we are already running in 15310 // the background for some other reason. For the decision here, we are going 15311 // to pick out a few specific states that we want to remain in when a client 15312 // is top (states that tend to be longer-term) and otherwise allow it to go 15313 // to the top state. 15314 switch (procState) { 15315 case ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND: 15316 case ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND: 15317 case ActivityManager.PROCESS_STATE_SERVICE: 15318 // These all are longer-term states, so pull them up to the top 15319 // of the background states, but not all the way to the top state. 15320 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15321 break; 15322 default: 15323 // Otherwise, top is a better choice, so take it. 15324 procState = ActivityManager.PROCESS_STATE_TOP; 15325 break; 15326 } 15327 } 15328 15329 if (procState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 15330 if (app.hasClientActivities) { 15331 // This is a cached process, but with client activities. Mark it so. 15332 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT; 15333 app.adjType = "cch-client-act"; 15334 } else if (app.treatLikeActivity) { 15335 // This is a cached process, but somebody wants us to treat it like it has 15336 // an activity, okay! 15337 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 15338 app.adjType = "cch-as-act"; 15339 } 15340 } 15341 15342 if (adj == ProcessList.SERVICE_ADJ) { 15343 if (doingAll) { 15344 app.serviceb = mNewNumAServiceProcs > (mNumServiceProcs/3); 15345 mNewNumServiceProcs++; 15346 //Slog.i(TAG, "ADJ " + app + " serviceb=" + app.serviceb); 15347 if (!app.serviceb) { 15348 // This service isn't far enough down on the LRU list to 15349 // normally be a B service, but if we are low on RAM and it 15350 // is large we want to force it down since we would prefer to 15351 // keep launcher over it. 15352 if (mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 15353 && app.lastPss >= mProcessList.getCachedRestoreThresholdKb()) { 15354 app.serviceHighRam = true; 15355 app.serviceb = true; 15356 //Slog.i(TAG, "ADJ " + app + " high ram!"); 15357 } else { 15358 mNewNumAServiceProcs++; 15359 //Slog.i(TAG, "ADJ " + app + " not high ram!"); 15360 } 15361 } else { 15362 app.serviceHighRam = false; 15363 } 15364 } 15365 if (app.serviceb) { 15366 adj = ProcessList.SERVICE_B_ADJ; 15367 } 15368 } 15369 15370 app.curRawAdj = adj; 15371 15372 //Slog.i(TAG, "OOM ADJ " + app + ": pid=" + app.pid + 15373 // " adj=" + adj + " curAdj=" + app.curAdj + " maxAdj=" + app.maxAdj); 15374 if (adj > app.maxAdj) { 15375 adj = app.maxAdj; 15376 if (app.maxAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 15377 schedGroup = Process.THREAD_GROUP_DEFAULT; 15378 } 15379 } 15380 if (adj < ProcessList.CACHED_APP_MIN_ADJ) { 15381 app.keeping = true; 15382 } 15383 15384 // Do final modification to adj. Everything we do between here and applying 15385 // the final setAdj must be done in this function, because we will also use 15386 // it when computing the final cached adj later. Note that we don't need to 15387 // worry about this for max adj above, since max adj will always be used to 15388 // keep it out of the cached vaues. 15389 app.curAdj = app.modifyRawOomAdj(adj); 15390 app.curSchedGroup = schedGroup; 15391 app.curProcState = procState; 15392 app.foregroundActivities = foregroundActivities; 15393 15394 return app.curRawAdj; 15395 } 15396 15397 /** 15398 * Schedule PSS collection of a process. 15399 */ 15400 void requestPssLocked(ProcessRecord proc, int procState) { 15401 if (mPendingPssProcesses.contains(proc)) { 15402 return; 15403 } 15404 if (mPendingPssProcesses.size() == 0) { 15405 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 15406 } 15407 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of: " + proc); 15408 proc.pssProcState = procState; 15409 mPendingPssProcesses.add(proc); 15410 } 15411 15412 /** 15413 * Schedule PSS collection of all processes. 15414 */ 15415 void requestPssAllProcsLocked(long now, boolean always, boolean memLowered) { 15416 if (!always) { 15417 if (now < (mLastFullPssTime + 15418 (memLowered ? FULL_PSS_LOWERED_INTERVAL : FULL_PSS_MIN_INTERVAL))) { 15419 return; 15420 } 15421 } 15422 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of all procs! memLowered=" + memLowered); 15423 mLastFullPssTime = now; 15424 mPendingPssProcesses.ensureCapacity(mLruProcesses.size()); 15425 mPendingPssProcesses.clear(); 15426 for (int i=mLruProcesses.size()-1; i>=0; i--) { 15427 ProcessRecord app = mLruProcesses.get(i); 15428 if (memLowered || now > (app.lastStateTime+ProcessList.PSS_ALL_INTERVAL)) { 15429 app.pssProcState = app.setProcState; 15430 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 15431 isSleeping(), now); 15432 mPendingPssProcesses.add(app); 15433 } 15434 } 15435 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 15436 } 15437 15438 /** 15439 * Ask a given process to GC right now. 15440 */ 15441 final void performAppGcLocked(ProcessRecord app) { 15442 try { 15443 app.lastRequestedGc = SystemClock.uptimeMillis(); 15444 if (app.thread != null) { 15445 if (app.reportLowMemory) { 15446 app.reportLowMemory = false; 15447 app.thread.scheduleLowMemory(); 15448 } else { 15449 app.thread.processInBackground(); 15450 } 15451 } 15452 } catch (Exception e) { 15453 // whatever. 15454 } 15455 } 15456 15457 /** 15458 * Returns true if things are idle enough to perform GCs. 15459 */ 15460 private final boolean canGcNowLocked() { 15461 boolean processingBroadcasts = false; 15462 for (BroadcastQueue q : mBroadcastQueues) { 15463 if (q.mParallelBroadcasts.size() != 0 || q.mOrderedBroadcasts.size() != 0) { 15464 processingBroadcasts = true; 15465 } 15466 } 15467 return !processingBroadcasts 15468 && (isSleeping() || mStackSupervisor.allResumedActivitiesIdle()); 15469 } 15470 15471 /** 15472 * Perform GCs on all processes that are waiting for it, but only 15473 * if things are idle. 15474 */ 15475 final void performAppGcsLocked() { 15476 final int N = mProcessesToGc.size(); 15477 if (N <= 0) { 15478 return; 15479 } 15480 if (canGcNowLocked()) { 15481 while (mProcessesToGc.size() > 0) { 15482 ProcessRecord proc = mProcessesToGc.remove(0); 15483 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ || proc.reportLowMemory) { 15484 if ((proc.lastRequestedGc+GC_MIN_INTERVAL) 15485 <= SystemClock.uptimeMillis()) { 15486 // To avoid spamming the system, we will GC processes one 15487 // at a time, waiting a few seconds between each. 15488 performAppGcLocked(proc); 15489 scheduleAppGcsLocked(); 15490 return; 15491 } else { 15492 // It hasn't been long enough since we last GCed this 15493 // process... put it in the list to wait for its time. 15494 addProcessToGcListLocked(proc); 15495 break; 15496 } 15497 } 15498 } 15499 15500 scheduleAppGcsLocked(); 15501 } 15502 } 15503 15504 /** 15505 * If all looks good, perform GCs on all processes waiting for them. 15506 */ 15507 final void performAppGcsIfAppropriateLocked() { 15508 if (canGcNowLocked()) { 15509 performAppGcsLocked(); 15510 return; 15511 } 15512 // Still not idle, wait some more. 15513 scheduleAppGcsLocked(); 15514 } 15515 15516 /** 15517 * Schedule the execution of all pending app GCs. 15518 */ 15519 final void scheduleAppGcsLocked() { 15520 mHandler.removeMessages(GC_BACKGROUND_PROCESSES_MSG); 15521 15522 if (mProcessesToGc.size() > 0) { 15523 // Schedule a GC for the time to the next process. 15524 ProcessRecord proc = mProcessesToGc.get(0); 15525 Message msg = mHandler.obtainMessage(GC_BACKGROUND_PROCESSES_MSG); 15526 15527 long when = proc.lastRequestedGc + GC_MIN_INTERVAL; 15528 long now = SystemClock.uptimeMillis(); 15529 if (when < (now+GC_TIMEOUT)) { 15530 when = now + GC_TIMEOUT; 15531 } 15532 mHandler.sendMessageAtTime(msg, when); 15533 } 15534 } 15535 15536 /** 15537 * Add a process to the array of processes waiting to be GCed. Keeps the 15538 * list in sorted order by the last GC time. The process can't already be 15539 * on the list. 15540 */ 15541 final void addProcessToGcListLocked(ProcessRecord proc) { 15542 boolean added = false; 15543 for (int i=mProcessesToGc.size()-1; i>=0; i--) { 15544 if (mProcessesToGc.get(i).lastRequestedGc < 15545 proc.lastRequestedGc) { 15546 added = true; 15547 mProcessesToGc.add(i+1, proc); 15548 break; 15549 } 15550 } 15551 if (!added) { 15552 mProcessesToGc.add(0, proc); 15553 } 15554 } 15555 15556 /** 15557 * Set up to ask a process to GC itself. This will either do it 15558 * immediately, or put it on the list of processes to gc the next 15559 * time things are idle. 15560 */ 15561 final void scheduleAppGcLocked(ProcessRecord app) { 15562 long now = SystemClock.uptimeMillis(); 15563 if ((app.lastRequestedGc+GC_MIN_INTERVAL) > now) { 15564 return; 15565 } 15566 if (!mProcessesToGc.contains(app)) { 15567 addProcessToGcListLocked(app); 15568 scheduleAppGcsLocked(); 15569 } 15570 } 15571 15572 final void checkExcessivePowerUsageLocked(boolean doKills) { 15573 updateCpuStatsNow(); 15574 15575 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 15576 boolean doWakeKills = doKills; 15577 boolean doCpuKills = doKills; 15578 if (mLastPowerCheckRealtime == 0) { 15579 doWakeKills = false; 15580 } 15581 if (mLastPowerCheckUptime == 0) { 15582 doCpuKills = false; 15583 } 15584 if (stats.isScreenOn()) { 15585 doWakeKills = false; 15586 } 15587 final long curRealtime = SystemClock.elapsedRealtime(); 15588 final long realtimeSince = curRealtime - mLastPowerCheckRealtime; 15589 final long curUptime = SystemClock.uptimeMillis(); 15590 final long uptimeSince = curUptime - mLastPowerCheckUptime; 15591 mLastPowerCheckRealtime = curRealtime; 15592 mLastPowerCheckUptime = curUptime; 15593 if (realtimeSince < WAKE_LOCK_MIN_CHECK_DURATION) { 15594 doWakeKills = false; 15595 } 15596 if (uptimeSince < CPU_MIN_CHECK_DURATION) { 15597 doCpuKills = false; 15598 } 15599 int i = mLruProcesses.size(); 15600 while (i > 0) { 15601 i--; 15602 ProcessRecord app = mLruProcesses.get(i); 15603 if (!app.keeping) { 15604 long wtime; 15605 synchronized (stats) { 15606 wtime = stats.getProcessWakeTime(app.info.uid, 15607 app.pid, curRealtime); 15608 } 15609 long wtimeUsed = wtime - app.lastWakeTime; 15610 long cputimeUsed = app.curCpuTime - app.lastCpuTime; 15611 if (DEBUG_POWER) { 15612 StringBuilder sb = new StringBuilder(128); 15613 sb.append("Wake for "); 15614 app.toShortString(sb); 15615 sb.append(": over "); 15616 TimeUtils.formatDuration(realtimeSince, sb); 15617 sb.append(" used "); 15618 TimeUtils.formatDuration(wtimeUsed, sb); 15619 sb.append(" ("); 15620 sb.append((wtimeUsed*100)/realtimeSince); 15621 sb.append("%)"); 15622 Slog.i(TAG, sb.toString()); 15623 sb.setLength(0); 15624 sb.append("CPU for "); 15625 app.toShortString(sb); 15626 sb.append(": over "); 15627 TimeUtils.formatDuration(uptimeSince, sb); 15628 sb.append(" used "); 15629 TimeUtils.formatDuration(cputimeUsed, sb); 15630 sb.append(" ("); 15631 sb.append((cputimeUsed*100)/uptimeSince); 15632 sb.append("%)"); 15633 Slog.i(TAG, sb.toString()); 15634 } 15635 // If a process has held a wake lock for more 15636 // than 50% of the time during this period, 15637 // that sounds bad. Kill! 15638 if (doWakeKills && realtimeSince > 0 15639 && ((wtimeUsed*100)/realtimeSince) >= 50) { 15640 synchronized (stats) { 15641 stats.reportExcessiveWakeLocked(app.info.uid, app.processName, 15642 realtimeSince, wtimeUsed); 15643 } 15644 killUnneededProcessLocked(app, "excessive wake held " + wtimeUsed 15645 + " during " + realtimeSince); 15646 app.baseProcessTracker.reportExcessiveWake(app.pkgList); 15647 } else if (doCpuKills && uptimeSince > 0 15648 && ((cputimeUsed*100)/uptimeSince) >= 50) { 15649 synchronized (stats) { 15650 stats.reportExcessiveCpuLocked(app.info.uid, app.processName, 15651 uptimeSince, cputimeUsed); 15652 } 15653 killUnneededProcessLocked(app, "excessive cpu " + cputimeUsed 15654 + " during " + uptimeSince); 15655 app.baseProcessTracker.reportExcessiveCpu(app.pkgList); 15656 } else { 15657 app.lastWakeTime = wtime; 15658 app.lastCpuTime = app.curCpuTime; 15659 } 15660 } 15661 } 15662 } 15663 15664 private final boolean applyOomAdjLocked(ProcessRecord app, boolean wasKeeping, 15665 ProcessRecord TOP_APP, boolean doingAll, long now) { 15666 boolean success = true; 15667 15668 if (app.curRawAdj != app.setRawAdj) { 15669 if (wasKeeping && !app.keeping) { 15670 // This app is no longer something we want to keep. Note 15671 // its current wake lock time to later know to kill it if 15672 // it is not behaving well. 15673 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 15674 synchronized (stats) { 15675 app.lastWakeTime = stats.getProcessWakeTime(app.info.uid, 15676 app.pid, SystemClock.elapsedRealtime()); 15677 } 15678 app.lastCpuTime = app.curCpuTime; 15679 } 15680 15681 app.setRawAdj = app.curRawAdj; 15682 } 15683 15684 int changes = 0; 15685 15686 if (app.curAdj != app.setAdj) { 15687 ProcessList.setOomAdj(app.pid, app.curAdj); 15688 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v( 15689 TAG, "Set " + app.pid + " " + app.processName + 15690 " adj " + app.curAdj + ": " + app.adjType); 15691 app.setAdj = app.curAdj; 15692 } 15693 15694 if (app.setSchedGroup != app.curSchedGroup) { 15695 app.setSchedGroup = app.curSchedGroup; 15696 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 15697 "Setting process group of " + app.processName 15698 + " to " + app.curSchedGroup); 15699 if (app.waitingToKill != null && 15700 app.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 15701 killUnneededProcessLocked(app, app.waitingToKill); 15702 success = false; 15703 } else { 15704 if (true) { 15705 long oldId = Binder.clearCallingIdentity(); 15706 try { 15707 Process.setProcessGroup(app.pid, app.curSchedGroup); 15708 } catch (Exception e) { 15709 Slog.w(TAG, "Failed setting process group of " + app.pid 15710 + " to " + app.curSchedGroup); 15711 e.printStackTrace(); 15712 } finally { 15713 Binder.restoreCallingIdentity(oldId); 15714 } 15715 } else { 15716 if (app.thread != null) { 15717 try { 15718 app.thread.setSchedulingGroup(app.curSchedGroup); 15719 } catch (RemoteException e) { 15720 } 15721 } 15722 } 15723 Process.setSwappiness(app.pid, 15724 app.curSchedGroup <= Process.THREAD_GROUP_BG_NONINTERACTIVE); 15725 } 15726 } 15727 if (app.repForegroundActivities != app.foregroundActivities) { 15728 app.repForegroundActivities = app.foregroundActivities; 15729 changes |= ProcessChangeItem.CHANGE_ACTIVITIES; 15730 } 15731 if (app.repProcState != app.curProcState) { 15732 app.repProcState = app.curProcState; 15733 changes |= ProcessChangeItem.CHANGE_PROCESS_STATE; 15734 if (app.thread != null) { 15735 try { 15736 if (false) { 15737 //RuntimeException h = new RuntimeException("here"); 15738 Slog.i(TAG, "Sending new process state " + app.repProcState 15739 + " to " + app /*, h*/); 15740 } 15741 app.thread.setProcessState(app.repProcState); 15742 } catch (RemoteException e) { 15743 } 15744 } 15745 } 15746 if (app.setProcState < 0 || ProcessList.procStatesDifferForMem(app.curProcState, 15747 app.setProcState)) { 15748 app.lastStateTime = now; 15749 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 15750 isSleeping(), now); 15751 if (DEBUG_PSS) Slog.d(TAG, "Process state change from " 15752 + ProcessList.makeProcStateString(app.setProcState) + " to " 15753 + ProcessList.makeProcStateString(app.curProcState) + " next pss in " 15754 + (app.nextPssTime-now) + ": " + app); 15755 } else { 15756 if (now > app.nextPssTime || (now > (app.lastPssTime+ProcessList.PSS_MAX_INTERVAL) 15757 && now > (app.lastStateTime+ProcessList.PSS_MIN_TIME_FROM_STATE_CHANGE))) { 15758 requestPssLocked(app, app.setProcState); 15759 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, false, 15760 isSleeping(), now); 15761 } else if (false && DEBUG_PSS) { 15762 Slog.d(TAG, "Not requesting PSS of " + app + ": next=" + (app.nextPssTime-now)); 15763 } 15764 } 15765 if (app.setProcState != app.curProcState) { 15766 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 15767 "Proc state change of " + app.processName 15768 + " to " + app.curProcState); 15769 app.setProcState = app.curProcState; 15770 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 15771 app.notCachedSinceIdle = false; 15772 } 15773 if (!doingAll) { 15774 setProcessTrackerState(app, mProcessStats.getMemFactorLocked(), now); 15775 } else { 15776 app.procStateChanged = true; 15777 } 15778 } 15779 15780 if (changes != 0) { 15781 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Changes in " + app + ": " + changes); 15782 int i = mPendingProcessChanges.size()-1; 15783 ProcessChangeItem item = null; 15784 while (i >= 0) { 15785 item = mPendingProcessChanges.get(i); 15786 if (item.pid == app.pid) { 15787 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Re-using existing item: " + item); 15788 break; 15789 } 15790 i--; 15791 } 15792 if (i < 0) { 15793 // No existing item in pending changes; need a new one. 15794 final int NA = mAvailProcessChanges.size(); 15795 if (NA > 0) { 15796 item = mAvailProcessChanges.remove(NA-1); 15797 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Retreiving available item: " + item); 15798 } else { 15799 item = new ProcessChangeItem(); 15800 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Allocating new item: " + item); 15801 } 15802 item.changes = 0; 15803 item.pid = app.pid; 15804 item.uid = app.info.uid; 15805 if (mPendingProcessChanges.size() == 0) { 15806 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, 15807 "*** Enqueueing dispatch processes changed!"); 15808 mHandler.obtainMessage(DISPATCH_PROCESSES_CHANGED).sendToTarget(); 15809 } 15810 mPendingProcessChanges.add(item); 15811 } 15812 item.changes |= changes; 15813 item.processState = app.repProcState; 15814 item.foregroundActivities = app.repForegroundActivities; 15815 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Item " 15816 + Integer.toHexString(System.identityHashCode(item)) 15817 + " " + app.toShortString() + ": changes=" + item.changes 15818 + " procState=" + item.processState 15819 + " foreground=" + item.foregroundActivities 15820 + " type=" + app.adjType + " source=" + app.adjSource 15821 + " target=" + app.adjTarget); 15822 } 15823 15824 return success; 15825 } 15826 15827 private final void setProcessTrackerState(ProcessRecord proc, int memFactor, long now) { 15828 if (proc.thread != null && proc.baseProcessTracker != null) { 15829 proc.baseProcessTracker.setState(proc.repProcState, memFactor, now, proc.pkgList); 15830 } 15831 } 15832 15833 private final boolean updateOomAdjLocked(ProcessRecord app, int cachedAdj, 15834 ProcessRecord TOP_APP, boolean doingAll, long now) { 15835 if (app.thread == null) { 15836 return false; 15837 } 15838 15839 final boolean wasKeeping = app.keeping; 15840 15841 computeOomAdjLocked(app, cachedAdj, TOP_APP, doingAll, now); 15842 15843 return applyOomAdjLocked(app, wasKeeping, TOP_APP, doingAll, now); 15844 } 15845 15846 final void updateProcessForegroundLocked(ProcessRecord proc, boolean isForeground, 15847 boolean oomAdj) { 15848 if (isForeground != proc.foregroundServices) { 15849 proc.foregroundServices = isForeground; 15850 ArrayList<ProcessRecord> curProcs = mForegroundPackages.get(proc.info.packageName, 15851 proc.info.uid); 15852 if (isForeground) { 15853 if (curProcs == null) { 15854 curProcs = new ArrayList<ProcessRecord>(); 15855 mForegroundPackages.put(proc.info.packageName, proc.info.uid, curProcs); 15856 } 15857 if (!curProcs.contains(proc)) { 15858 curProcs.add(proc); 15859 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_FOREGROUND_START, 15860 proc.info.packageName, proc.info.uid); 15861 } 15862 } else { 15863 if (curProcs != null) { 15864 if (curProcs.remove(proc)) { 15865 mBatteryStatsService.noteEvent( 15866 BatteryStats.HistoryItem.EVENT_FOREGROUND_FINISH, 15867 proc.info.packageName, proc.info.uid); 15868 if (curProcs.size() <= 0) { 15869 mForegroundPackages.remove(proc.info.packageName, proc.info.uid); 15870 } 15871 } 15872 } 15873 } 15874 if (oomAdj) { 15875 updateOomAdjLocked(); 15876 } 15877 } 15878 } 15879 15880 private final ActivityRecord resumedAppLocked() { 15881 ActivityRecord act = mStackSupervisor.resumedAppLocked(); 15882 String pkg; 15883 int uid; 15884 if (act != null && !act.sleeping) { 15885 pkg = act.packageName; 15886 uid = act.info.applicationInfo.uid; 15887 } else { 15888 pkg = null; 15889 uid = -1; 15890 } 15891 // Has the UID or resumed package name changed? 15892 if (uid != mCurResumedUid || (pkg != mCurResumedPackage 15893 && (pkg == null || !pkg.equals(mCurResumedPackage)))) { 15894 if (mCurResumedPackage != null) { 15895 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_FINISH, 15896 mCurResumedPackage, mCurResumedUid); 15897 } 15898 mCurResumedPackage = pkg; 15899 mCurResumedUid = uid; 15900 if (mCurResumedPackage != null) { 15901 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_START, 15902 mCurResumedPackage, mCurResumedUid); 15903 } 15904 } 15905 return act; 15906 } 15907 15908 final boolean updateOomAdjLocked(ProcessRecord app) { 15909 final ActivityRecord TOP_ACT = resumedAppLocked(); 15910 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 15911 final boolean wasCached = app.cached; 15912 15913 mAdjSeq++; 15914 15915 // This is the desired cached adjusment we want to tell it to use. 15916 // If our app is currently cached, we know it, and that is it. Otherwise, 15917 // we don't know it yet, and it needs to now be cached we will then 15918 // need to do a complete oom adj. 15919 final int cachedAdj = app.curRawAdj >= ProcessList.CACHED_APP_MIN_ADJ 15920 ? app.curRawAdj : ProcessList.UNKNOWN_ADJ; 15921 boolean success = updateOomAdjLocked(app, cachedAdj, TOP_APP, false, 15922 SystemClock.uptimeMillis()); 15923 if (wasCached != app.cached || app.curRawAdj == ProcessList.UNKNOWN_ADJ) { 15924 // Changed to/from cached state, so apps after it in the LRU 15925 // list may also be changed. 15926 updateOomAdjLocked(); 15927 } 15928 return success; 15929 } 15930 15931 final void updateOomAdjLocked() { 15932 final ActivityRecord TOP_ACT = resumedAppLocked(); 15933 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 15934 final long now = SystemClock.uptimeMillis(); 15935 final long oldTime = now - ProcessList.MAX_EMPTY_TIME; 15936 final int N = mLruProcesses.size(); 15937 15938 if (false) { 15939 RuntimeException e = new RuntimeException(); 15940 e.fillInStackTrace(); 15941 Slog.i(TAG, "updateOomAdj: top=" + TOP_ACT, e); 15942 } 15943 15944 mAdjSeq++; 15945 mNewNumServiceProcs = 0; 15946 mNewNumAServiceProcs = 0; 15947 15948 final int emptyProcessLimit; 15949 final int cachedProcessLimit; 15950 if (mProcessLimit <= 0) { 15951 emptyProcessLimit = cachedProcessLimit = 0; 15952 } else if (mProcessLimit == 1) { 15953 emptyProcessLimit = 1; 15954 cachedProcessLimit = 0; 15955 } else { 15956 emptyProcessLimit = ProcessList.computeEmptyProcessLimit(mProcessLimit); 15957 cachedProcessLimit = mProcessLimit - emptyProcessLimit; 15958 } 15959 15960 // Let's determine how many processes we have running vs. 15961 // how many slots we have for background processes; we may want 15962 // to put multiple processes in a slot of there are enough of 15963 // them. 15964 int numSlots = (ProcessList.CACHED_APP_MAX_ADJ 15965 - ProcessList.CACHED_APP_MIN_ADJ + 1) / 2; 15966 int numEmptyProcs = N - mNumNonCachedProcs - mNumCachedHiddenProcs; 15967 if (numEmptyProcs > cachedProcessLimit) { 15968 // If there are more empty processes than our limit on cached 15969 // processes, then use the cached process limit for the factor. 15970 // This ensures that the really old empty processes get pushed 15971 // down to the bottom, so if we are running low on memory we will 15972 // have a better chance at keeping around more cached processes 15973 // instead of a gazillion empty processes. 15974 numEmptyProcs = cachedProcessLimit; 15975 } 15976 int emptyFactor = numEmptyProcs/numSlots; 15977 if (emptyFactor < 1) emptyFactor = 1; 15978 int cachedFactor = (mNumCachedHiddenProcs > 0 ? mNumCachedHiddenProcs : 1)/numSlots; 15979 if (cachedFactor < 1) cachedFactor = 1; 15980 int stepCached = 0; 15981 int stepEmpty = 0; 15982 int numCached = 0; 15983 int numEmpty = 0; 15984 int numTrimming = 0; 15985 15986 mNumNonCachedProcs = 0; 15987 mNumCachedHiddenProcs = 0; 15988 15989 // First update the OOM adjustment for each of the 15990 // application processes based on their current state. 15991 int curCachedAdj = ProcessList.CACHED_APP_MIN_ADJ; 15992 int nextCachedAdj = curCachedAdj+1; 15993 int curEmptyAdj = ProcessList.CACHED_APP_MIN_ADJ; 15994 int nextEmptyAdj = curEmptyAdj+2; 15995 for (int i=N-1; i>=0; i--) { 15996 ProcessRecord app = mLruProcesses.get(i); 15997 if (!app.killedByAm && app.thread != null) { 15998 app.procStateChanged = false; 15999 final boolean wasKeeping = app.keeping; 16000 computeOomAdjLocked(app, ProcessList.UNKNOWN_ADJ, TOP_APP, true, now); 16001 16002 // If we haven't yet assigned the final cached adj 16003 // to the process, do that now. 16004 if (app.curAdj >= ProcessList.UNKNOWN_ADJ) { 16005 switch (app.curProcState) { 16006 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 16007 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 16008 // This process is a cached process holding activities... 16009 // assign it the next cached value for that type, and then 16010 // step that cached level. 16011 app.curRawAdj = curCachedAdj; 16012 app.curAdj = app.modifyRawOomAdj(curCachedAdj); 16013 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning activity LRU #" + i 16014 + " adj: " + app.curAdj + " (curCachedAdj=" + curCachedAdj 16015 + ")"); 16016 if (curCachedAdj != nextCachedAdj) { 16017 stepCached++; 16018 if (stepCached >= cachedFactor) { 16019 stepCached = 0; 16020 curCachedAdj = nextCachedAdj; 16021 nextCachedAdj += 2; 16022 if (nextCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) { 16023 nextCachedAdj = ProcessList.CACHED_APP_MAX_ADJ; 16024 } 16025 } 16026 } 16027 break; 16028 default: 16029 // For everything else, assign next empty cached process 16030 // level and bump that up. Note that this means that 16031 // long-running services that have dropped down to the 16032 // cached level will be treated as empty (since their process 16033 // state is still as a service), which is what we want. 16034 app.curRawAdj = curEmptyAdj; 16035 app.curAdj = app.modifyRawOomAdj(curEmptyAdj); 16036 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning empty LRU #" + i 16037 + " adj: " + app.curAdj + " (curEmptyAdj=" + curEmptyAdj 16038 + ")"); 16039 if (curEmptyAdj != nextEmptyAdj) { 16040 stepEmpty++; 16041 if (stepEmpty >= emptyFactor) { 16042 stepEmpty = 0; 16043 curEmptyAdj = nextEmptyAdj; 16044 nextEmptyAdj += 2; 16045 if (nextEmptyAdj > ProcessList.CACHED_APP_MAX_ADJ) { 16046 nextEmptyAdj = ProcessList.CACHED_APP_MAX_ADJ; 16047 } 16048 } 16049 } 16050 break; 16051 } 16052 } 16053 16054 applyOomAdjLocked(app, wasKeeping, TOP_APP, true, now); 16055 16056 // Count the number of process types. 16057 switch (app.curProcState) { 16058 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 16059 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 16060 mNumCachedHiddenProcs++; 16061 numCached++; 16062 if (numCached > cachedProcessLimit) { 16063 killUnneededProcessLocked(app, "cached #" + numCached); 16064 } 16065 break; 16066 case ActivityManager.PROCESS_STATE_CACHED_EMPTY: 16067 if (numEmpty > ProcessList.TRIM_EMPTY_APPS 16068 && app.lastActivityTime < oldTime) { 16069 killUnneededProcessLocked(app, "empty for " 16070 + ((oldTime + ProcessList.MAX_EMPTY_TIME - app.lastActivityTime) 16071 / 1000) + "s"); 16072 } else { 16073 numEmpty++; 16074 if (numEmpty > emptyProcessLimit) { 16075 killUnneededProcessLocked(app, "empty #" + numEmpty); 16076 } 16077 } 16078 break; 16079 default: 16080 mNumNonCachedProcs++; 16081 break; 16082 } 16083 16084 if (app.isolated && app.services.size() <= 0) { 16085 // If this is an isolated process, and there are no 16086 // services running in it, then the process is no longer 16087 // needed. We agressively kill these because we can by 16088 // definition not re-use the same process again, and it is 16089 // good to avoid having whatever code was running in them 16090 // left sitting around after no longer needed. 16091 killUnneededProcessLocked(app, "isolated not needed"); 16092 } 16093 16094 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 16095 && !app.killedByAm) { 16096 numTrimming++; 16097 } 16098 } 16099 } 16100 16101 mNumServiceProcs = mNewNumServiceProcs; 16102 16103 // Now determine the memory trimming level of background processes. 16104 // Unfortunately we need to start at the back of the list to do this 16105 // properly. We only do this if the number of background apps we 16106 // are managing to keep around is less than half the maximum we desire; 16107 // if we are keeping a good number around, we'll let them use whatever 16108 // memory they want. 16109 final int numCachedAndEmpty = numCached + numEmpty; 16110 int memFactor; 16111 if (numCached <= ProcessList.TRIM_CACHED_APPS 16112 && numEmpty <= ProcessList.TRIM_EMPTY_APPS) { 16113 if (numCachedAndEmpty <= ProcessList.TRIM_CRITICAL_THRESHOLD) { 16114 memFactor = ProcessStats.ADJ_MEM_FACTOR_CRITICAL; 16115 } else if (numCachedAndEmpty <= ProcessList.TRIM_LOW_THRESHOLD) { 16116 memFactor = ProcessStats.ADJ_MEM_FACTOR_LOW; 16117 } else { 16118 memFactor = ProcessStats.ADJ_MEM_FACTOR_MODERATE; 16119 } 16120 } else { 16121 memFactor = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 16122 } 16123 // We always allow the memory level to go up (better). We only allow it to go 16124 // down if we are in a state where that is allowed, *and* the total number of processes 16125 // has gone down since last time. 16126 if (DEBUG_OOM_ADJ) Slog.d(TAG, "oom: memFactor=" + memFactor + " last=" + mLastMemoryLevel 16127 + " allowLow=" + mAllowLowerMemLevel + " numProcs=" + mLruProcesses.size() 16128 + " last=" + mLastNumProcesses); 16129 if (memFactor > mLastMemoryLevel) { 16130 if (!mAllowLowerMemLevel || mLruProcesses.size() >= mLastNumProcesses) { 16131 memFactor = mLastMemoryLevel; 16132 if (DEBUG_OOM_ADJ) Slog.d(TAG, "Keeping last mem factor!"); 16133 } 16134 } 16135 mLastMemoryLevel = memFactor; 16136 mLastNumProcesses = mLruProcesses.size(); 16137 boolean allChanged = mProcessStats.setMemFactorLocked(memFactor, !isSleeping(), now); 16138 final int trackerMemFactor = mProcessStats.getMemFactorLocked(); 16139 if (memFactor != ProcessStats.ADJ_MEM_FACTOR_NORMAL) { 16140 if (mLowRamStartTime == 0) { 16141 mLowRamStartTime = now; 16142 } 16143 int step = 0; 16144 int fgTrimLevel; 16145 switch (memFactor) { 16146 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 16147 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_CRITICAL; 16148 break; 16149 case ProcessStats.ADJ_MEM_FACTOR_LOW: 16150 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_LOW; 16151 break; 16152 default: 16153 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_MODERATE; 16154 break; 16155 } 16156 int factor = numTrimming/3; 16157 int minFactor = 2; 16158 if (mHomeProcess != null) minFactor++; 16159 if (mPreviousProcess != null) minFactor++; 16160 if (factor < minFactor) factor = minFactor; 16161 int curLevel = ComponentCallbacks2.TRIM_MEMORY_COMPLETE; 16162 for (int i=N-1; i>=0; i--) { 16163 ProcessRecord app = mLruProcesses.get(i); 16164 if (allChanged || app.procStateChanged) { 16165 setProcessTrackerState(app, trackerMemFactor, now); 16166 app.procStateChanged = false; 16167 } 16168 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 16169 && !app.killedByAm) { 16170 if (app.trimMemoryLevel < curLevel && app.thread != null) { 16171 try { 16172 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16173 "Trimming memory of " + app.processName 16174 + " to " + curLevel); 16175 app.thread.scheduleTrimMemory(curLevel); 16176 } catch (RemoteException e) { 16177 } 16178 if (false) { 16179 // For now we won't do this; our memory trimming seems 16180 // to be good enough at this point that destroying 16181 // activities causes more harm than good. 16182 if (curLevel >= ComponentCallbacks2.TRIM_MEMORY_COMPLETE 16183 && app != mHomeProcess && app != mPreviousProcess) { 16184 // Need to do this on its own message because the stack may not 16185 // be in a consistent state at this point. 16186 // For these apps we will also finish their activities 16187 // to help them free memory. 16188 mStackSupervisor.scheduleDestroyAllActivities(app, "trim"); 16189 } 16190 } 16191 } 16192 app.trimMemoryLevel = curLevel; 16193 step++; 16194 if (step >= factor) { 16195 step = 0; 16196 switch (curLevel) { 16197 case ComponentCallbacks2.TRIM_MEMORY_COMPLETE: 16198 curLevel = ComponentCallbacks2.TRIM_MEMORY_MODERATE; 16199 break; 16200 case ComponentCallbacks2.TRIM_MEMORY_MODERATE: 16201 curLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 16202 break; 16203 } 16204 } 16205 } else if (app.curProcState == ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 16206 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_BACKGROUND 16207 && app.thread != null) { 16208 try { 16209 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16210 "Trimming memory of heavy-weight " + app.processName 16211 + " to " + ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 16212 app.thread.scheduleTrimMemory( 16213 ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 16214 } catch (RemoteException e) { 16215 } 16216 } 16217 app.trimMemoryLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 16218 } else { 16219 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 16220 || app.systemNoUi) && app.pendingUiClean) { 16221 // If this application is now in the background and it 16222 // had done UI, then give it the special trim level to 16223 // have it free UI resources. 16224 final int level = ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN; 16225 if (app.trimMemoryLevel < level && app.thread != null) { 16226 try { 16227 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16228 "Trimming memory of bg-ui " + app.processName 16229 + " to " + level); 16230 app.thread.scheduleTrimMemory(level); 16231 } catch (RemoteException e) { 16232 } 16233 } 16234 app.pendingUiClean = false; 16235 } 16236 if (app.trimMemoryLevel < fgTrimLevel && app.thread != null) { 16237 try { 16238 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16239 "Trimming memory of fg " + app.processName 16240 + " to " + fgTrimLevel); 16241 app.thread.scheduleTrimMemory(fgTrimLevel); 16242 } catch (RemoteException e) { 16243 } 16244 } 16245 app.trimMemoryLevel = fgTrimLevel; 16246 } 16247 } 16248 } else { 16249 if (mLowRamStartTime != 0) { 16250 mLowRamTimeSinceLastIdle += now - mLowRamStartTime; 16251 mLowRamStartTime = 0; 16252 } 16253 for (int i=N-1; i>=0; i--) { 16254 ProcessRecord app = mLruProcesses.get(i); 16255 if (allChanged || app.procStateChanged) { 16256 setProcessTrackerState(app, trackerMemFactor, now); 16257 app.procStateChanged = false; 16258 } 16259 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 16260 || app.systemNoUi) && app.pendingUiClean) { 16261 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN 16262 && app.thread != null) { 16263 try { 16264 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16265 "Trimming memory of ui hidden " + app.processName 16266 + " to " + ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 16267 app.thread.scheduleTrimMemory( 16268 ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 16269 } catch (RemoteException e) { 16270 } 16271 } 16272 app.pendingUiClean = false; 16273 } 16274 app.trimMemoryLevel = 0; 16275 } 16276 } 16277 16278 if (mAlwaysFinishActivities) { 16279 // Need to do this on its own message because the stack may not 16280 // be in a consistent state at this point. 16281 mStackSupervisor.scheduleDestroyAllActivities(null, "always-finish"); 16282 } 16283 16284 if (allChanged) { 16285 requestPssAllProcsLocked(now, false, mProcessStats.isMemFactorLowered()); 16286 } 16287 16288 if (mProcessStats.shouldWriteNowLocked(now)) { 16289 mHandler.post(new Runnable() { 16290 @Override public void run() { 16291 synchronized (ActivityManagerService.this) { 16292 mProcessStats.writeStateAsyncLocked(); 16293 } 16294 } 16295 }); 16296 } 16297 16298 if (DEBUG_OOM_ADJ) { 16299 Slog.d(TAG, "Did OOM ADJ in " + (SystemClock.uptimeMillis()-now) + "ms"); 16300 } 16301 } 16302 16303 final void trimApplications() { 16304 synchronized (this) { 16305 int i; 16306 16307 // First remove any unused application processes whose package 16308 // has been removed. 16309 for (i=mRemovedProcesses.size()-1; i>=0; i--) { 16310 final ProcessRecord app = mRemovedProcesses.get(i); 16311 if (app.activities.size() == 0 16312 && app.curReceiver == null && app.services.size() == 0) { 16313 Slog.i( 16314 TAG, "Exiting empty application process " 16315 + app.processName + " (" 16316 + (app.thread != null ? app.thread.asBinder() : null) 16317 + ")\n"); 16318 if (app.pid > 0 && app.pid != MY_PID) { 16319 EventLog.writeEvent(EventLogTags.AM_KILL, app.userId, app.pid, 16320 app.processName, app.setAdj, "empty"); 16321 app.killedByAm = true; 16322 Process.killProcessQuiet(app.pid); 16323 } else { 16324 try { 16325 app.thread.scheduleExit(); 16326 } catch (Exception e) { 16327 // Ignore exceptions. 16328 } 16329 } 16330 cleanUpApplicationRecordLocked(app, false, true, -1); 16331 mRemovedProcesses.remove(i); 16332 16333 if (app.persistent) { 16334 if (app.persistent) { 16335 addAppLocked(app.info, false, null /* ABI override */); 16336 } 16337 } 16338 } 16339 } 16340 16341 // Now update the oom adj for all processes. 16342 updateOomAdjLocked(); 16343 } 16344 } 16345 16346 /** This method sends the specified signal to each of the persistent apps */ 16347 public void signalPersistentProcesses(int sig) throws RemoteException { 16348 if (sig != Process.SIGNAL_USR1) { 16349 throw new SecurityException("Only SIGNAL_USR1 is allowed"); 16350 } 16351 16352 synchronized (this) { 16353 if (checkCallingPermission(android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES) 16354 != PackageManager.PERMISSION_GRANTED) { 16355 throw new SecurityException("Requires permission " 16356 + android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES); 16357 } 16358 16359 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 16360 ProcessRecord r = mLruProcesses.get(i); 16361 if (r.thread != null && r.persistent) { 16362 Process.sendSignal(r.pid, sig); 16363 } 16364 } 16365 } 16366 } 16367 16368 private void stopProfilerLocked(ProcessRecord proc, String path, int profileType) { 16369 if (proc == null || proc == mProfileProc) { 16370 proc = mProfileProc; 16371 path = mProfileFile; 16372 profileType = mProfileType; 16373 clearProfilerLocked(); 16374 } 16375 if (proc == null) { 16376 return; 16377 } 16378 try { 16379 proc.thread.profilerControl(false, path, null, profileType); 16380 } catch (RemoteException e) { 16381 throw new IllegalStateException("Process disappeared"); 16382 } 16383 } 16384 16385 private void clearProfilerLocked() { 16386 if (mProfileFd != null) { 16387 try { 16388 mProfileFd.close(); 16389 } catch (IOException e) { 16390 } 16391 } 16392 mProfileApp = null; 16393 mProfileProc = null; 16394 mProfileFile = null; 16395 mProfileType = 0; 16396 mAutoStopProfiler = false; 16397 } 16398 16399 public boolean profileControl(String process, int userId, boolean start, 16400 String path, ParcelFileDescriptor fd, int profileType) throws RemoteException { 16401 16402 try { 16403 synchronized (this) { 16404 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 16405 // its own permission. 16406 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 16407 != PackageManager.PERMISSION_GRANTED) { 16408 throw new SecurityException("Requires permission " 16409 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 16410 } 16411 16412 if (start && fd == null) { 16413 throw new IllegalArgumentException("null fd"); 16414 } 16415 16416 ProcessRecord proc = null; 16417 if (process != null) { 16418 proc = findProcessLocked(process, userId, "profileControl"); 16419 } 16420 16421 if (start && (proc == null || proc.thread == null)) { 16422 throw new IllegalArgumentException("Unknown process: " + process); 16423 } 16424 16425 if (start) { 16426 stopProfilerLocked(null, null, 0); 16427 setProfileApp(proc.info, proc.processName, path, fd, false); 16428 mProfileProc = proc; 16429 mProfileType = profileType; 16430 try { 16431 fd = fd.dup(); 16432 } catch (IOException e) { 16433 fd = null; 16434 } 16435 proc.thread.profilerControl(start, path, fd, profileType); 16436 fd = null; 16437 mProfileFd = null; 16438 } else { 16439 stopProfilerLocked(proc, path, profileType); 16440 if (fd != null) { 16441 try { 16442 fd.close(); 16443 } catch (IOException e) { 16444 } 16445 } 16446 } 16447 16448 return true; 16449 } 16450 } catch (RemoteException e) { 16451 throw new IllegalStateException("Process disappeared"); 16452 } finally { 16453 if (fd != null) { 16454 try { 16455 fd.close(); 16456 } catch (IOException e) { 16457 } 16458 } 16459 } 16460 } 16461 16462 private ProcessRecord findProcessLocked(String process, int userId, String callName) { 16463 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 16464 userId, true, true, callName, null); 16465 ProcessRecord proc = null; 16466 try { 16467 int pid = Integer.parseInt(process); 16468 synchronized (mPidsSelfLocked) { 16469 proc = mPidsSelfLocked.get(pid); 16470 } 16471 } catch (NumberFormatException e) { 16472 } 16473 16474 if (proc == null) { 16475 ArrayMap<String, SparseArray<ProcessRecord>> all 16476 = mProcessNames.getMap(); 16477 SparseArray<ProcessRecord> procs = all.get(process); 16478 if (procs != null && procs.size() > 0) { 16479 proc = procs.valueAt(0); 16480 if (userId != UserHandle.USER_ALL && proc.userId != userId) { 16481 for (int i=1; i<procs.size(); i++) { 16482 ProcessRecord thisProc = procs.valueAt(i); 16483 if (thisProc.userId == userId) { 16484 proc = thisProc; 16485 break; 16486 } 16487 } 16488 } 16489 } 16490 } 16491 16492 return proc; 16493 } 16494 16495 public boolean dumpHeap(String process, int userId, boolean managed, 16496 String path, ParcelFileDescriptor fd) throws RemoteException { 16497 16498 try { 16499 synchronized (this) { 16500 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 16501 // its own permission (same as profileControl). 16502 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 16503 != PackageManager.PERMISSION_GRANTED) { 16504 throw new SecurityException("Requires permission " 16505 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 16506 } 16507 16508 if (fd == null) { 16509 throw new IllegalArgumentException("null fd"); 16510 } 16511 16512 ProcessRecord proc = findProcessLocked(process, userId, "dumpHeap"); 16513 if (proc == null || proc.thread == null) { 16514 throw new IllegalArgumentException("Unknown process: " + process); 16515 } 16516 16517 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 16518 if (!isDebuggable) { 16519 if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 16520 throw new SecurityException("Process not debuggable: " + proc); 16521 } 16522 } 16523 16524 proc.thread.dumpHeap(managed, path, fd); 16525 fd = null; 16526 return true; 16527 } 16528 } catch (RemoteException e) { 16529 throw new IllegalStateException("Process disappeared"); 16530 } finally { 16531 if (fd != null) { 16532 try { 16533 fd.close(); 16534 } catch (IOException e) { 16535 } 16536 } 16537 } 16538 } 16539 16540 /** In this method we try to acquire our lock to make sure that we have not deadlocked */ 16541 public void monitor() { 16542 synchronized (this) { } 16543 } 16544 16545 void onCoreSettingsChange(Bundle settings) { 16546 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 16547 ProcessRecord processRecord = mLruProcesses.get(i); 16548 try { 16549 if (processRecord.thread != null) { 16550 processRecord.thread.setCoreSettings(settings); 16551 } 16552 } catch (RemoteException re) { 16553 /* ignore */ 16554 } 16555 } 16556 } 16557 16558 // Multi-user methods 16559 16560 /** 16561 * Start user, if its not already running, but don't bring it to foreground. 16562 */ 16563 @Override 16564 public boolean startUserInBackground(final int userId) { 16565 return startUser(userId, /* foreground */ false); 16566 } 16567 16568 /** 16569 * Refreshes the list of users related to the current user when either a 16570 * user switch happens or when a new related user is started in the 16571 * background. 16572 */ 16573 private void updateCurrentProfileIdsLocked() { 16574 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 16575 mCurrentUserId, false /* enabledOnly */); 16576 int[] currentProfileIds = new int[profiles.size()]; // profiles will not be null 16577 for (int i = 0; i < currentProfileIds.length; i++) { 16578 currentProfileIds[i] = profiles.get(i).id; 16579 } 16580 mCurrentProfileIds = currentProfileIds; 16581 } 16582 16583 private Set getProfileIdsLocked(int userId) { 16584 Set userIds = new HashSet<Integer>(); 16585 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 16586 userId, false /* enabledOnly */); 16587 for (UserInfo user : profiles) { 16588 userIds.add(Integer.valueOf(user.id)); 16589 } 16590 return userIds; 16591 } 16592 16593 @Override 16594 public boolean switchUser(final int userId) { 16595 return startUser(userId, /* foregound */ true); 16596 } 16597 16598 private boolean startUser(final int userId, boolean foreground) { 16599 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 16600 != PackageManager.PERMISSION_GRANTED) { 16601 String msg = "Permission Denial: switchUser() from pid=" 16602 + Binder.getCallingPid() 16603 + ", uid=" + Binder.getCallingUid() 16604 + " requires " + INTERACT_ACROSS_USERS_FULL; 16605 Slog.w(TAG, msg); 16606 throw new SecurityException(msg); 16607 } 16608 16609 if (DEBUG_MU) Slog.i(TAG_MU, "starting userid:" + userId + " fore:" + foreground); 16610 16611 final long ident = Binder.clearCallingIdentity(); 16612 try { 16613 synchronized (this) { 16614 final int oldUserId = mCurrentUserId; 16615 if (oldUserId == userId) { 16616 return true; 16617 } 16618 16619 mStackSupervisor.setLockTaskModeLocked(null); 16620 16621 final UserInfo userInfo = getUserManagerLocked().getUserInfo(userId); 16622 if (userInfo == null) { 16623 Slog.w(TAG, "No user info for user #" + userId); 16624 return false; 16625 } 16626 16627 if (foreground) { 16628 mWindowManager.startFreezingScreen(R.anim.screen_user_exit, 16629 R.anim.screen_user_enter); 16630 } 16631 16632 boolean needStart = false; 16633 16634 // If the user we are switching to is not currently started, then 16635 // we need to start it now. 16636 if (mStartedUsers.get(userId) == null) { 16637 mStartedUsers.put(userId, new UserStartedState(new UserHandle(userId), false)); 16638 updateStartedUserArrayLocked(); 16639 needStart = true; 16640 } 16641 16642 final Integer userIdInt = Integer.valueOf(userId); 16643 mUserLru.remove(userIdInt); 16644 mUserLru.add(userIdInt); 16645 16646 if (foreground) { 16647 mCurrentUserId = userId; 16648 updateCurrentProfileIdsLocked(); 16649 mWindowManager.setCurrentUser(userId, mCurrentProfileIds); 16650 // Once the internal notion of the active user has switched, we lock the device 16651 // with the option to show the user switcher on the keyguard. 16652 mWindowManager.lockNow(null); 16653 } else { 16654 final Integer currentUserIdInt = Integer.valueOf(mCurrentUserId); 16655 updateCurrentProfileIdsLocked(); 16656 mWindowManager.setCurrentProfileIds(mCurrentProfileIds); 16657 mUserLru.remove(currentUserIdInt); 16658 mUserLru.add(currentUserIdInt); 16659 } 16660 16661 final UserStartedState uss = mStartedUsers.get(userId); 16662 16663 // Make sure user is in the started state. If it is currently 16664 // stopping, we need to knock that off. 16665 if (uss.mState == UserStartedState.STATE_STOPPING) { 16666 // If we are stopping, we haven't sent ACTION_SHUTDOWN, 16667 // so we can just fairly silently bring the user back from 16668 // the almost-dead. 16669 uss.mState = UserStartedState.STATE_RUNNING; 16670 updateStartedUserArrayLocked(); 16671 needStart = true; 16672 } else if (uss.mState == UserStartedState.STATE_SHUTDOWN) { 16673 // This means ACTION_SHUTDOWN has been sent, so we will 16674 // need to treat this as a new boot of the user. 16675 uss.mState = UserStartedState.STATE_BOOTING; 16676 updateStartedUserArrayLocked(); 16677 needStart = true; 16678 } 16679 16680 if (uss.mState == UserStartedState.STATE_BOOTING) { 16681 // Booting up a new user, need to tell system services about it. 16682 // Note that this is on the same handler as scheduling of broadcasts, 16683 // which is important because it needs to go first. 16684 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_START_MSG, userId)); 16685 } 16686 16687 if (foreground) { 16688 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_CURRENT_MSG, userId)); 16689 mHandler.removeMessages(REPORT_USER_SWITCH_MSG); 16690 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 16691 mHandler.sendMessage(mHandler.obtainMessage(REPORT_USER_SWITCH_MSG, 16692 oldUserId, userId, uss)); 16693 mHandler.sendMessageDelayed(mHandler.obtainMessage(USER_SWITCH_TIMEOUT_MSG, 16694 oldUserId, userId, uss), USER_SWITCH_TIMEOUT); 16695 } 16696 16697 if (needStart) { 16698 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 16699 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 16700 | Intent.FLAG_RECEIVER_FOREGROUND); 16701 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 16702 broadcastIntentLocked(null, null, intent, 16703 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 16704 false, false, MY_PID, Process.SYSTEM_UID, userId); 16705 } 16706 16707 if ((userInfo.flags&UserInfo.FLAG_INITIALIZED) == 0) { 16708 if (userId != UserHandle.USER_OWNER) { 16709 Intent intent = new Intent(Intent.ACTION_USER_INITIALIZE); 16710 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 16711 broadcastIntentLocked(null, null, intent, null, 16712 new IIntentReceiver.Stub() { 16713 public void performReceive(Intent intent, int resultCode, 16714 String data, Bundle extras, boolean ordered, 16715 boolean sticky, int sendingUser) { 16716 userInitialized(uss, userId); 16717 } 16718 }, 0, null, null, null, AppOpsManager.OP_NONE, 16719 true, false, MY_PID, Process.SYSTEM_UID, 16720 userId); 16721 uss.initializing = true; 16722 } else { 16723 getUserManagerLocked().makeInitialized(userInfo.id); 16724 } 16725 } 16726 16727 if (foreground) { 16728 boolean homeInFront = mStackSupervisor.switchUserLocked(userId, uss); 16729 if (homeInFront) { 16730 startHomeActivityLocked(userId); 16731 } else { 16732 mStackSupervisor.resumeTopActivitiesLocked(); 16733 } 16734 EventLogTags.writeAmSwitchUser(userId); 16735 getUserManagerLocked().userForeground(userId); 16736 sendUserSwitchBroadcastsLocked(oldUserId, userId); 16737 } else { 16738 mStackSupervisor.startBackgroundUserLocked(userId, uss); 16739 } 16740 16741 if (needStart) { 16742 Intent intent = new Intent(Intent.ACTION_USER_STARTING); 16743 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 16744 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 16745 broadcastIntentLocked(null, null, intent, 16746 null, new IIntentReceiver.Stub() { 16747 @Override 16748 public void performReceive(Intent intent, int resultCode, String data, 16749 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 16750 throws RemoteException { 16751 } 16752 }, 0, null, null, 16753 android.Manifest.permission.INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 16754 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 16755 } 16756 } 16757 } finally { 16758 Binder.restoreCallingIdentity(ident); 16759 } 16760 16761 return true; 16762 } 16763 16764 void sendUserSwitchBroadcastsLocked(int oldUserId, int newUserId) { 16765 long ident = Binder.clearCallingIdentity(); 16766 try { 16767 Intent intent; 16768 if (oldUserId >= 0) { 16769 intent = new Intent(Intent.ACTION_USER_BACKGROUND); 16770 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 16771 | Intent.FLAG_RECEIVER_FOREGROUND); 16772 intent.putExtra(Intent.EXTRA_USER_HANDLE, oldUserId); 16773 broadcastIntentLocked(null, null, intent, 16774 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 16775 false, false, MY_PID, Process.SYSTEM_UID, oldUserId); 16776 } 16777 if (newUserId >= 0) { 16778 intent = new Intent(Intent.ACTION_USER_FOREGROUND); 16779 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 16780 | Intent.FLAG_RECEIVER_FOREGROUND); 16781 intent.putExtra(Intent.EXTRA_USER_HANDLE, newUserId); 16782 broadcastIntentLocked(null, null, intent, 16783 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 16784 false, false, MY_PID, Process.SYSTEM_UID, newUserId); 16785 intent = new Intent(Intent.ACTION_USER_SWITCHED); 16786 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 16787 | Intent.FLAG_RECEIVER_FOREGROUND); 16788 intent.putExtra(Intent.EXTRA_USER_HANDLE, newUserId); 16789 broadcastIntentLocked(null, null, intent, 16790 null, null, 0, null, null, 16791 android.Manifest.permission.MANAGE_USERS, AppOpsManager.OP_NONE, 16792 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 16793 } 16794 } finally { 16795 Binder.restoreCallingIdentity(ident); 16796 } 16797 } 16798 16799 void dispatchUserSwitch(final UserStartedState uss, final int oldUserId, 16800 final int newUserId) { 16801 final int N = mUserSwitchObservers.beginBroadcast(); 16802 if (N > 0) { 16803 final IRemoteCallback callback = new IRemoteCallback.Stub() { 16804 int mCount = 0; 16805 @Override 16806 public void sendResult(Bundle data) throws RemoteException { 16807 synchronized (ActivityManagerService.this) { 16808 if (mCurUserSwitchCallback == this) { 16809 mCount++; 16810 if (mCount == N) { 16811 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 16812 } 16813 } 16814 } 16815 } 16816 }; 16817 synchronized (this) { 16818 uss.switching = true; 16819 mCurUserSwitchCallback = callback; 16820 } 16821 for (int i=0; i<N; i++) { 16822 try { 16823 mUserSwitchObservers.getBroadcastItem(i).onUserSwitching( 16824 newUserId, callback); 16825 } catch (RemoteException e) { 16826 } 16827 } 16828 } else { 16829 synchronized (this) { 16830 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 16831 } 16832 } 16833 mUserSwitchObservers.finishBroadcast(); 16834 } 16835 16836 void timeoutUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 16837 synchronized (this) { 16838 Slog.w(TAG, "User switch timeout: from " + oldUserId + " to " + newUserId); 16839 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 16840 } 16841 } 16842 16843 void sendContinueUserSwitchLocked(UserStartedState uss, int oldUserId, int newUserId) { 16844 mCurUserSwitchCallback = null; 16845 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 16846 mHandler.sendMessage(mHandler.obtainMessage(CONTINUE_USER_SWITCH_MSG, 16847 oldUserId, newUserId, uss)); 16848 } 16849 16850 void userInitialized(UserStartedState uss, int newUserId) { 16851 completeSwitchAndInitalize(uss, newUserId, true, false); 16852 } 16853 16854 void continueUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 16855 completeSwitchAndInitalize(uss, newUserId, false, true); 16856 } 16857 16858 void completeSwitchAndInitalize(UserStartedState uss, int newUserId, 16859 boolean clearInitializing, boolean clearSwitching) { 16860 boolean unfrozen = false; 16861 synchronized (this) { 16862 if (clearInitializing) { 16863 uss.initializing = false; 16864 getUserManagerLocked().makeInitialized(uss.mHandle.getIdentifier()); 16865 } 16866 if (clearSwitching) { 16867 uss.switching = false; 16868 } 16869 if (!uss.switching && !uss.initializing) { 16870 mWindowManager.stopFreezingScreen(); 16871 unfrozen = true; 16872 } 16873 } 16874 if (unfrozen) { 16875 final int N = mUserSwitchObservers.beginBroadcast(); 16876 for (int i=0; i<N; i++) { 16877 try { 16878 mUserSwitchObservers.getBroadcastItem(i).onUserSwitchComplete(newUserId); 16879 } catch (RemoteException e) { 16880 } 16881 } 16882 mUserSwitchObservers.finishBroadcast(); 16883 } 16884 } 16885 16886 void scheduleStartProfilesLocked() { 16887 if (!mHandler.hasMessages(START_PROFILES_MSG)) { 16888 mHandler.sendMessageDelayed(mHandler.obtainMessage(START_PROFILES_MSG), 16889 DateUtils.SECOND_IN_MILLIS); 16890 } 16891 } 16892 16893 void startProfilesLocked() { 16894 if (DEBUG_MU) Slog.i(TAG_MU, "startProfilesLocked"); 16895 List<UserInfo> profiles = getUserManagerLocked().getProfiles( 16896 mCurrentUserId, false /* enabledOnly */); 16897 List<UserInfo> toStart = new ArrayList<UserInfo>(profiles.size()); 16898 for (UserInfo user : profiles) { 16899 if ((user.flags & UserInfo.FLAG_INITIALIZED) == UserInfo.FLAG_INITIALIZED 16900 && user.id != mCurrentUserId) { 16901 toStart.add(user); 16902 } 16903 } 16904 final int n = toStart.size(); 16905 int i = 0; 16906 for (; i < n && i < (MAX_RUNNING_USERS - 1); ++i) { 16907 startUserInBackground(toStart.get(i).id); 16908 } 16909 if (i < n) { 16910 Slog.w(TAG_MU, "More profiles than MAX_RUNNING_USERS"); 16911 } 16912 } 16913 16914 void finishUserBoot(UserStartedState uss) { 16915 synchronized (this) { 16916 if (uss.mState == UserStartedState.STATE_BOOTING 16917 && mStartedUsers.get(uss.mHandle.getIdentifier()) == uss) { 16918 uss.mState = UserStartedState.STATE_RUNNING; 16919 final int userId = uss.mHandle.getIdentifier(); 16920 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 16921 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 16922 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 16923 broadcastIntentLocked(null, null, intent, 16924 null, null, 0, null, null, 16925 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, AppOpsManager.OP_NONE, 16926 true, false, MY_PID, Process.SYSTEM_UID, userId); 16927 } 16928 } 16929 } 16930 16931 void finishUserSwitch(UserStartedState uss) { 16932 synchronized (this) { 16933 finishUserBoot(uss); 16934 16935 startProfilesLocked(); 16936 16937 int num = mUserLru.size(); 16938 int i = 0; 16939 while (num > MAX_RUNNING_USERS && i < mUserLru.size()) { 16940 Integer oldUserId = mUserLru.get(i); 16941 UserStartedState oldUss = mStartedUsers.get(oldUserId); 16942 if (oldUss == null) { 16943 // Shouldn't happen, but be sane if it does. 16944 mUserLru.remove(i); 16945 num--; 16946 continue; 16947 } 16948 if (oldUss.mState == UserStartedState.STATE_STOPPING 16949 || oldUss.mState == UserStartedState.STATE_SHUTDOWN) { 16950 // This user is already stopping, doesn't count. 16951 num--; 16952 i++; 16953 continue; 16954 } 16955 if (oldUserId == UserHandle.USER_OWNER || oldUserId == mCurrentUserId) { 16956 // Owner and current can't be stopped, but count as running. 16957 i++; 16958 continue; 16959 } 16960 // This is a user to be stopped. 16961 stopUserLocked(oldUserId, null); 16962 num--; 16963 i++; 16964 } 16965 } 16966 } 16967 16968 @Override 16969 public int stopUser(final int userId, final IStopUserCallback callback) { 16970 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 16971 != PackageManager.PERMISSION_GRANTED) { 16972 String msg = "Permission Denial: switchUser() from pid=" 16973 + Binder.getCallingPid() 16974 + ", uid=" + Binder.getCallingUid() 16975 + " requires " + INTERACT_ACROSS_USERS_FULL; 16976 Slog.w(TAG, msg); 16977 throw new SecurityException(msg); 16978 } 16979 if (userId <= 0) { 16980 throw new IllegalArgumentException("Can't stop primary user " + userId); 16981 } 16982 synchronized (this) { 16983 return stopUserLocked(userId, callback); 16984 } 16985 } 16986 16987 private int stopUserLocked(final int userId, final IStopUserCallback callback) { 16988 if (DEBUG_MU) Slog.i(TAG_MU, "stopUserLocked userId=" + userId); 16989 if (mCurrentUserId == userId) { 16990 return ActivityManager.USER_OP_IS_CURRENT; 16991 } 16992 16993 final UserStartedState uss = mStartedUsers.get(userId); 16994 if (uss == null) { 16995 // User is not started, nothing to do... but we do need to 16996 // callback if requested. 16997 if (callback != null) { 16998 mHandler.post(new Runnable() { 16999 @Override 17000 public void run() { 17001 try { 17002 callback.userStopped(userId); 17003 } catch (RemoteException e) { 17004 } 17005 } 17006 }); 17007 } 17008 return ActivityManager.USER_OP_SUCCESS; 17009 } 17010 17011 if (callback != null) { 17012 uss.mStopCallbacks.add(callback); 17013 } 17014 17015 if (uss.mState != UserStartedState.STATE_STOPPING 17016 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17017 uss.mState = UserStartedState.STATE_STOPPING; 17018 updateStartedUserArrayLocked(); 17019 17020 long ident = Binder.clearCallingIdentity(); 17021 try { 17022 // We are going to broadcast ACTION_USER_STOPPING and then 17023 // once that is done send a final ACTION_SHUTDOWN and then 17024 // stop the user. 17025 final Intent stoppingIntent = new Intent(Intent.ACTION_USER_STOPPING); 17026 stoppingIntent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 17027 stoppingIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17028 stoppingIntent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 17029 final Intent shutdownIntent = new Intent(Intent.ACTION_SHUTDOWN); 17030 // This is the result receiver for the final shutdown broadcast. 17031 final IIntentReceiver shutdownReceiver = new IIntentReceiver.Stub() { 17032 @Override 17033 public void performReceive(Intent intent, int resultCode, String data, 17034 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 17035 finishUserStop(uss); 17036 } 17037 }; 17038 // This is the result receiver for the initial stopping broadcast. 17039 final IIntentReceiver stoppingReceiver = new IIntentReceiver.Stub() { 17040 @Override 17041 public void performReceive(Intent intent, int resultCode, String data, 17042 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 17043 // On to the next. 17044 synchronized (ActivityManagerService.this) { 17045 if (uss.mState != UserStartedState.STATE_STOPPING) { 17046 // Whoops, we are being started back up. Abort, abort! 17047 return; 17048 } 17049 uss.mState = UserStartedState.STATE_SHUTDOWN; 17050 } 17051 mSystemServiceManager.stopUser(userId); 17052 broadcastIntentLocked(null, null, shutdownIntent, 17053 null, shutdownReceiver, 0, null, null, null, AppOpsManager.OP_NONE, 17054 true, false, MY_PID, Process.SYSTEM_UID, userId); 17055 } 17056 }; 17057 // Kick things off. 17058 broadcastIntentLocked(null, null, stoppingIntent, 17059 null, stoppingReceiver, 0, null, null, 17060 android.Manifest.permission.INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 17061 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 17062 } finally { 17063 Binder.restoreCallingIdentity(ident); 17064 } 17065 } 17066 17067 return ActivityManager.USER_OP_SUCCESS; 17068 } 17069 17070 void finishUserStop(UserStartedState uss) { 17071 final int userId = uss.mHandle.getIdentifier(); 17072 boolean stopped; 17073 ArrayList<IStopUserCallback> callbacks; 17074 synchronized (this) { 17075 callbacks = new ArrayList<IStopUserCallback>(uss.mStopCallbacks); 17076 if (mStartedUsers.get(userId) != uss) { 17077 stopped = false; 17078 } else if (uss.mState != UserStartedState.STATE_SHUTDOWN) { 17079 stopped = false; 17080 } else { 17081 stopped = true; 17082 // User can no longer run. 17083 mStartedUsers.remove(userId); 17084 mUserLru.remove(Integer.valueOf(userId)); 17085 updateStartedUserArrayLocked(); 17086 17087 // Clean up all state and processes associated with the user. 17088 // Kill all the processes for the user. 17089 forceStopUserLocked(userId, "finish user"); 17090 } 17091 } 17092 17093 for (int i=0; i<callbacks.size(); i++) { 17094 try { 17095 if (stopped) callbacks.get(i).userStopped(userId); 17096 else callbacks.get(i).userStopAborted(userId); 17097 } catch (RemoteException e) { 17098 } 17099 } 17100 17101 if (stopped) { 17102 mSystemServiceManager.cleanupUser(userId); 17103 synchronized (this) { 17104 mStackSupervisor.removeUserLocked(userId); 17105 } 17106 } 17107 } 17108 17109 @Override 17110 public UserInfo getCurrentUser() { 17111 if ((checkCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS) 17112 != PackageManager.PERMISSION_GRANTED) && ( 17113 checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17114 != PackageManager.PERMISSION_GRANTED)) { 17115 String msg = "Permission Denial: getCurrentUser() from pid=" 17116 + Binder.getCallingPid() 17117 + ", uid=" + Binder.getCallingUid() 17118 + " requires " + android.Manifest.permission.INTERACT_ACROSS_USERS; 17119 Slog.w(TAG, msg); 17120 throw new SecurityException(msg); 17121 } 17122 synchronized (this) { 17123 return getUserManagerLocked().getUserInfo(mCurrentUserId); 17124 } 17125 } 17126 17127 int getCurrentUserIdLocked() { 17128 return mCurrentUserId; 17129 } 17130 17131 @Override 17132 public boolean isUserRunning(int userId, boolean orStopped) { 17133 if (checkCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS) 17134 != PackageManager.PERMISSION_GRANTED) { 17135 String msg = "Permission Denial: isUserRunning() from pid=" 17136 + Binder.getCallingPid() 17137 + ", uid=" + Binder.getCallingUid() 17138 + " requires " + android.Manifest.permission.INTERACT_ACROSS_USERS; 17139 Slog.w(TAG, msg); 17140 throw new SecurityException(msg); 17141 } 17142 synchronized (this) { 17143 return isUserRunningLocked(userId, orStopped); 17144 } 17145 } 17146 17147 boolean isUserRunningLocked(int userId, boolean orStopped) { 17148 UserStartedState state = mStartedUsers.get(userId); 17149 if (state == null) { 17150 return false; 17151 } 17152 if (orStopped) { 17153 return true; 17154 } 17155 return state.mState != UserStartedState.STATE_STOPPING 17156 && state.mState != UserStartedState.STATE_SHUTDOWN; 17157 } 17158 17159 @Override 17160 public int[] getRunningUserIds() { 17161 if (checkCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS) 17162 != PackageManager.PERMISSION_GRANTED) { 17163 String msg = "Permission Denial: isUserRunning() from pid=" 17164 + Binder.getCallingPid() 17165 + ", uid=" + Binder.getCallingUid() 17166 + " requires " + android.Manifest.permission.INTERACT_ACROSS_USERS; 17167 Slog.w(TAG, msg); 17168 throw new SecurityException(msg); 17169 } 17170 synchronized (this) { 17171 return mStartedUserArray; 17172 } 17173 } 17174 17175 private void updateStartedUserArrayLocked() { 17176 int num = 0; 17177 for (int i=0; i<mStartedUsers.size(); i++) { 17178 UserStartedState uss = mStartedUsers.valueAt(i); 17179 // This list does not include stopping users. 17180 if (uss.mState != UserStartedState.STATE_STOPPING 17181 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17182 num++; 17183 } 17184 } 17185 mStartedUserArray = new int[num]; 17186 num = 0; 17187 for (int i=0; i<mStartedUsers.size(); i++) { 17188 UserStartedState uss = mStartedUsers.valueAt(i); 17189 if (uss.mState != UserStartedState.STATE_STOPPING 17190 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17191 mStartedUserArray[num] = mStartedUsers.keyAt(i); 17192 num++; 17193 } 17194 } 17195 } 17196 17197 @Override 17198 public void registerUserSwitchObserver(IUserSwitchObserver observer) { 17199 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17200 != PackageManager.PERMISSION_GRANTED) { 17201 String msg = "Permission Denial: registerUserSwitchObserver() from pid=" 17202 + Binder.getCallingPid() 17203 + ", uid=" + Binder.getCallingUid() 17204 + " requires " + INTERACT_ACROSS_USERS_FULL; 17205 Slog.w(TAG, msg); 17206 throw new SecurityException(msg); 17207 } 17208 17209 mUserSwitchObservers.register(observer); 17210 } 17211 17212 @Override 17213 public void unregisterUserSwitchObserver(IUserSwitchObserver observer) { 17214 mUserSwitchObservers.unregister(observer); 17215 } 17216 17217 private boolean userExists(int userId) { 17218 if (userId == 0) { 17219 return true; 17220 } 17221 UserManagerService ums = getUserManagerLocked(); 17222 return ums != null ? (ums.getUserInfo(userId) != null) : false; 17223 } 17224 17225 int[] getUsersLocked() { 17226 UserManagerService ums = getUserManagerLocked(); 17227 return ums != null ? ums.getUserIds() : new int[] { 0 }; 17228 } 17229 17230 UserManagerService getUserManagerLocked() { 17231 if (mUserManager == null) { 17232 IBinder b = ServiceManager.getService(Context.USER_SERVICE); 17233 mUserManager = (UserManagerService)IUserManager.Stub.asInterface(b); 17234 } 17235 return mUserManager; 17236 } 17237 17238 private int applyUserId(int uid, int userId) { 17239 return UserHandle.getUid(userId, uid); 17240 } 17241 17242 ApplicationInfo getAppInfoForUser(ApplicationInfo info, int userId) { 17243 if (info == null) return null; 17244 ApplicationInfo newInfo = new ApplicationInfo(info); 17245 newInfo.uid = applyUserId(info.uid, userId); 17246 newInfo.dataDir = USER_DATA_DIR + userId + "/" 17247 + info.packageName; 17248 return newInfo; 17249 } 17250 17251 ActivityInfo getActivityInfoForUser(ActivityInfo aInfo, int userId) { 17252 if (aInfo == null 17253 || (userId < 1 && aInfo.applicationInfo.uid < UserHandle.PER_USER_RANGE)) { 17254 return aInfo; 17255 } 17256 17257 ActivityInfo info = new ActivityInfo(aInfo); 17258 info.applicationInfo = getAppInfoForUser(info.applicationInfo, userId); 17259 return info; 17260 } 17261 17262 private final class LocalService extends ActivityManagerInternal { 17263 @Override 17264 public void goingToSleep() { 17265 ActivityManagerService.this.goingToSleep(); 17266 } 17267 17268 @Override 17269 public void wakingUp() { 17270 ActivityManagerService.this.wakingUp(); 17271 } 17272 } 17273 17274 /** 17275 * An implementation of IAppTask, that allows an app to manage its own tasks via 17276 * {@link android.app.ActivityManager.AppTask}. We keep track of the callingUid to ensure that 17277 * only the process that calls getAppTasks() can call the AppTask methods. 17278 */ 17279 class AppTaskImpl extends IAppTask.Stub { 17280 private int mTaskId; 17281 private int mCallingUid; 17282 17283 public AppTaskImpl(int taskId, int callingUid) { 17284 mTaskId = taskId; 17285 mCallingUid = callingUid; 17286 } 17287 17288 @Override 17289 public void finishAndRemoveTask() { 17290 // Ensure that we are called from the same process that created this AppTask 17291 if (mCallingUid != Binder.getCallingUid()) { 17292 Slog.w(TAG, "finishAndRemoveTask: caller " + mCallingUid 17293 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 17294 return; 17295 } 17296 17297 synchronized (ActivityManagerService.this) { 17298 long origId = Binder.clearCallingIdentity(); 17299 try { 17300 TaskRecord tr = recentTaskForIdLocked(mTaskId); 17301 if (tr != null) { 17302 // Only kill the process if we are not a new document 17303 int flags = tr.getBaseIntent().getFlags(); 17304 boolean isDocument = (flags & Intent.FLAG_ACTIVITY_NEW_DOCUMENT) == 17305 Intent.FLAG_ACTIVITY_NEW_DOCUMENT; 17306 removeTaskByIdLocked(mTaskId, 17307 !isDocument ? ActivityManager.REMOVE_TASK_KILL_PROCESS : 0); 17308 } 17309 } finally { 17310 Binder.restoreCallingIdentity(origId); 17311 } 17312 } 17313 } 17314 17315 @Override 17316 public ActivityManager.RecentTaskInfo getTaskInfo() { 17317 // Ensure that we are called from the same process that created this AppTask 17318 if (mCallingUid != Binder.getCallingUid()) { 17319 Slog.w(TAG, "finishAndRemoveTask: caller " + mCallingUid 17320 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 17321 return null; 17322 } 17323 17324 synchronized (ActivityManagerService.this) { 17325 long origId = Binder.clearCallingIdentity(); 17326 try { 17327 TaskRecord tr = recentTaskForIdLocked(mTaskId); 17328 if (tr != null) { 17329 return createRecentTaskInfoFromTaskRecord(tr); 17330 } 17331 } finally { 17332 Binder.restoreCallingIdentity(origId); 17333 } 17334 return null; 17335 } 17336 } 17337 } 17338} 17339