ActivityManagerService.java revision d7b8621bde44857ebb07130693a00f5f777887d4
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 : 200; 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 final ComponentName comp = intent.getComponent(); 3542 3543 int maxRecents = task.maxRecents - 1; 3544 for (int i=0; i<N; i++) { 3545 TaskRecord tr = mRecentTasks.get(i); 3546 if (task != tr) { 3547 if (task.userId != tr.userId) { 3548 continue; 3549 } 3550 final Intent trIntent = tr.intent; 3551 if ((task.affinity == null || !task.affinity.equals(tr.affinity)) && 3552 (intent == null || !intent.filterEquals(trIntent))) { 3553 continue; 3554 } 3555 final boolean trIsDocument = trIntent != null && trIntent.isDocument(); 3556 if (document && trIsDocument) { 3557 // These are the same document activity (not necessarily the same doc). 3558 if (maxRecents > 0) { 3559 --maxRecents; 3560 continue; 3561 } 3562 // Hit the maximum number of documents for this task. Fall through 3563 // and remove this document from recents. 3564 } else if (document || trIsDocument) { 3565 // Only one of these is a document. Not the droid we're looking for. 3566 continue; 3567 } 3568 } 3569 3570 // Either task and tr are the same or, their affinities match or their intents match 3571 // and neither of them is a document, or they are documents using the same activity 3572 // and their maxRecents has been reached. 3573 tr.disposeThumbnail(); 3574 mRecentTasks.remove(i); 3575 i--; 3576 N--; 3577 if (task.intent == null) { 3578 // If the new recent task we are adding is not fully 3579 // specified, then replace it with the existing recent task. 3580 task = tr; 3581 } 3582 mTaskPersister.notify(tr, false); 3583 } 3584 if (N >= MAX_RECENT_TASKS) { 3585 mRecentTasks.remove(N-1).disposeThumbnail(); 3586 } 3587 mRecentTasks.add(0, task); 3588 } 3589 3590 @Override 3591 public void reportActivityFullyDrawn(IBinder token) { 3592 synchronized (this) { 3593 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3594 if (r == null) { 3595 return; 3596 } 3597 r.reportFullyDrawnLocked(); 3598 } 3599 } 3600 3601 @Override 3602 public void setRequestedOrientation(IBinder token, int requestedOrientation) { 3603 synchronized (this) { 3604 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3605 if (r == null) { 3606 return; 3607 } 3608 final long origId = Binder.clearCallingIdentity(); 3609 mWindowManager.setAppOrientation(r.appToken, requestedOrientation); 3610 Configuration config = mWindowManager.updateOrientationFromAppTokens( 3611 mConfiguration, r.mayFreezeScreenLocked(r.app) ? r.appToken : null); 3612 if (config != null) { 3613 r.frozenBeforeDestroy = true; 3614 if (!updateConfigurationLocked(config, r, false, false)) { 3615 mStackSupervisor.resumeTopActivitiesLocked(); 3616 } 3617 } 3618 Binder.restoreCallingIdentity(origId); 3619 } 3620 } 3621 3622 @Override 3623 public int getRequestedOrientation(IBinder token) { 3624 synchronized (this) { 3625 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3626 if (r == null) { 3627 return ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED; 3628 } 3629 return mWindowManager.getAppOrientation(r.appToken); 3630 } 3631 } 3632 3633 /** 3634 * This is the internal entry point for handling Activity.finish(). 3635 * 3636 * @param token The Binder token referencing the Activity we want to finish. 3637 * @param resultCode Result code, if any, from this Activity. 3638 * @param resultData Result data (Intent), if any, from this Activity. 3639 * @param finishTask Whether to finish the task associated with this Activity. Only applies to 3640 * the root Activity in the task. 3641 * 3642 * @return Returns true if the activity successfully finished, or false if it is still running. 3643 */ 3644 @Override 3645 public final boolean finishActivity(IBinder token, int resultCode, Intent resultData, 3646 boolean finishTask) { 3647 // Refuse possible leaked file descriptors 3648 if (resultData != null && resultData.hasFileDescriptors() == true) { 3649 throw new IllegalArgumentException("File descriptors passed in Intent"); 3650 } 3651 3652 synchronized(this) { 3653 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3654 if (r == null) { 3655 return true; 3656 } 3657 // Keep track of the root activity of the task before we finish it 3658 TaskRecord tr = r.task; 3659 ActivityRecord rootR = tr.getRootActivity(); 3660 if (mController != null) { 3661 // Find the first activity that is not finishing. 3662 ActivityRecord next = r.task.stack.topRunningActivityLocked(token, 0); 3663 if (next != null) { 3664 // ask watcher if this is allowed 3665 boolean resumeOK = true; 3666 try { 3667 resumeOK = mController.activityResuming(next.packageName); 3668 } catch (RemoteException e) { 3669 mController = null; 3670 Watchdog.getInstance().setActivityController(null); 3671 } 3672 3673 if (!resumeOK) { 3674 return false; 3675 } 3676 } 3677 } 3678 final long origId = Binder.clearCallingIdentity(); 3679 try { 3680 boolean res; 3681 if (finishTask && r == rootR) { 3682 // If requested, remove the task that is associated to this activity only if it 3683 // was the root activity in the task. The result code and data is ignored because 3684 // we don't support returning them across task boundaries. 3685 res = removeTaskByIdLocked(tr.taskId, 0); 3686 } else { 3687 res = tr.stack.requestFinishActivityLocked(token, resultCode, 3688 resultData, "app-request", true); 3689 } 3690 return res; 3691 } finally { 3692 Binder.restoreCallingIdentity(origId); 3693 } 3694 } 3695 } 3696 3697 @Override 3698 public final void finishHeavyWeightApp() { 3699 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 3700 != PackageManager.PERMISSION_GRANTED) { 3701 String msg = "Permission Denial: finishHeavyWeightApp() from pid=" 3702 + Binder.getCallingPid() 3703 + ", uid=" + Binder.getCallingUid() 3704 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 3705 Slog.w(TAG, msg); 3706 throw new SecurityException(msg); 3707 } 3708 3709 synchronized(this) { 3710 if (mHeavyWeightProcess == null) { 3711 return; 3712 } 3713 3714 ArrayList<ActivityRecord> activities = new ArrayList<ActivityRecord>( 3715 mHeavyWeightProcess.activities); 3716 for (int i=0; i<activities.size(); i++) { 3717 ActivityRecord r = activities.get(i); 3718 if (!r.finishing) { 3719 r.task.stack.finishActivityLocked(r, Activity.RESULT_CANCELED, 3720 null, "finish-heavy", true); 3721 } 3722 } 3723 3724 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 3725 mHeavyWeightProcess.userId, 0)); 3726 mHeavyWeightProcess = null; 3727 } 3728 } 3729 3730 @Override 3731 public void crashApplication(int uid, int initialPid, String packageName, 3732 String message) { 3733 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 3734 != PackageManager.PERMISSION_GRANTED) { 3735 String msg = "Permission Denial: crashApplication() from pid=" 3736 + Binder.getCallingPid() 3737 + ", uid=" + Binder.getCallingUid() 3738 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 3739 Slog.w(TAG, msg); 3740 throw new SecurityException(msg); 3741 } 3742 3743 synchronized(this) { 3744 ProcessRecord proc = null; 3745 3746 // Figure out which process to kill. We don't trust that initialPid 3747 // still has any relation to current pids, so must scan through the 3748 // list. 3749 synchronized (mPidsSelfLocked) { 3750 for (int i=0; i<mPidsSelfLocked.size(); i++) { 3751 ProcessRecord p = mPidsSelfLocked.valueAt(i); 3752 if (p.uid != uid) { 3753 continue; 3754 } 3755 if (p.pid == initialPid) { 3756 proc = p; 3757 break; 3758 } 3759 if (p.pkgList.containsKey(packageName)) { 3760 proc = p; 3761 } 3762 } 3763 } 3764 3765 if (proc == null) { 3766 Slog.w(TAG, "crashApplication: nothing for uid=" + uid 3767 + " initialPid=" + initialPid 3768 + " packageName=" + packageName); 3769 return; 3770 } 3771 3772 if (proc.thread != null) { 3773 if (proc.pid == Process.myPid()) { 3774 Log.w(TAG, "crashApplication: trying to crash self!"); 3775 return; 3776 } 3777 long ident = Binder.clearCallingIdentity(); 3778 try { 3779 proc.thread.scheduleCrash(message); 3780 } catch (RemoteException e) { 3781 } 3782 Binder.restoreCallingIdentity(ident); 3783 } 3784 } 3785 } 3786 3787 @Override 3788 public final void finishSubActivity(IBinder token, String resultWho, 3789 int requestCode) { 3790 synchronized(this) { 3791 final long origId = Binder.clearCallingIdentity(); 3792 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3793 if (r != null) { 3794 r.task.stack.finishSubActivityLocked(r, resultWho, requestCode); 3795 } 3796 Binder.restoreCallingIdentity(origId); 3797 } 3798 } 3799 3800 @Override 3801 public boolean finishActivityAffinity(IBinder token) { 3802 synchronized(this) { 3803 final long origId = Binder.clearCallingIdentity(); 3804 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3805 boolean res = false; 3806 if (r != null) { 3807 res = r.task.stack.finishActivityAffinityLocked(r); 3808 } 3809 Binder.restoreCallingIdentity(origId); 3810 return res; 3811 } 3812 } 3813 3814 @Override 3815 public boolean willActivityBeVisible(IBinder token) { 3816 synchronized(this) { 3817 ActivityStack stack = ActivityRecord.getStackLocked(token); 3818 if (stack != null) { 3819 return stack.willActivityBeVisibleLocked(token); 3820 } 3821 return false; 3822 } 3823 } 3824 3825 @Override 3826 public void overridePendingTransition(IBinder token, String packageName, 3827 int enterAnim, int exitAnim) { 3828 synchronized(this) { 3829 ActivityRecord self = ActivityRecord.isInStackLocked(token); 3830 if (self == null) { 3831 return; 3832 } 3833 3834 final long origId = Binder.clearCallingIdentity(); 3835 3836 if (self.state == ActivityState.RESUMED 3837 || self.state == ActivityState.PAUSING) { 3838 mWindowManager.overridePendingAppTransition(packageName, 3839 enterAnim, exitAnim, null); 3840 } 3841 3842 Binder.restoreCallingIdentity(origId); 3843 } 3844 } 3845 3846 /** 3847 * Main function for removing an existing process from the activity manager 3848 * as a result of that process going away. Clears out all connections 3849 * to the process. 3850 */ 3851 private final void handleAppDiedLocked(ProcessRecord app, 3852 boolean restarting, boolean allowRestart) { 3853 int pid = app.pid; 3854 cleanUpApplicationRecordLocked(app, restarting, allowRestart, -1); 3855 if (!restarting) { 3856 removeLruProcessLocked(app); 3857 if (pid > 0) { 3858 ProcessList.remove(pid); 3859 } 3860 } 3861 3862 if (mProfileProc == app) { 3863 clearProfilerLocked(); 3864 } 3865 3866 // Remove this application's activities from active lists. 3867 boolean hasVisibleActivities = mStackSupervisor.handleAppDiedLocked(app); 3868 3869 app.activities.clear(); 3870 3871 if (app.instrumentationClass != null) { 3872 Slog.w(TAG, "Crash of app " + app.processName 3873 + " running instrumentation " + app.instrumentationClass); 3874 Bundle info = new Bundle(); 3875 info.putString("shortMsg", "Process crashed."); 3876 finishInstrumentationLocked(app, Activity.RESULT_CANCELED, info); 3877 } 3878 3879 if (!restarting) { 3880 if (!mStackSupervisor.resumeTopActivitiesLocked()) { 3881 // If there was nothing to resume, and we are not already 3882 // restarting this process, but there is a visible activity that 3883 // is hosted by the process... then make sure all visible 3884 // activities are running, taking care of restarting this 3885 // process. 3886 if (hasVisibleActivities) { 3887 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 3888 } 3889 } 3890 } 3891 } 3892 3893 private final int getLRURecordIndexForAppLocked(IApplicationThread thread) { 3894 IBinder threadBinder = thread.asBinder(); 3895 // Find the application record. 3896 for (int i=mLruProcesses.size()-1; i>=0; i--) { 3897 ProcessRecord rec = mLruProcesses.get(i); 3898 if (rec.thread != null && rec.thread.asBinder() == threadBinder) { 3899 return i; 3900 } 3901 } 3902 return -1; 3903 } 3904 3905 final ProcessRecord getRecordForAppLocked( 3906 IApplicationThread thread) { 3907 if (thread == null) { 3908 return null; 3909 } 3910 3911 int appIndex = getLRURecordIndexForAppLocked(thread); 3912 return appIndex >= 0 ? mLruProcesses.get(appIndex) : null; 3913 } 3914 3915 final void doLowMemReportIfNeededLocked(ProcessRecord dyingProc) { 3916 // If there are no longer any background processes running, 3917 // and the app that died was not running instrumentation, 3918 // then tell everyone we are now low on memory. 3919 boolean haveBg = false; 3920 for (int i=mLruProcesses.size()-1; i>=0; i--) { 3921 ProcessRecord rec = mLruProcesses.get(i); 3922 if (rec.thread != null 3923 && rec.setProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 3924 haveBg = true; 3925 break; 3926 } 3927 } 3928 3929 if (!haveBg) { 3930 boolean doReport = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 3931 if (doReport) { 3932 long now = SystemClock.uptimeMillis(); 3933 if (now < (mLastMemUsageReportTime+5*60*1000)) { 3934 doReport = false; 3935 } else { 3936 mLastMemUsageReportTime = now; 3937 } 3938 } 3939 final ArrayList<ProcessMemInfo> memInfos 3940 = doReport ? new ArrayList<ProcessMemInfo>(mLruProcesses.size()) : null; 3941 EventLog.writeEvent(EventLogTags.AM_LOW_MEMORY, mLruProcesses.size()); 3942 long now = SystemClock.uptimeMillis(); 3943 for (int i=mLruProcesses.size()-1; i>=0; i--) { 3944 ProcessRecord rec = mLruProcesses.get(i); 3945 if (rec == dyingProc || rec.thread == null) { 3946 continue; 3947 } 3948 if (doReport) { 3949 memInfos.add(new ProcessMemInfo(rec.processName, rec.pid, rec.setAdj, 3950 rec.setProcState, rec.adjType, rec.makeAdjReason())); 3951 } 3952 if ((rec.lastLowMemory+GC_MIN_INTERVAL) <= now) { 3953 // The low memory report is overriding any current 3954 // state for a GC request. Make sure to do 3955 // heavy/important/visible/foreground processes first. 3956 if (rec.setAdj <= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 3957 rec.lastRequestedGc = 0; 3958 } else { 3959 rec.lastRequestedGc = rec.lastLowMemory; 3960 } 3961 rec.reportLowMemory = true; 3962 rec.lastLowMemory = now; 3963 mProcessesToGc.remove(rec); 3964 addProcessToGcListLocked(rec); 3965 } 3966 } 3967 if (doReport) { 3968 Message msg = mHandler.obtainMessage(REPORT_MEM_USAGE_MSG, memInfos); 3969 mHandler.sendMessage(msg); 3970 } 3971 scheduleAppGcsLocked(); 3972 } 3973 } 3974 3975 final void appDiedLocked(ProcessRecord app, int pid, 3976 IApplicationThread thread) { 3977 3978 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 3979 synchronized (stats) { 3980 stats.noteProcessDiedLocked(app.info.uid, pid); 3981 } 3982 3983 // Clean up already done if the process has been re-started. 3984 if (app.pid == pid && app.thread != null && 3985 app.thread.asBinder() == thread.asBinder()) { 3986 boolean doLowMem = app.instrumentationClass == null; 3987 boolean doOomAdj = doLowMem; 3988 if (!app.killedByAm) { 3989 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 3990 + ") has died."); 3991 mAllowLowerMemLevel = true; 3992 } else { 3993 // Note that we always want to do oom adj to update our state with the 3994 // new number of procs. 3995 mAllowLowerMemLevel = false; 3996 doLowMem = false; 3997 } 3998 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 3999 if (DEBUG_CLEANUP) Slog.v( 4000 TAG, "Dying app: " + app + ", pid: " + pid 4001 + ", thread: " + thread.asBinder()); 4002 handleAppDiedLocked(app, false, true); 4003 4004 if (doOomAdj) { 4005 updateOomAdjLocked(); 4006 } 4007 if (doLowMem) { 4008 doLowMemReportIfNeededLocked(app); 4009 } 4010 } else if (app.pid != pid) { 4011 // A new process has already been started. 4012 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4013 + ") has died and restarted (pid " + app.pid + ")."); 4014 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4015 } else if (DEBUG_PROCESSES) { 4016 Slog.d(TAG, "Received spurious death notification for thread " 4017 + thread.asBinder()); 4018 } 4019 } 4020 4021 /** 4022 * If a stack trace dump file is configured, dump process stack traces. 4023 * @param clearTraces causes the dump file to be erased prior to the new 4024 * traces being written, if true; when false, the new traces will be 4025 * appended to any existing file content. 4026 * @param firstPids of dalvik VM processes to dump stack traces for first 4027 * @param lastPids of dalvik VM processes to dump stack traces for last 4028 * @param nativeProcs optional list of native process names to dump stack crawls 4029 * @return file containing stack traces, or null if no dump file is configured 4030 */ 4031 public static File dumpStackTraces(boolean clearTraces, ArrayList<Integer> firstPids, 4032 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4033 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4034 if (tracesPath == null || tracesPath.length() == 0) { 4035 return null; 4036 } 4037 4038 File tracesFile = new File(tracesPath); 4039 try { 4040 File tracesDir = tracesFile.getParentFile(); 4041 if (!tracesDir.exists()) { 4042 tracesFile.mkdirs(); 4043 if (!SELinux.restorecon(tracesDir)) { 4044 return null; 4045 } 4046 } 4047 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4048 4049 if (clearTraces && tracesFile.exists()) tracesFile.delete(); 4050 tracesFile.createNewFile(); 4051 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4052 } catch (IOException e) { 4053 Slog.w(TAG, "Unable to prepare ANR traces file: " + tracesPath, e); 4054 return null; 4055 } 4056 4057 dumpStackTraces(tracesPath, firstPids, processCpuTracker, lastPids, nativeProcs); 4058 return tracesFile; 4059 } 4060 4061 private static void dumpStackTraces(String tracesPath, ArrayList<Integer> firstPids, 4062 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4063 // Use a FileObserver to detect when traces finish writing. 4064 // The order of traces is considered important to maintain for legibility. 4065 FileObserver observer = new FileObserver(tracesPath, FileObserver.CLOSE_WRITE) { 4066 @Override 4067 public synchronized void onEvent(int event, String path) { notify(); } 4068 }; 4069 4070 try { 4071 observer.startWatching(); 4072 4073 // First collect all of the stacks of the most important pids. 4074 if (firstPids != null) { 4075 try { 4076 int num = firstPids.size(); 4077 for (int i = 0; i < num; i++) { 4078 synchronized (observer) { 4079 Process.sendSignal(firstPids.get(i), Process.SIGNAL_QUIT); 4080 observer.wait(200); // Wait for write-close, give up after 200msec 4081 } 4082 } 4083 } catch (InterruptedException e) { 4084 Log.wtf(TAG, e); 4085 } 4086 } 4087 4088 // Next collect the stacks of the native pids 4089 if (nativeProcs != null) { 4090 int[] pids = Process.getPidsForCommands(nativeProcs); 4091 if (pids != null) { 4092 for (int pid : pids) { 4093 Debug.dumpNativeBacktraceToFile(pid, tracesPath); 4094 } 4095 } 4096 } 4097 4098 // Lastly, measure CPU usage. 4099 if (processCpuTracker != null) { 4100 processCpuTracker.init(); 4101 System.gc(); 4102 processCpuTracker.update(); 4103 try { 4104 synchronized (processCpuTracker) { 4105 processCpuTracker.wait(500); // measure over 1/2 second. 4106 } 4107 } catch (InterruptedException e) { 4108 } 4109 processCpuTracker.update(); 4110 4111 // We'll take the stack crawls of just the top apps using CPU. 4112 final int N = processCpuTracker.countWorkingStats(); 4113 int numProcs = 0; 4114 for (int i=0; i<N && numProcs<5; i++) { 4115 ProcessCpuTracker.Stats stats = processCpuTracker.getWorkingStats(i); 4116 if (lastPids.indexOfKey(stats.pid) >= 0) { 4117 numProcs++; 4118 try { 4119 synchronized (observer) { 4120 Process.sendSignal(stats.pid, Process.SIGNAL_QUIT); 4121 observer.wait(200); // Wait for write-close, give up after 200msec 4122 } 4123 } catch (InterruptedException e) { 4124 Log.wtf(TAG, e); 4125 } 4126 4127 } 4128 } 4129 } 4130 } finally { 4131 observer.stopWatching(); 4132 } 4133 } 4134 4135 final void logAppTooSlow(ProcessRecord app, long startTime, String msg) { 4136 if (true || IS_USER_BUILD) { 4137 return; 4138 } 4139 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4140 if (tracesPath == null || tracesPath.length() == 0) { 4141 return; 4142 } 4143 4144 StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads(); 4145 StrictMode.allowThreadDiskWrites(); 4146 try { 4147 final File tracesFile = new File(tracesPath); 4148 final File tracesDir = tracesFile.getParentFile(); 4149 final File tracesTmp = new File(tracesDir, "__tmp__"); 4150 try { 4151 if (!tracesDir.exists()) { 4152 tracesFile.mkdirs(); 4153 if (!SELinux.restorecon(tracesDir.getPath())) { 4154 return; 4155 } 4156 } 4157 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4158 4159 if (tracesFile.exists()) { 4160 tracesTmp.delete(); 4161 tracesFile.renameTo(tracesTmp); 4162 } 4163 StringBuilder sb = new StringBuilder(); 4164 Time tobj = new Time(); 4165 tobj.set(System.currentTimeMillis()); 4166 sb.append(tobj.format("%Y-%m-%d %H:%M:%S")); 4167 sb.append(": "); 4168 TimeUtils.formatDuration(SystemClock.uptimeMillis()-startTime, sb); 4169 sb.append(" since "); 4170 sb.append(msg); 4171 FileOutputStream fos = new FileOutputStream(tracesFile); 4172 fos.write(sb.toString().getBytes()); 4173 if (app == null) { 4174 fos.write("\n*** No application process!".getBytes()); 4175 } 4176 fos.close(); 4177 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4178 } catch (IOException e) { 4179 Slog.w(TAG, "Unable to prepare slow app traces file: " + tracesPath, e); 4180 return; 4181 } 4182 4183 if (app != null) { 4184 ArrayList<Integer> firstPids = new ArrayList<Integer>(); 4185 firstPids.add(app.pid); 4186 dumpStackTraces(tracesPath, firstPids, null, null, null); 4187 } 4188 4189 File lastTracesFile = null; 4190 File curTracesFile = null; 4191 for (int i=9; i>=0; i--) { 4192 String name = String.format(Locale.US, "slow%02d.txt", i); 4193 curTracesFile = new File(tracesDir, name); 4194 if (curTracesFile.exists()) { 4195 if (lastTracesFile != null) { 4196 curTracesFile.renameTo(lastTracesFile); 4197 } else { 4198 curTracesFile.delete(); 4199 } 4200 } 4201 lastTracesFile = curTracesFile; 4202 } 4203 tracesFile.renameTo(curTracesFile); 4204 if (tracesTmp.exists()) { 4205 tracesTmp.renameTo(tracesFile); 4206 } 4207 } finally { 4208 StrictMode.setThreadPolicy(oldPolicy); 4209 } 4210 } 4211 4212 final void appNotResponding(ProcessRecord app, ActivityRecord activity, 4213 ActivityRecord parent, boolean aboveSystem, final String annotation) { 4214 ArrayList<Integer> firstPids = new ArrayList<Integer>(5); 4215 SparseArray<Boolean> lastPids = new SparseArray<Boolean>(20); 4216 4217 if (mController != null) { 4218 try { 4219 // 0 == continue, -1 = kill process immediately 4220 int res = mController.appEarlyNotResponding(app.processName, app.pid, annotation); 4221 if (res < 0 && app.pid != MY_PID) Process.killProcess(app.pid); 4222 } catch (RemoteException e) { 4223 mController = null; 4224 Watchdog.getInstance().setActivityController(null); 4225 } 4226 } 4227 4228 long anrTime = SystemClock.uptimeMillis(); 4229 if (MONITOR_CPU_USAGE) { 4230 updateCpuStatsNow(); 4231 } 4232 4233 synchronized (this) { 4234 // PowerManager.reboot() can block for a long time, so ignore ANRs while shutting down. 4235 if (mShuttingDown) { 4236 Slog.i(TAG, "During shutdown skipping ANR: " + app + " " + annotation); 4237 return; 4238 } else if (app.notResponding) { 4239 Slog.i(TAG, "Skipping duplicate ANR: " + app + " " + annotation); 4240 return; 4241 } else if (app.crashing) { 4242 Slog.i(TAG, "Crashing app skipping ANR: " + app + " " + annotation); 4243 return; 4244 } 4245 4246 // In case we come through here for the same app before completing 4247 // this one, mark as anring now so we will bail out. 4248 app.notResponding = true; 4249 4250 // Log the ANR to the event log. 4251 EventLog.writeEvent(EventLogTags.AM_ANR, app.userId, app.pid, 4252 app.processName, app.info.flags, annotation); 4253 4254 // Dump thread traces as quickly as we can, starting with "interesting" processes. 4255 firstPids.add(app.pid); 4256 4257 int parentPid = app.pid; 4258 if (parent != null && parent.app != null && parent.app.pid > 0) parentPid = parent.app.pid; 4259 if (parentPid != app.pid) firstPids.add(parentPid); 4260 4261 if (MY_PID != app.pid && MY_PID != parentPid) firstPids.add(MY_PID); 4262 4263 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 4264 ProcessRecord r = mLruProcesses.get(i); 4265 if (r != null && r.thread != null) { 4266 int pid = r.pid; 4267 if (pid > 0 && pid != app.pid && pid != parentPid && pid != MY_PID) { 4268 if (r.persistent) { 4269 firstPids.add(pid); 4270 } else { 4271 lastPids.put(pid, Boolean.TRUE); 4272 } 4273 } 4274 } 4275 } 4276 } 4277 4278 // Log the ANR to the main log. 4279 StringBuilder info = new StringBuilder(); 4280 info.setLength(0); 4281 info.append("ANR in ").append(app.processName); 4282 if (activity != null && activity.shortComponentName != null) { 4283 info.append(" (").append(activity.shortComponentName).append(")"); 4284 } 4285 info.append("\n"); 4286 info.append("PID: ").append(app.pid).append("\n"); 4287 if (annotation != null) { 4288 info.append("Reason: ").append(annotation).append("\n"); 4289 } 4290 if (parent != null && parent != activity) { 4291 info.append("Parent: ").append(parent.shortComponentName).append("\n"); 4292 } 4293 4294 final ProcessCpuTracker processCpuTracker = new ProcessCpuTracker(true); 4295 4296 File tracesFile = dumpStackTraces(true, firstPids, processCpuTracker, lastPids, 4297 NATIVE_STACKS_OF_INTEREST); 4298 4299 String cpuInfo = null; 4300 if (MONITOR_CPU_USAGE) { 4301 updateCpuStatsNow(); 4302 synchronized (mProcessCpuThread) { 4303 cpuInfo = mProcessCpuTracker.printCurrentState(anrTime); 4304 } 4305 info.append(processCpuTracker.printCurrentLoad()); 4306 info.append(cpuInfo); 4307 } 4308 4309 info.append(processCpuTracker.printCurrentState(anrTime)); 4310 4311 Slog.e(TAG, info.toString()); 4312 if (tracesFile == null) { 4313 // There is no trace file, so dump (only) the alleged culprit's threads to the log 4314 Process.sendSignal(app.pid, Process.SIGNAL_QUIT); 4315 } 4316 4317 addErrorToDropBox("anr", app, app.processName, activity, parent, annotation, 4318 cpuInfo, tracesFile, null); 4319 4320 if (mController != null) { 4321 try { 4322 // 0 == show dialog, 1 = keep waiting, -1 = kill process immediately 4323 int res = mController.appNotResponding(app.processName, app.pid, info.toString()); 4324 if (res != 0) { 4325 if (res < 0 && app.pid != MY_PID) { 4326 Process.killProcess(app.pid); 4327 } else { 4328 synchronized (this) { 4329 mServices.scheduleServiceTimeoutLocked(app); 4330 } 4331 } 4332 return; 4333 } 4334 } catch (RemoteException e) { 4335 mController = null; 4336 Watchdog.getInstance().setActivityController(null); 4337 } 4338 } 4339 4340 // Unless configured otherwise, swallow ANRs in background processes & kill the process. 4341 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 4342 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 4343 4344 synchronized (this) { 4345 if (!showBackground && !app.isInterestingToUserLocked() && app.pid != MY_PID) { 4346 killUnneededProcessLocked(app, "background ANR"); 4347 return; 4348 } 4349 4350 // Set the app's notResponding state, and look up the errorReportReceiver 4351 makeAppNotRespondingLocked(app, 4352 activity != null ? activity.shortComponentName : null, 4353 annotation != null ? "ANR " + annotation : "ANR", 4354 info.toString()); 4355 4356 // Bring up the infamous App Not Responding dialog 4357 Message msg = Message.obtain(); 4358 HashMap<String, Object> map = new HashMap<String, Object>(); 4359 msg.what = SHOW_NOT_RESPONDING_MSG; 4360 msg.obj = map; 4361 msg.arg1 = aboveSystem ? 1 : 0; 4362 map.put("app", app); 4363 if (activity != null) { 4364 map.put("activity", activity); 4365 } 4366 4367 mHandler.sendMessage(msg); 4368 } 4369 } 4370 4371 final void showLaunchWarningLocked(final ActivityRecord cur, final ActivityRecord next) { 4372 if (!mLaunchWarningShown) { 4373 mLaunchWarningShown = true; 4374 mHandler.post(new Runnable() { 4375 @Override 4376 public void run() { 4377 synchronized (ActivityManagerService.this) { 4378 final Dialog d = new LaunchWarningWindow(mContext, cur, next); 4379 d.show(); 4380 mHandler.postDelayed(new Runnable() { 4381 @Override 4382 public void run() { 4383 synchronized (ActivityManagerService.this) { 4384 d.dismiss(); 4385 mLaunchWarningShown = false; 4386 } 4387 } 4388 }, 4000); 4389 } 4390 } 4391 }); 4392 } 4393 } 4394 4395 @Override 4396 public boolean clearApplicationUserData(final String packageName, 4397 final IPackageDataObserver observer, int userId) { 4398 enforceNotIsolatedCaller("clearApplicationUserData"); 4399 int uid = Binder.getCallingUid(); 4400 int pid = Binder.getCallingPid(); 4401 userId = handleIncomingUser(pid, uid, 4402 userId, false, true, "clearApplicationUserData", null); 4403 long callingId = Binder.clearCallingIdentity(); 4404 try { 4405 IPackageManager pm = AppGlobals.getPackageManager(); 4406 int pkgUid = -1; 4407 synchronized(this) { 4408 try { 4409 pkgUid = pm.getPackageUid(packageName, userId); 4410 } catch (RemoteException e) { 4411 } 4412 if (pkgUid == -1) { 4413 Slog.w(TAG, "Invalid packageName: " + packageName); 4414 if (observer != null) { 4415 try { 4416 observer.onRemoveCompleted(packageName, false); 4417 } catch (RemoteException e) { 4418 Slog.i(TAG, "Observer no longer exists."); 4419 } 4420 } 4421 return false; 4422 } 4423 if (uid == pkgUid || checkComponentPermission( 4424 android.Manifest.permission.CLEAR_APP_USER_DATA, 4425 pid, uid, -1, true) 4426 == PackageManager.PERMISSION_GRANTED) { 4427 forceStopPackageLocked(packageName, pkgUid, "clear data"); 4428 } else { 4429 throw new SecurityException("PID " + pid + " does not have permission " 4430 + android.Manifest.permission.CLEAR_APP_USER_DATA + " to clear data" 4431 + " of package " + packageName); 4432 } 4433 } 4434 4435 try { 4436 // Clear application user data 4437 pm.clearApplicationUserData(packageName, observer, userId); 4438 4439 // Remove all permissions granted from/to this package 4440 removeUriPermissionsForPackageLocked(packageName, userId, true); 4441 4442 Intent intent = new Intent(Intent.ACTION_PACKAGE_DATA_CLEARED, 4443 Uri.fromParts("package", packageName, null)); 4444 intent.putExtra(Intent.EXTRA_UID, pkgUid); 4445 broadcastIntentInPackage("android", Process.SYSTEM_UID, intent, 4446 null, null, 0, null, null, null, false, false, userId); 4447 } catch (RemoteException e) { 4448 } 4449 } finally { 4450 Binder.restoreCallingIdentity(callingId); 4451 } 4452 return true; 4453 } 4454 4455 @Override 4456 public void killBackgroundProcesses(final String packageName, int userId) { 4457 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 4458 != PackageManager.PERMISSION_GRANTED && 4459 checkCallingPermission(android.Manifest.permission.RESTART_PACKAGES) 4460 != PackageManager.PERMISSION_GRANTED) { 4461 String msg = "Permission Denial: killBackgroundProcesses() from pid=" 4462 + Binder.getCallingPid() 4463 + ", uid=" + Binder.getCallingUid() 4464 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 4465 Slog.w(TAG, msg); 4466 throw new SecurityException(msg); 4467 } 4468 4469 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4470 userId, true, true, "killBackgroundProcesses", null); 4471 long callingId = Binder.clearCallingIdentity(); 4472 try { 4473 IPackageManager pm = AppGlobals.getPackageManager(); 4474 synchronized(this) { 4475 int appId = -1; 4476 try { 4477 appId = UserHandle.getAppId(pm.getPackageUid(packageName, 0)); 4478 } catch (RemoteException e) { 4479 } 4480 if (appId == -1) { 4481 Slog.w(TAG, "Invalid packageName: " + packageName); 4482 return; 4483 } 4484 killPackageProcessesLocked(packageName, appId, userId, 4485 ProcessList.SERVICE_ADJ, false, true, true, false, "kill background"); 4486 } 4487 } finally { 4488 Binder.restoreCallingIdentity(callingId); 4489 } 4490 } 4491 4492 @Override 4493 public void killAllBackgroundProcesses() { 4494 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 4495 != PackageManager.PERMISSION_GRANTED) { 4496 String msg = "Permission Denial: killAllBackgroundProcesses() from pid=" 4497 + Binder.getCallingPid() 4498 + ", uid=" + Binder.getCallingUid() 4499 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 4500 Slog.w(TAG, msg); 4501 throw new SecurityException(msg); 4502 } 4503 4504 long callingId = Binder.clearCallingIdentity(); 4505 try { 4506 synchronized(this) { 4507 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 4508 final int NP = mProcessNames.getMap().size(); 4509 for (int ip=0; ip<NP; ip++) { 4510 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 4511 final int NA = apps.size(); 4512 for (int ia=0; ia<NA; ia++) { 4513 ProcessRecord app = apps.valueAt(ia); 4514 if (app.persistent) { 4515 // we don't kill persistent processes 4516 continue; 4517 } 4518 if (app.removed) { 4519 procs.add(app); 4520 } else if (app.setAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 4521 app.removed = true; 4522 procs.add(app); 4523 } 4524 } 4525 } 4526 4527 int N = procs.size(); 4528 for (int i=0; i<N; i++) { 4529 removeProcessLocked(procs.get(i), false, true, "kill all background"); 4530 } 4531 mAllowLowerMemLevel = true; 4532 updateOomAdjLocked(); 4533 doLowMemReportIfNeededLocked(null); 4534 } 4535 } finally { 4536 Binder.restoreCallingIdentity(callingId); 4537 } 4538 } 4539 4540 @Override 4541 public void forceStopPackage(final String packageName, int userId) { 4542 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4543 != PackageManager.PERMISSION_GRANTED) { 4544 String msg = "Permission Denial: forceStopPackage() from pid=" 4545 + Binder.getCallingPid() 4546 + ", uid=" + Binder.getCallingUid() 4547 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4548 Slog.w(TAG, msg); 4549 throw new SecurityException(msg); 4550 } 4551 final int callingPid = Binder.getCallingPid(); 4552 userId = handleIncomingUser(callingPid, Binder.getCallingUid(), 4553 userId, true, true, "forceStopPackage", null); 4554 long callingId = Binder.clearCallingIdentity(); 4555 try { 4556 IPackageManager pm = AppGlobals.getPackageManager(); 4557 synchronized(this) { 4558 int[] users = userId == UserHandle.USER_ALL 4559 ? getUsersLocked() : new int[] { userId }; 4560 for (int user : users) { 4561 int pkgUid = -1; 4562 try { 4563 pkgUid = pm.getPackageUid(packageName, user); 4564 } catch (RemoteException e) { 4565 } 4566 if (pkgUid == -1) { 4567 Slog.w(TAG, "Invalid packageName: " + packageName); 4568 continue; 4569 } 4570 try { 4571 pm.setPackageStoppedState(packageName, true, user); 4572 } catch (RemoteException e) { 4573 } catch (IllegalArgumentException e) { 4574 Slog.w(TAG, "Failed trying to unstop package " 4575 + packageName + ": " + e); 4576 } 4577 if (isUserRunningLocked(user, false)) { 4578 forceStopPackageLocked(packageName, pkgUid, "from pid " + callingPid); 4579 } 4580 } 4581 } 4582 } finally { 4583 Binder.restoreCallingIdentity(callingId); 4584 } 4585 } 4586 4587 /* 4588 * The pkg name and app id have to be specified. 4589 */ 4590 @Override 4591 public void killApplicationWithAppId(String pkg, int appid, String reason) { 4592 if (pkg == null) { 4593 return; 4594 } 4595 // Make sure the uid is valid. 4596 if (appid < 0) { 4597 Slog.w(TAG, "Invalid appid specified for pkg : " + pkg); 4598 return; 4599 } 4600 int callerUid = Binder.getCallingUid(); 4601 // Only the system server can kill an application 4602 if (callerUid == Process.SYSTEM_UID) { 4603 // Post an aysnc message to kill the application 4604 Message msg = mHandler.obtainMessage(KILL_APPLICATION_MSG); 4605 msg.arg1 = appid; 4606 msg.arg2 = 0; 4607 Bundle bundle = new Bundle(); 4608 bundle.putString("pkg", pkg); 4609 bundle.putString("reason", reason); 4610 msg.obj = bundle; 4611 mHandler.sendMessage(msg); 4612 } else { 4613 throw new SecurityException(callerUid + " cannot kill pkg: " + 4614 pkg); 4615 } 4616 } 4617 4618 @Override 4619 public void closeSystemDialogs(String reason) { 4620 enforceNotIsolatedCaller("closeSystemDialogs"); 4621 4622 final int pid = Binder.getCallingPid(); 4623 final int uid = Binder.getCallingUid(); 4624 final long origId = Binder.clearCallingIdentity(); 4625 try { 4626 synchronized (this) { 4627 // Only allow this from foreground processes, so that background 4628 // applications can't abuse it to prevent system UI from being shown. 4629 if (uid >= Process.FIRST_APPLICATION_UID) { 4630 ProcessRecord proc; 4631 synchronized (mPidsSelfLocked) { 4632 proc = mPidsSelfLocked.get(pid); 4633 } 4634 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 4635 Slog.w(TAG, "Ignoring closeSystemDialogs " + reason 4636 + " from background process " + proc); 4637 return; 4638 } 4639 } 4640 closeSystemDialogsLocked(reason); 4641 } 4642 } finally { 4643 Binder.restoreCallingIdentity(origId); 4644 } 4645 } 4646 4647 void closeSystemDialogsLocked(String reason) { 4648 Intent intent = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS); 4649 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4650 | Intent.FLAG_RECEIVER_FOREGROUND); 4651 if (reason != null) { 4652 intent.putExtra("reason", reason); 4653 } 4654 mWindowManager.closeSystemDialogs(reason); 4655 4656 mStackSupervisor.closeSystemDialogsLocked(); 4657 4658 broadcastIntentLocked(null, null, intent, null, 4659 null, 0, null, null, null, AppOpsManager.OP_NONE, false, false, -1, 4660 Process.SYSTEM_UID, UserHandle.USER_ALL); 4661 } 4662 4663 @Override 4664 public Debug.MemoryInfo[] getProcessMemoryInfo(int[] pids) { 4665 enforceNotIsolatedCaller("getProcessMemoryInfo"); 4666 Debug.MemoryInfo[] infos = new Debug.MemoryInfo[pids.length]; 4667 for (int i=pids.length-1; i>=0; i--) { 4668 ProcessRecord proc; 4669 int oomAdj; 4670 synchronized (this) { 4671 synchronized (mPidsSelfLocked) { 4672 proc = mPidsSelfLocked.get(pids[i]); 4673 oomAdj = proc != null ? proc.setAdj : 0; 4674 } 4675 } 4676 infos[i] = new Debug.MemoryInfo(); 4677 Debug.getMemoryInfo(pids[i], infos[i]); 4678 if (proc != null) { 4679 synchronized (this) { 4680 if (proc.thread != null && proc.setAdj == oomAdj) { 4681 // Record this for posterity if the process has been stable. 4682 proc.baseProcessTracker.addPss(infos[i].getTotalPss(), 4683 infos[i].getTotalUss(), false, proc.pkgList); 4684 } 4685 } 4686 } 4687 } 4688 return infos; 4689 } 4690 4691 @Override 4692 public long[] getProcessPss(int[] pids) { 4693 enforceNotIsolatedCaller("getProcessPss"); 4694 long[] pss = new long[pids.length]; 4695 for (int i=pids.length-1; i>=0; i--) { 4696 ProcessRecord proc; 4697 int oomAdj; 4698 synchronized (this) { 4699 synchronized (mPidsSelfLocked) { 4700 proc = mPidsSelfLocked.get(pids[i]); 4701 oomAdj = proc != null ? proc.setAdj : 0; 4702 } 4703 } 4704 long[] tmpUss = new long[1]; 4705 pss[i] = Debug.getPss(pids[i], tmpUss); 4706 if (proc != null) { 4707 synchronized (this) { 4708 if (proc.thread != null && proc.setAdj == oomAdj) { 4709 // Record this for posterity if the process has been stable. 4710 proc.baseProcessTracker.addPss(pss[i], tmpUss[0], false, proc.pkgList); 4711 } 4712 } 4713 } 4714 } 4715 return pss; 4716 } 4717 4718 @Override 4719 public void killApplicationProcess(String processName, int uid) { 4720 if (processName == null) { 4721 return; 4722 } 4723 4724 int callerUid = Binder.getCallingUid(); 4725 // Only the system server can kill an application 4726 if (callerUid == Process.SYSTEM_UID) { 4727 synchronized (this) { 4728 ProcessRecord app = getProcessRecordLocked(processName, uid, true); 4729 if (app != null && app.thread != null) { 4730 try { 4731 app.thread.scheduleSuicide(); 4732 } catch (RemoteException e) { 4733 // If the other end already died, then our work here is done. 4734 } 4735 } else { 4736 Slog.w(TAG, "Process/uid not found attempting kill of " 4737 + processName + " / " + uid); 4738 } 4739 } 4740 } else { 4741 throw new SecurityException(callerUid + " cannot kill app process: " + 4742 processName); 4743 } 4744 } 4745 4746 private void forceStopPackageLocked(final String packageName, int uid, String reason) { 4747 forceStopPackageLocked(packageName, UserHandle.getAppId(uid), false, 4748 false, true, false, false, UserHandle.getUserId(uid), reason); 4749 Intent intent = new Intent(Intent.ACTION_PACKAGE_RESTARTED, 4750 Uri.fromParts("package", packageName, null)); 4751 if (!mProcessesReady) { 4752 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4753 | Intent.FLAG_RECEIVER_FOREGROUND); 4754 } 4755 intent.putExtra(Intent.EXTRA_UID, uid); 4756 intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(uid)); 4757 broadcastIntentLocked(null, null, intent, 4758 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 4759 false, false, 4760 MY_PID, Process.SYSTEM_UID, UserHandle.getUserId(uid)); 4761 } 4762 4763 private void forceStopUserLocked(int userId, String reason) { 4764 forceStopPackageLocked(null, -1, false, false, true, false, false, userId, reason); 4765 Intent intent = new Intent(Intent.ACTION_USER_STOPPED); 4766 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4767 | Intent.FLAG_RECEIVER_FOREGROUND); 4768 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 4769 broadcastIntentLocked(null, null, intent, 4770 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 4771 false, false, 4772 MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 4773 } 4774 4775 private final boolean killPackageProcessesLocked(String packageName, int appId, 4776 int userId, int minOomAdj, boolean callerWillRestart, boolean allowRestart, 4777 boolean doit, boolean evenPersistent, String reason) { 4778 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 4779 4780 // Remove all processes this package may have touched: all with the 4781 // same UID (except for the system or root user), and all whose name 4782 // matches the package name. 4783 final String procNamePrefix = packageName != null ? (packageName + ":") : null; 4784 final int NP = mProcessNames.getMap().size(); 4785 for (int ip=0; ip<NP; ip++) { 4786 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 4787 final int NA = apps.size(); 4788 for (int ia=0; ia<NA; ia++) { 4789 ProcessRecord app = apps.valueAt(ia); 4790 if (app.persistent && !evenPersistent) { 4791 // we don't kill persistent processes 4792 continue; 4793 } 4794 if (app.removed) { 4795 if (doit) { 4796 procs.add(app); 4797 } 4798 continue; 4799 } 4800 4801 // Skip process if it doesn't meet our oom adj requirement. 4802 if (app.setAdj < minOomAdj) { 4803 continue; 4804 } 4805 4806 // If no package is specified, we call all processes under the 4807 // give user id. 4808 if (packageName == null) { 4809 if (app.userId != userId) { 4810 continue; 4811 } 4812 if (appId >= 0 && UserHandle.getAppId(app.uid) != appId) { 4813 continue; 4814 } 4815 // Package has been specified, we want to hit all processes 4816 // that match it. We need to qualify this by the processes 4817 // that are running under the specified app and user ID. 4818 } else { 4819 if (UserHandle.getAppId(app.uid) != appId) { 4820 continue; 4821 } 4822 if (userId != UserHandle.USER_ALL && app.userId != userId) { 4823 continue; 4824 } 4825 if (!app.pkgList.containsKey(packageName)) { 4826 continue; 4827 } 4828 } 4829 4830 // Process has passed all conditions, kill it! 4831 if (!doit) { 4832 return true; 4833 } 4834 app.removed = true; 4835 procs.add(app); 4836 } 4837 } 4838 4839 int N = procs.size(); 4840 for (int i=0; i<N; i++) { 4841 removeProcessLocked(procs.get(i), callerWillRestart, allowRestart, reason); 4842 } 4843 updateOomAdjLocked(); 4844 return N > 0; 4845 } 4846 4847 private final boolean forceStopPackageLocked(String name, int appId, 4848 boolean callerWillRestart, boolean purgeCache, boolean doit, 4849 boolean evenPersistent, boolean uninstalling, int userId, String reason) { 4850 int i; 4851 int N; 4852 4853 if (userId == UserHandle.USER_ALL && name == null) { 4854 Slog.w(TAG, "Can't force stop all processes of all users, that is insane!"); 4855 } 4856 4857 if (appId < 0 && name != null) { 4858 try { 4859 appId = UserHandle.getAppId( 4860 AppGlobals.getPackageManager().getPackageUid(name, 0)); 4861 } catch (RemoteException e) { 4862 } 4863 } 4864 4865 if (doit) { 4866 if (name != null) { 4867 Slog.i(TAG, "Force stopping " + name + " appid=" + appId 4868 + " user=" + userId + ": " + reason); 4869 } else { 4870 Slog.i(TAG, "Force stopping u" + userId + ": " + reason); 4871 } 4872 4873 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 4874 for (int ip=pmap.size()-1; ip>=0; ip--) { 4875 SparseArray<Long> ba = pmap.valueAt(ip); 4876 for (i=ba.size()-1; i>=0; i--) { 4877 boolean remove = false; 4878 final int entUid = ba.keyAt(i); 4879 if (name != null) { 4880 if (userId == UserHandle.USER_ALL) { 4881 if (UserHandle.getAppId(entUid) == appId) { 4882 remove = true; 4883 } 4884 } else { 4885 if (entUid == UserHandle.getUid(userId, appId)) { 4886 remove = true; 4887 } 4888 } 4889 } else if (UserHandle.getUserId(entUid) == userId) { 4890 remove = true; 4891 } 4892 if (remove) { 4893 ba.removeAt(i); 4894 } 4895 } 4896 if (ba.size() == 0) { 4897 pmap.removeAt(ip); 4898 } 4899 } 4900 } 4901 4902 boolean didSomething = killPackageProcessesLocked(name, appId, userId, 4903 -100, callerWillRestart, true, doit, evenPersistent, 4904 name == null ? ("stop user " + userId) : ("stop " + name)); 4905 4906 if (mStackSupervisor.forceStopPackageLocked(name, doit, evenPersistent, userId)) { 4907 if (!doit) { 4908 return true; 4909 } 4910 didSomething = true; 4911 } 4912 4913 if (mServices.forceStopLocked(name, userId, evenPersistent, doit)) { 4914 if (!doit) { 4915 return true; 4916 } 4917 didSomething = true; 4918 } 4919 4920 if (name == null) { 4921 // Remove all sticky broadcasts from this user. 4922 mStickyBroadcasts.remove(userId); 4923 } 4924 4925 ArrayList<ContentProviderRecord> providers = new ArrayList<ContentProviderRecord>(); 4926 if (mProviderMap.collectForceStopProviders(name, appId, doit, evenPersistent, 4927 userId, providers)) { 4928 if (!doit) { 4929 return true; 4930 } 4931 didSomething = true; 4932 } 4933 N = providers.size(); 4934 for (i=0; i<N; i++) { 4935 removeDyingProviderLocked(null, providers.get(i), true); 4936 } 4937 4938 // Remove transient permissions granted from/to this package/user 4939 removeUriPermissionsForPackageLocked(name, userId, false); 4940 4941 if (name == null || uninstalling) { 4942 // Remove pending intents. For now we only do this when force 4943 // stopping users, because we have some problems when doing this 4944 // for packages -- app widgets are not currently cleaned up for 4945 // such packages, so they can be left with bad pending intents. 4946 if (mIntentSenderRecords.size() > 0) { 4947 Iterator<WeakReference<PendingIntentRecord>> it 4948 = mIntentSenderRecords.values().iterator(); 4949 while (it.hasNext()) { 4950 WeakReference<PendingIntentRecord> wpir = it.next(); 4951 if (wpir == null) { 4952 it.remove(); 4953 continue; 4954 } 4955 PendingIntentRecord pir = wpir.get(); 4956 if (pir == null) { 4957 it.remove(); 4958 continue; 4959 } 4960 if (name == null) { 4961 // Stopping user, remove all objects for the user. 4962 if (pir.key.userId != userId) { 4963 // Not the same user, skip it. 4964 continue; 4965 } 4966 } else { 4967 if (UserHandle.getAppId(pir.uid) != appId) { 4968 // Different app id, skip it. 4969 continue; 4970 } 4971 if (userId != UserHandle.USER_ALL && pir.key.userId != userId) { 4972 // Different user, skip it. 4973 continue; 4974 } 4975 if (!pir.key.packageName.equals(name)) { 4976 // Different package, skip it. 4977 continue; 4978 } 4979 } 4980 if (!doit) { 4981 return true; 4982 } 4983 didSomething = true; 4984 it.remove(); 4985 pir.canceled = true; 4986 if (pir.key.activity != null) { 4987 pir.key.activity.pendingResults.remove(pir.ref); 4988 } 4989 } 4990 } 4991 } 4992 4993 if (doit) { 4994 if (purgeCache && name != null) { 4995 AttributeCache ac = AttributeCache.instance(); 4996 if (ac != null) { 4997 ac.removePackage(name); 4998 } 4999 } 5000 if (mBooted) { 5001 mStackSupervisor.resumeTopActivitiesLocked(); 5002 mStackSupervisor.scheduleIdleLocked(); 5003 } 5004 } 5005 5006 return didSomething; 5007 } 5008 5009 private final boolean removeProcessLocked(ProcessRecord app, 5010 boolean callerWillRestart, boolean allowRestart, String reason) { 5011 final String name = app.processName; 5012 final int uid = app.uid; 5013 if (DEBUG_PROCESSES) Slog.d( 5014 TAG, "Force removing proc " + app.toShortString() + " (" + name 5015 + "/" + uid + ")"); 5016 5017 mProcessNames.remove(name, uid); 5018 mIsolatedProcesses.remove(app.uid); 5019 if (mHeavyWeightProcess == app) { 5020 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5021 mHeavyWeightProcess.userId, 0)); 5022 mHeavyWeightProcess = null; 5023 } 5024 boolean needRestart = false; 5025 if (app.pid > 0 && app.pid != MY_PID) { 5026 int pid = app.pid; 5027 synchronized (mPidsSelfLocked) { 5028 mPidsSelfLocked.remove(pid); 5029 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5030 } 5031 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_PROC_FINISH, 5032 app.processName, app.info.uid); 5033 if (app.isolated) { 5034 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5035 } 5036 killUnneededProcessLocked(app, reason); 5037 handleAppDiedLocked(app, true, allowRestart); 5038 removeLruProcessLocked(app); 5039 5040 if (app.persistent && !app.isolated) { 5041 if (!callerWillRestart) { 5042 addAppLocked(app.info, false, null /* ABI override */); 5043 } else { 5044 needRestart = true; 5045 } 5046 } 5047 } else { 5048 mRemovedProcesses.add(app); 5049 } 5050 5051 return needRestart; 5052 } 5053 5054 private final void processStartTimedOutLocked(ProcessRecord app) { 5055 final int pid = app.pid; 5056 boolean gone = false; 5057 synchronized (mPidsSelfLocked) { 5058 ProcessRecord knownApp = mPidsSelfLocked.get(pid); 5059 if (knownApp != null && knownApp.thread == null) { 5060 mPidsSelfLocked.remove(pid); 5061 gone = true; 5062 } 5063 } 5064 5065 if (gone) { 5066 Slog.w(TAG, "Process " + app + " failed to attach"); 5067 EventLog.writeEvent(EventLogTags.AM_PROCESS_START_TIMEOUT, app.userId, 5068 pid, app.uid, app.processName); 5069 mProcessNames.remove(app.processName, app.uid); 5070 mIsolatedProcesses.remove(app.uid); 5071 if (mHeavyWeightProcess == app) { 5072 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5073 mHeavyWeightProcess.userId, 0)); 5074 mHeavyWeightProcess = null; 5075 } 5076 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_PROC_FINISH, 5077 app.processName, app.info.uid); 5078 if (app.isolated) { 5079 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5080 } 5081 // Take care of any launching providers waiting for this process. 5082 checkAppInLaunchingProvidersLocked(app, true); 5083 // Take care of any services that are waiting for the process. 5084 mServices.processStartTimedOutLocked(app); 5085 killUnneededProcessLocked(app, "start timeout"); 5086 if (mBackupTarget != null && mBackupTarget.app.pid == pid) { 5087 Slog.w(TAG, "Unattached app died before backup, skipping"); 5088 try { 5089 IBackupManager bm = IBackupManager.Stub.asInterface( 5090 ServiceManager.getService(Context.BACKUP_SERVICE)); 5091 bm.agentDisconnected(app.info.packageName); 5092 } catch (RemoteException e) { 5093 // Can't happen; the backup manager is local 5094 } 5095 } 5096 if (isPendingBroadcastProcessLocked(pid)) { 5097 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 5098 skipPendingBroadcastLocked(pid); 5099 } 5100 } else { 5101 Slog.w(TAG, "Spurious process start timeout - pid not known for " + app); 5102 } 5103 } 5104 5105 private final boolean attachApplicationLocked(IApplicationThread thread, 5106 int pid) { 5107 5108 // Find the application record that is being attached... either via 5109 // the pid if we are running in multiple processes, or just pull the 5110 // next app record if we are emulating process with anonymous threads. 5111 ProcessRecord app; 5112 if (pid != MY_PID && pid >= 0) { 5113 synchronized (mPidsSelfLocked) { 5114 app = mPidsSelfLocked.get(pid); 5115 } 5116 } else { 5117 app = null; 5118 } 5119 5120 if (app == null) { 5121 Slog.w(TAG, "No pending application record for pid " + pid 5122 + " (IApplicationThread " + thread + "); dropping process"); 5123 EventLog.writeEvent(EventLogTags.AM_DROP_PROCESS, pid); 5124 if (pid > 0 && pid != MY_PID) { 5125 Process.killProcessQuiet(pid); 5126 } else { 5127 try { 5128 thread.scheduleExit(); 5129 } catch (Exception e) { 5130 // Ignore exceptions. 5131 } 5132 } 5133 return false; 5134 } 5135 5136 // If this application record is still attached to a previous 5137 // process, clean it up now. 5138 if (app.thread != null) { 5139 handleAppDiedLocked(app, true, true); 5140 } 5141 5142 // Tell the process all about itself. 5143 5144 if (localLOGV) Slog.v( 5145 TAG, "Binding process pid " + pid + " to record " + app); 5146 5147 final String processName = app.processName; 5148 try { 5149 AppDeathRecipient adr = new AppDeathRecipient( 5150 app, pid, thread); 5151 thread.asBinder().linkToDeath(adr, 0); 5152 app.deathRecipient = adr; 5153 } catch (RemoteException e) { 5154 app.resetPackageList(mProcessStats); 5155 startProcessLocked(app, "link fail", processName, null /* ABI override */); 5156 return false; 5157 } 5158 5159 EventLog.writeEvent(EventLogTags.AM_PROC_BOUND, app.userId, app.pid, app.processName); 5160 5161 app.makeActive(thread, mProcessStats); 5162 app.curAdj = app.setAdj = -100; 5163 app.curSchedGroup = app.setSchedGroup = Process.THREAD_GROUP_DEFAULT; 5164 app.forcingToForeground = null; 5165 updateProcessForegroundLocked(app, false, false); 5166 app.hasShownUi = false; 5167 app.debugging = false; 5168 app.cached = false; 5169 5170 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5171 5172 boolean normalMode = mProcessesReady || isAllowedWhileBooting(app.info); 5173 List<ProviderInfo> providers = normalMode ? generateApplicationProvidersLocked(app) : null; 5174 5175 if (!normalMode) { 5176 Slog.i(TAG, "Launching preboot mode app: " + app); 5177 } 5178 5179 if (localLOGV) Slog.v( 5180 TAG, "New app record " + app 5181 + " thread=" + thread.asBinder() + " pid=" + pid); 5182 try { 5183 int testMode = IApplicationThread.DEBUG_OFF; 5184 if (mDebugApp != null && mDebugApp.equals(processName)) { 5185 testMode = mWaitForDebugger 5186 ? IApplicationThread.DEBUG_WAIT 5187 : IApplicationThread.DEBUG_ON; 5188 app.debugging = true; 5189 if (mDebugTransient) { 5190 mDebugApp = mOrigDebugApp; 5191 mWaitForDebugger = mOrigWaitForDebugger; 5192 } 5193 } 5194 String profileFile = app.instrumentationProfileFile; 5195 ParcelFileDescriptor profileFd = null; 5196 boolean profileAutoStop = false; 5197 if (mProfileApp != null && mProfileApp.equals(processName)) { 5198 mProfileProc = app; 5199 profileFile = mProfileFile; 5200 profileFd = mProfileFd; 5201 profileAutoStop = mAutoStopProfiler; 5202 } 5203 boolean enableOpenGlTrace = false; 5204 if (mOpenGlTraceApp != null && mOpenGlTraceApp.equals(processName)) { 5205 enableOpenGlTrace = true; 5206 mOpenGlTraceApp = null; 5207 } 5208 5209 // If the app is being launched for restore or full backup, set it up specially 5210 boolean isRestrictedBackupMode = false; 5211 if (mBackupTarget != null && mBackupAppName.equals(processName)) { 5212 isRestrictedBackupMode = (mBackupTarget.backupMode == BackupRecord.RESTORE) 5213 || (mBackupTarget.backupMode == BackupRecord.RESTORE_FULL) 5214 || (mBackupTarget.backupMode == BackupRecord.BACKUP_FULL); 5215 } 5216 5217 ensurePackageDexOpt(app.instrumentationInfo != null 5218 ? app.instrumentationInfo.packageName 5219 : app.info.packageName); 5220 if (app.instrumentationClass != null) { 5221 ensurePackageDexOpt(app.instrumentationClass.getPackageName()); 5222 } 5223 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Binding proc " 5224 + processName + " with config " + mConfiguration); 5225 ApplicationInfo appInfo = app.instrumentationInfo != null 5226 ? app.instrumentationInfo : app.info; 5227 app.compat = compatibilityInfoForPackageLocked(appInfo); 5228 if (profileFd != null) { 5229 profileFd = profileFd.dup(); 5230 } 5231 thread.bindApplication(processName, appInfo, providers, 5232 app.instrumentationClass, profileFile, profileFd, profileAutoStop, 5233 app.instrumentationArguments, app.instrumentationWatcher, 5234 app.instrumentationUiAutomationConnection, testMode, enableOpenGlTrace, 5235 isRestrictedBackupMode || !normalMode, app.persistent, 5236 new Configuration(mConfiguration), app.compat, getCommonServicesLocked(), 5237 mCoreSettingsObserver.getCoreSettingsLocked()); 5238 updateLruProcessLocked(app, false, null); 5239 app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis(); 5240 } catch (Exception e) { 5241 // todo: Yikes! What should we do? For now we will try to 5242 // start another process, but that could easily get us in 5243 // an infinite loop of restarting processes... 5244 Slog.w(TAG, "Exception thrown during bind!", e); 5245 5246 app.resetPackageList(mProcessStats); 5247 app.unlinkDeathRecipient(); 5248 startProcessLocked(app, "bind fail", processName, null /* ABI override */); 5249 return false; 5250 } 5251 5252 // Remove this record from the list of starting applications. 5253 mPersistentStartingProcesses.remove(app); 5254 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 5255 "Attach application locked removing on hold: " + app); 5256 mProcessesOnHold.remove(app); 5257 5258 boolean badApp = false; 5259 boolean didSomething = false; 5260 5261 // See if the top visible activity is waiting to run in this process... 5262 if (normalMode) { 5263 try { 5264 if (mStackSupervisor.attachApplicationLocked(app)) { 5265 didSomething = true; 5266 } 5267 } catch (Exception e) { 5268 badApp = true; 5269 } 5270 } 5271 5272 // Find any services that should be running in this process... 5273 if (!badApp) { 5274 try { 5275 didSomething |= mServices.attachApplicationLocked(app, processName); 5276 } catch (Exception e) { 5277 badApp = true; 5278 } 5279 } 5280 5281 // Check if a next-broadcast receiver is in this process... 5282 if (!badApp && isPendingBroadcastProcessLocked(pid)) { 5283 try { 5284 didSomething |= sendPendingBroadcastsLocked(app); 5285 } catch (Exception e) { 5286 // If the app died trying to launch the receiver we declare it 'bad' 5287 badApp = true; 5288 } 5289 } 5290 5291 // Check whether the next backup agent is in this process... 5292 if (!badApp && mBackupTarget != null && mBackupTarget.appInfo.uid == app.uid) { 5293 if (DEBUG_BACKUP) Slog.v(TAG, "New app is backup target, launching agent for " + app); 5294 ensurePackageDexOpt(mBackupTarget.appInfo.packageName); 5295 try { 5296 thread.scheduleCreateBackupAgent(mBackupTarget.appInfo, 5297 compatibilityInfoForPackageLocked(mBackupTarget.appInfo), 5298 mBackupTarget.backupMode); 5299 } catch (Exception e) { 5300 Slog.w(TAG, "Exception scheduling backup agent creation: "); 5301 e.printStackTrace(); 5302 } 5303 } 5304 5305 if (badApp) { 5306 // todo: Also need to kill application to deal with all 5307 // kinds of exceptions. 5308 handleAppDiedLocked(app, false, true); 5309 return false; 5310 } 5311 5312 if (!didSomething) { 5313 updateOomAdjLocked(); 5314 } 5315 5316 return true; 5317 } 5318 5319 @Override 5320 public final void attachApplication(IApplicationThread thread) { 5321 synchronized (this) { 5322 int callingPid = Binder.getCallingPid(); 5323 final long origId = Binder.clearCallingIdentity(); 5324 attachApplicationLocked(thread, callingPid); 5325 Binder.restoreCallingIdentity(origId); 5326 } 5327 } 5328 5329 @Override 5330 public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) { 5331 final long origId = Binder.clearCallingIdentity(); 5332 synchronized (this) { 5333 ActivityStack stack = ActivityRecord.getStackLocked(token); 5334 if (stack != null) { 5335 ActivityRecord r = 5336 mStackSupervisor.activityIdleInternalLocked(token, false, config); 5337 if (stopProfiling) { 5338 if ((mProfileProc == r.app) && (mProfileFd != null)) { 5339 try { 5340 mProfileFd.close(); 5341 } catch (IOException e) { 5342 } 5343 clearProfilerLocked(); 5344 } 5345 } 5346 } 5347 } 5348 Binder.restoreCallingIdentity(origId); 5349 } 5350 5351 void enableScreenAfterBoot() { 5352 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN, 5353 SystemClock.uptimeMillis()); 5354 mWindowManager.enableScreenAfterBoot(); 5355 5356 synchronized (this) { 5357 updateEventDispatchingLocked(); 5358 } 5359 } 5360 5361 @Override 5362 public void showBootMessage(final CharSequence msg, final boolean always) { 5363 enforceNotIsolatedCaller("showBootMessage"); 5364 mWindowManager.showBootMessage(msg, always); 5365 } 5366 5367 @Override 5368 public void dismissKeyguardOnNextActivity() { 5369 enforceNotIsolatedCaller("dismissKeyguardOnNextActivity"); 5370 final long token = Binder.clearCallingIdentity(); 5371 try { 5372 synchronized (this) { 5373 if (DEBUG_LOCKSCREEN) logLockScreen(""); 5374 if (mLockScreenShown) { 5375 mLockScreenShown = false; 5376 comeOutOfSleepIfNeededLocked(); 5377 } 5378 mStackSupervisor.setDismissKeyguard(true); 5379 } 5380 } finally { 5381 Binder.restoreCallingIdentity(token); 5382 } 5383 } 5384 5385 final void finishBooting() { 5386 // Register receivers to handle package update events 5387 mPackageMonitor.register(mContext, Looper.getMainLooper(), false); 5388 5389 synchronized (this) { 5390 // Ensure that any processes we had put on hold are now started 5391 // up. 5392 final int NP = mProcessesOnHold.size(); 5393 if (NP > 0) { 5394 ArrayList<ProcessRecord> procs = 5395 new ArrayList<ProcessRecord>(mProcessesOnHold); 5396 for (int ip=0; ip<NP; ip++) { 5397 if (DEBUG_PROCESSES) Slog.v(TAG, "Starting process on hold: " 5398 + procs.get(ip)); 5399 startProcessLocked(procs.get(ip), "on-hold", null, null /* ABI override */); 5400 } 5401 } 5402 5403 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 5404 // Start looking for apps that are abusing wake locks. 5405 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 5406 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 5407 // Tell anyone interested that we are done booting! 5408 SystemProperties.set("sys.boot_completed", "1"); 5409 SystemProperties.set("dev.bootcomplete", "1"); 5410 for (int i=0; i<mStartedUsers.size(); i++) { 5411 UserStartedState uss = mStartedUsers.valueAt(i); 5412 if (uss.mState == UserStartedState.STATE_BOOTING) { 5413 uss.mState = UserStartedState.STATE_RUNNING; 5414 final int userId = mStartedUsers.keyAt(i); 5415 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 5416 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 5417 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 5418 broadcastIntentLocked(null, null, intent, null, 5419 new IIntentReceiver.Stub() { 5420 @Override 5421 public void performReceive(Intent intent, int resultCode, 5422 String data, Bundle extras, boolean ordered, 5423 boolean sticky, int sendingUser) { 5424 synchronized (ActivityManagerService.this) { 5425 requestPssAllProcsLocked(SystemClock.uptimeMillis(), 5426 true, false); 5427 } 5428 } 5429 }, 5430 0, null, null, 5431 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, 5432 AppOpsManager.OP_NONE, true, false, MY_PID, Process.SYSTEM_UID, 5433 userId); 5434 } 5435 } 5436 scheduleStartProfilesLocked(); 5437 } 5438 } 5439 } 5440 5441 final void ensureBootCompleted() { 5442 boolean booting; 5443 boolean enableScreen; 5444 synchronized (this) { 5445 booting = mBooting; 5446 mBooting = false; 5447 enableScreen = !mBooted; 5448 mBooted = true; 5449 } 5450 5451 if (booting) { 5452 finishBooting(); 5453 } 5454 5455 if (enableScreen) { 5456 enableScreenAfterBoot(); 5457 } 5458 } 5459 5460 @Override 5461 public final void activityResumed(IBinder token) { 5462 final long origId = Binder.clearCallingIdentity(); 5463 synchronized(this) { 5464 ActivityStack stack = ActivityRecord.getStackLocked(token); 5465 if (stack != null) { 5466 ActivityRecord.activityResumedLocked(token); 5467 } 5468 } 5469 Binder.restoreCallingIdentity(origId); 5470 } 5471 5472 @Override 5473 public final void activityPaused(IBinder token, PersistableBundle persistentState) { 5474 final long origId = Binder.clearCallingIdentity(); 5475 synchronized(this) { 5476 ActivityStack stack = ActivityRecord.getStackLocked(token); 5477 if (stack != null) { 5478 stack.activityPausedLocked(token, false, persistentState); 5479 } 5480 } 5481 Binder.restoreCallingIdentity(origId); 5482 } 5483 5484 @Override 5485 public final void activityStopped(IBinder token, Bundle icicle, 5486 PersistableBundle persistentState, CharSequence description) { 5487 if (localLOGV) Slog.v(TAG, "Activity stopped: token=" + token); 5488 5489 // Refuse possible leaked file descriptors 5490 if (icicle != null && icicle.hasFileDescriptors()) { 5491 throw new IllegalArgumentException("File descriptors passed in Bundle"); 5492 } 5493 5494 final long origId = Binder.clearCallingIdentity(); 5495 5496 synchronized (this) { 5497 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5498 if (r != null) { 5499 r.task.stack.activityStoppedLocked(r, icicle, persistentState, description); 5500 } 5501 } 5502 5503 trimApplications(); 5504 5505 Binder.restoreCallingIdentity(origId); 5506 } 5507 5508 @Override 5509 public final void activityDestroyed(IBinder token) { 5510 if (DEBUG_SWITCH) Slog.v(TAG, "ACTIVITY DESTROYED: " + token); 5511 synchronized (this) { 5512 ActivityStack stack = ActivityRecord.getStackLocked(token); 5513 if (stack != null) { 5514 stack.activityDestroyedLocked(token); 5515 } 5516 } 5517 } 5518 5519 @Override 5520 public String getCallingPackage(IBinder token) { 5521 synchronized (this) { 5522 ActivityRecord r = getCallingRecordLocked(token); 5523 return r != null ? r.info.packageName : null; 5524 } 5525 } 5526 5527 @Override 5528 public ComponentName getCallingActivity(IBinder token) { 5529 synchronized (this) { 5530 ActivityRecord r = getCallingRecordLocked(token); 5531 return r != null ? r.intent.getComponent() : null; 5532 } 5533 } 5534 5535 private ActivityRecord getCallingRecordLocked(IBinder token) { 5536 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5537 if (r == null) { 5538 return null; 5539 } 5540 return r.resultTo; 5541 } 5542 5543 @Override 5544 public ComponentName getActivityClassForToken(IBinder token) { 5545 synchronized(this) { 5546 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5547 if (r == null) { 5548 return null; 5549 } 5550 return r.intent.getComponent(); 5551 } 5552 } 5553 5554 @Override 5555 public String getPackageForToken(IBinder token) { 5556 synchronized(this) { 5557 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5558 if (r == null) { 5559 return null; 5560 } 5561 return r.packageName; 5562 } 5563 } 5564 5565 @Override 5566 public IIntentSender getIntentSender(int type, 5567 String packageName, IBinder token, String resultWho, 5568 int requestCode, Intent[] intents, String[] resolvedTypes, 5569 int flags, Bundle options, int userId) { 5570 enforceNotIsolatedCaller("getIntentSender"); 5571 // Refuse possible leaked file descriptors 5572 if (intents != null) { 5573 if (intents.length < 1) { 5574 throw new IllegalArgumentException("Intents array length must be >= 1"); 5575 } 5576 for (int i=0; i<intents.length; i++) { 5577 Intent intent = intents[i]; 5578 if (intent != null) { 5579 if (intent.hasFileDescriptors()) { 5580 throw new IllegalArgumentException("File descriptors passed in Intent"); 5581 } 5582 if (type == ActivityManager.INTENT_SENDER_BROADCAST && 5583 (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 5584 throw new IllegalArgumentException( 5585 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 5586 } 5587 intents[i] = new Intent(intent); 5588 } 5589 } 5590 if (resolvedTypes != null && resolvedTypes.length != intents.length) { 5591 throw new IllegalArgumentException( 5592 "Intent array length does not match resolvedTypes length"); 5593 } 5594 } 5595 if (options != null) { 5596 if (options.hasFileDescriptors()) { 5597 throw new IllegalArgumentException("File descriptors passed in options"); 5598 } 5599 } 5600 5601 synchronized(this) { 5602 int callingUid = Binder.getCallingUid(); 5603 int origUserId = userId; 5604 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 5605 type == ActivityManager.INTENT_SENDER_BROADCAST, false, 5606 "getIntentSender", null); 5607 if (origUserId == UserHandle.USER_CURRENT) { 5608 // We don't want to evaluate this until the pending intent is 5609 // actually executed. However, we do want to always do the 5610 // security checking for it above. 5611 userId = UserHandle.USER_CURRENT; 5612 } 5613 try { 5614 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 5615 int uid = AppGlobals.getPackageManager() 5616 .getPackageUid(packageName, UserHandle.getUserId(callingUid)); 5617 if (!UserHandle.isSameApp(callingUid, uid)) { 5618 String msg = "Permission Denial: getIntentSender() from pid=" 5619 + Binder.getCallingPid() 5620 + ", uid=" + Binder.getCallingUid() 5621 + ", (need uid=" + uid + ")" 5622 + " is not allowed to send as package " + packageName; 5623 Slog.w(TAG, msg); 5624 throw new SecurityException(msg); 5625 } 5626 } 5627 5628 return getIntentSenderLocked(type, packageName, callingUid, userId, 5629 token, resultWho, requestCode, intents, resolvedTypes, flags, options); 5630 5631 } catch (RemoteException e) { 5632 throw new SecurityException(e); 5633 } 5634 } 5635 } 5636 5637 IIntentSender getIntentSenderLocked(int type, String packageName, 5638 int callingUid, int userId, IBinder token, String resultWho, 5639 int requestCode, Intent[] intents, String[] resolvedTypes, int flags, 5640 Bundle options) { 5641 if (DEBUG_MU) 5642 Slog.v(TAG_MU, "getIntentSenderLocked(): uid=" + callingUid); 5643 ActivityRecord activity = null; 5644 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 5645 activity = ActivityRecord.isInStackLocked(token); 5646 if (activity == null) { 5647 return null; 5648 } 5649 if (activity.finishing) { 5650 return null; 5651 } 5652 } 5653 5654 final boolean noCreate = (flags&PendingIntent.FLAG_NO_CREATE) != 0; 5655 final boolean cancelCurrent = (flags&PendingIntent.FLAG_CANCEL_CURRENT) != 0; 5656 final boolean updateCurrent = (flags&PendingIntent.FLAG_UPDATE_CURRENT) != 0; 5657 flags &= ~(PendingIntent.FLAG_NO_CREATE|PendingIntent.FLAG_CANCEL_CURRENT 5658 |PendingIntent.FLAG_UPDATE_CURRENT); 5659 5660 PendingIntentRecord.Key key = new PendingIntentRecord.Key( 5661 type, packageName, activity, resultWho, 5662 requestCode, intents, resolvedTypes, flags, options, userId); 5663 WeakReference<PendingIntentRecord> ref; 5664 ref = mIntentSenderRecords.get(key); 5665 PendingIntentRecord rec = ref != null ? ref.get() : null; 5666 if (rec != null) { 5667 if (!cancelCurrent) { 5668 if (updateCurrent) { 5669 if (rec.key.requestIntent != null) { 5670 rec.key.requestIntent.replaceExtras(intents != null ? 5671 intents[intents.length - 1] : null); 5672 } 5673 if (intents != null) { 5674 intents[intents.length-1] = rec.key.requestIntent; 5675 rec.key.allIntents = intents; 5676 rec.key.allResolvedTypes = resolvedTypes; 5677 } else { 5678 rec.key.allIntents = null; 5679 rec.key.allResolvedTypes = null; 5680 } 5681 } 5682 return rec; 5683 } 5684 rec.canceled = true; 5685 mIntentSenderRecords.remove(key); 5686 } 5687 if (noCreate) { 5688 return rec; 5689 } 5690 rec = new PendingIntentRecord(this, key, callingUid); 5691 mIntentSenderRecords.put(key, rec.ref); 5692 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 5693 if (activity.pendingResults == null) { 5694 activity.pendingResults 5695 = new HashSet<WeakReference<PendingIntentRecord>>(); 5696 } 5697 activity.pendingResults.add(rec.ref); 5698 } 5699 return rec; 5700 } 5701 5702 @Override 5703 public void cancelIntentSender(IIntentSender sender) { 5704 if (!(sender instanceof PendingIntentRecord)) { 5705 return; 5706 } 5707 synchronized(this) { 5708 PendingIntentRecord rec = (PendingIntentRecord)sender; 5709 try { 5710 int uid = AppGlobals.getPackageManager() 5711 .getPackageUid(rec.key.packageName, UserHandle.getCallingUserId()); 5712 if (!UserHandle.isSameApp(uid, Binder.getCallingUid())) { 5713 String msg = "Permission Denial: cancelIntentSender() from pid=" 5714 + Binder.getCallingPid() 5715 + ", uid=" + Binder.getCallingUid() 5716 + " is not allowed to cancel packges " 5717 + rec.key.packageName; 5718 Slog.w(TAG, msg); 5719 throw new SecurityException(msg); 5720 } 5721 } catch (RemoteException e) { 5722 throw new SecurityException(e); 5723 } 5724 cancelIntentSenderLocked(rec, true); 5725 } 5726 } 5727 5728 void cancelIntentSenderLocked(PendingIntentRecord rec, boolean cleanActivity) { 5729 rec.canceled = true; 5730 mIntentSenderRecords.remove(rec.key); 5731 if (cleanActivity && rec.key.activity != null) { 5732 rec.key.activity.pendingResults.remove(rec.ref); 5733 } 5734 } 5735 5736 @Override 5737 public String getPackageForIntentSender(IIntentSender pendingResult) { 5738 if (!(pendingResult instanceof PendingIntentRecord)) { 5739 return null; 5740 } 5741 try { 5742 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5743 return res.key.packageName; 5744 } catch (ClassCastException e) { 5745 } 5746 return null; 5747 } 5748 5749 @Override 5750 public int getUidForIntentSender(IIntentSender sender) { 5751 if (sender instanceof PendingIntentRecord) { 5752 try { 5753 PendingIntentRecord res = (PendingIntentRecord)sender; 5754 return res.uid; 5755 } catch (ClassCastException e) { 5756 } 5757 } 5758 return -1; 5759 } 5760 5761 @Override 5762 public boolean isIntentSenderTargetedToPackage(IIntentSender pendingResult) { 5763 if (!(pendingResult instanceof PendingIntentRecord)) { 5764 return false; 5765 } 5766 try { 5767 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5768 if (res.key.allIntents == null) { 5769 return false; 5770 } 5771 for (int i=0; i<res.key.allIntents.length; i++) { 5772 Intent intent = res.key.allIntents[i]; 5773 if (intent.getPackage() != null && intent.getComponent() != null) { 5774 return false; 5775 } 5776 } 5777 return true; 5778 } catch (ClassCastException e) { 5779 } 5780 return false; 5781 } 5782 5783 @Override 5784 public boolean isIntentSenderAnActivity(IIntentSender pendingResult) { 5785 if (!(pendingResult instanceof PendingIntentRecord)) { 5786 return false; 5787 } 5788 try { 5789 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5790 if (res.key.type == ActivityManager.INTENT_SENDER_ACTIVITY) { 5791 return true; 5792 } 5793 return false; 5794 } catch (ClassCastException e) { 5795 } 5796 return false; 5797 } 5798 5799 @Override 5800 public Intent getIntentForIntentSender(IIntentSender pendingResult) { 5801 if (!(pendingResult instanceof PendingIntentRecord)) { 5802 return null; 5803 } 5804 try { 5805 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5806 return res.key.requestIntent != null ? new Intent(res.key.requestIntent) : null; 5807 } catch (ClassCastException e) { 5808 } 5809 return null; 5810 } 5811 5812 @Override 5813 public String getTagForIntentSender(IIntentSender pendingResult, String prefix) { 5814 if (!(pendingResult instanceof PendingIntentRecord)) { 5815 return null; 5816 } 5817 try { 5818 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5819 Intent intent = res.key.requestIntent; 5820 if (intent != null) { 5821 if (res.lastTag != null && res.lastTagPrefix == prefix && (res.lastTagPrefix == null 5822 || res.lastTagPrefix.equals(prefix))) { 5823 return res.lastTag; 5824 } 5825 res.lastTagPrefix = prefix; 5826 StringBuilder sb = new StringBuilder(128); 5827 if (prefix != null) { 5828 sb.append(prefix); 5829 } 5830 if (intent.getAction() != null) { 5831 sb.append(intent.getAction()); 5832 } else if (intent.getComponent() != null) { 5833 intent.getComponent().appendShortString(sb); 5834 } else { 5835 sb.append("?"); 5836 } 5837 return res.lastTag = sb.toString(); 5838 } 5839 } catch (ClassCastException e) { 5840 } 5841 return null; 5842 } 5843 5844 @Override 5845 public void setProcessLimit(int max) { 5846 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 5847 "setProcessLimit()"); 5848 synchronized (this) { 5849 mProcessLimit = max < 0 ? ProcessList.MAX_CACHED_APPS : max; 5850 mProcessLimitOverride = max; 5851 } 5852 trimApplications(); 5853 } 5854 5855 @Override 5856 public int getProcessLimit() { 5857 synchronized (this) { 5858 return mProcessLimitOverride; 5859 } 5860 } 5861 5862 void foregroundTokenDied(ForegroundToken token) { 5863 synchronized (ActivityManagerService.this) { 5864 synchronized (mPidsSelfLocked) { 5865 ForegroundToken cur 5866 = mForegroundProcesses.get(token.pid); 5867 if (cur != token) { 5868 return; 5869 } 5870 mForegroundProcesses.remove(token.pid); 5871 ProcessRecord pr = mPidsSelfLocked.get(token.pid); 5872 if (pr == null) { 5873 return; 5874 } 5875 pr.forcingToForeground = null; 5876 updateProcessForegroundLocked(pr, false, false); 5877 } 5878 updateOomAdjLocked(); 5879 } 5880 } 5881 5882 @Override 5883 public void setProcessForeground(IBinder token, int pid, boolean isForeground) { 5884 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 5885 "setProcessForeground()"); 5886 synchronized(this) { 5887 boolean changed = false; 5888 5889 synchronized (mPidsSelfLocked) { 5890 ProcessRecord pr = mPidsSelfLocked.get(pid); 5891 if (pr == null && isForeground) { 5892 Slog.w(TAG, "setProcessForeground called on unknown pid: " + pid); 5893 return; 5894 } 5895 ForegroundToken oldToken = mForegroundProcesses.get(pid); 5896 if (oldToken != null) { 5897 oldToken.token.unlinkToDeath(oldToken, 0); 5898 mForegroundProcesses.remove(pid); 5899 if (pr != null) { 5900 pr.forcingToForeground = null; 5901 } 5902 changed = true; 5903 } 5904 if (isForeground && token != null) { 5905 ForegroundToken newToken = new ForegroundToken() { 5906 @Override 5907 public void binderDied() { 5908 foregroundTokenDied(this); 5909 } 5910 }; 5911 newToken.pid = pid; 5912 newToken.token = token; 5913 try { 5914 token.linkToDeath(newToken, 0); 5915 mForegroundProcesses.put(pid, newToken); 5916 pr.forcingToForeground = token; 5917 changed = true; 5918 } catch (RemoteException e) { 5919 // If the process died while doing this, we will later 5920 // do the cleanup with the process death link. 5921 } 5922 } 5923 } 5924 5925 if (changed) { 5926 updateOomAdjLocked(); 5927 } 5928 } 5929 } 5930 5931 // ========================================================= 5932 // PERMISSIONS 5933 // ========================================================= 5934 5935 static class PermissionController extends IPermissionController.Stub { 5936 ActivityManagerService mActivityManagerService; 5937 PermissionController(ActivityManagerService activityManagerService) { 5938 mActivityManagerService = activityManagerService; 5939 } 5940 5941 @Override 5942 public boolean checkPermission(String permission, int pid, int uid) { 5943 return mActivityManagerService.checkPermission(permission, pid, 5944 uid) == PackageManager.PERMISSION_GRANTED; 5945 } 5946 } 5947 5948 class IntentFirewallInterface implements IntentFirewall.AMSInterface { 5949 @Override 5950 public int checkComponentPermission(String permission, int pid, int uid, 5951 int owningUid, boolean exported) { 5952 return ActivityManagerService.this.checkComponentPermission(permission, pid, uid, 5953 owningUid, exported); 5954 } 5955 5956 @Override 5957 public Object getAMSLock() { 5958 return ActivityManagerService.this; 5959 } 5960 } 5961 5962 /** 5963 * This can be called with or without the global lock held. 5964 */ 5965 int checkComponentPermission(String permission, int pid, int uid, 5966 int owningUid, boolean exported) { 5967 // We might be performing an operation on behalf of an indirect binder 5968 // invocation, e.g. via {@link #openContentUri}. Check and adjust the 5969 // client identity accordingly before proceeding. 5970 Identity tlsIdentity = sCallerIdentity.get(); 5971 if (tlsIdentity != null) { 5972 Slog.d(TAG, "checkComponentPermission() adjusting {pid,uid} to {" 5973 + tlsIdentity.pid + "," + tlsIdentity.uid + "}"); 5974 uid = tlsIdentity.uid; 5975 pid = tlsIdentity.pid; 5976 } 5977 5978 if (pid == MY_PID) { 5979 return PackageManager.PERMISSION_GRANTED; 5980 } 5981 5982 return ActivityManager.checkComponentPermission(permission, uid, 5983 owningUid, exported); 5984 } 5985 5986 /** 5987 * As the only public entry point for permissions checking, this method 5988 * can enforce the semantic that requesting a check on a null global 5989 * permission is automatically denied. (Internally a null permission 5990 * string is used when calling {@link #checkComponentPermission} in cases 5991 * when only uid-based security is needed.) 5992 * 5993 * This can be called with or without the global lock held. 5994 */ 5995 @Override 5996 public int checkPermission(String permission, int pid, int uid) { 5997 if (permission == null) { 5998 return PackageManager.PERMISSION_DENIED; 5999 } 6000 return checkComponentPermission(permission, pid, UserHandle.getAppId(uid), -1, true); 6001 } 6002 6003 /** 6004 * Binder IPC calls go through the public entry point. 6005 * This can be called with or without the global lock held. 6006 */ 6007 int checkCallingPermission(String permission) { 6008 return checkPermission(permission, 6009 Binder.getCallingPid(), 6010 UserHandle.getAppId(Binder.getCallingUid())); 6011 } 6012 6013 /** 6014 * This can be called with or without the global lock held. 6015 */ 6016 void enforceCallingPermission(String permission, String func) { 6017 if (checkCallingPermission(permission) 6018 == PackageManager.PERMISSION_GRANTED) { 6019 return; 6020 } 6021 6022 String msg = "Permission Denial: " + func + " from pid=" 6023 + Binder.getCallingPid() 6024 + ", uid=" + Binder.getCallingUid() 6025 + " requires " + permission; 6026 Slog.w(TAG, msg); 6027 throw new SecurityException(msg); 6028 } 6029 6030 /** 6031 * Determine if UID is holding permissions required to access {@link Uri} in 6032 * the given {@link ProviderInfo}. Final permission checking is always done 6033 * in {@link ContentProvider}. 6034 */ 6035 private final boolean checkHoldingPermissionsLocked( 6036 IPackageManager pm, ProviderInfo pi, GrantUri grantUri, int uid, final int modeFlags) { 6037 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6038 "checkHoldingPermissionsLocked: uri=" + grantUri + " uid=" + uid); 6039 if (UserHandle.getUserId(uid) != grantUri.sourceUserId) { 6040 return false; 6041 } 6042 6043 if (pi.applicationInfo.uid == uid) { 6044 return true; 6045 } else if (!pi.exported) { 6046 return false; 6047 } 6048 6049 boolean readMet = (modeFlags & Intent.FLAG_GRANT_READ_URI_PERMISSION) == 0; 6050 boolean writeMet = (modeFlags & Intent.FLAG_GRANT_WRITE_URI_PERMISSION) == 0; 6051 try { 6052 // check if target holds top-level <provider> permissions 6053 if (!readMet && pi.readPermission != null 6054 && (pm.checkUidPermission(pi.readPermission, uid) == PERMISSION_GRANTED)) { 6055 readMet = true; 6056 } 6057 if (!writeMet && pi.writePermission != null 6058 && (pm.checkUidPermission(pi.writePermission, uid) == PERMISSION_GRANTED)) { 6059 writeMet = true; 6060 } 6061 6062 // track if unprotected read/write is allowed; any denied 6063 // <path-permission> below removes this ability 6064 boolean allowDefaultRead = pi.readPermission == null; 6065 boolean allowDefaultWrite = pi.writePermission == null; 6066 6067 // check if target holds any <path-permission> that match uri 6068 final PathPermission[] pps = pi.pathPermissions; 6069 if (pps != null) { 6070 final String path = grantUri.uri.getPath(); 6071 int i = pps.length; 6072 while (i > 0 && (!readMet || !writeMet)) { 6073 i--; 6074 PathPermission pp = pps[i]; 6075 if (pp.match(path)) { 6076 if (!readMet) { 6077 final String pprperm = pp.getReadPermission(); 6078 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking read perm for " 6079 + pprperm + " for " + pp.getPath() 6080 + ": match=" + pp.match(path) 6081 + " check=" + pm.checkUidPermission(pprperm, uid)); 6082 if (pprperm != null) { 6083 if (pm.checkUidPermission(pprperm, uid) == PERMISSION_GRANTED) { 6084 readMet = true; 6085 } else { 6086 allowDefaultRead = false; 6087 } 6088 } 6089 } 6090 if (!writeMet) { 6091 final String ppwperm = pp.getWritePermission(); 6092 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking write perm " 6093 + ppwperm + " for " + pp.getPath() 6094 + ": match=" + pp.match(path) 6095 + " check=" + pm.checkUidPermission(ppwperm, uid)); 6096 if (ppwperm != null) { 6097 if (pm.checkUidPermission(ppwperm, uid) == PERMISSION_GRANTED) { 6098 writeMet = true; 6099 } else { 6100 allowDefaultWrite = false; 6101 } 6102 } 6103 } 6104 } 6105 } 6106 } 6107 6108 // grant unprotected <provider> read/write, if not blocked by 6109 // <path-permission> above 6110 if (allowDefaultRead) readMet = true; 6111 if (allowDefaultWrite) writeMet = true; 6112 6113 } catch (RemoteException e) { 6114 return false; 6115 } 6116 6117 return readMet && writeMet; 6118 } 6119 6120 private ProviderInfo getProviderInfoLocked(String authority, int userHandle) { 6121 ProviderInfo pi = null; 6122 ContentProviderRecord cpr = mProviderMap.getProviderByName(authority, userHandle); 6123 if (cpr != null) { 6124 pi = cpr.info; 6125 } else { 6126 try { 6127 pi = AppGlobals.getPackageManager().resolveContentProvider( 6128 authority, PackageManager.GET_URI_PERMISSION_PATTERNS, userHandle); 6129 } catch (RemoteException ex) { 6130 } 6131 } 6132 return pi; 6133 } 6134 6135 private UriPermission findUriPermissionLocked(int targetUid, GrantUri grantUri) { 6136 final ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6137 if (targetUris != null) { 6138 return targetUris.get(grantUri); 6139 } 6140 return null; 6141 } 6142 6143 private UriPermission findOrCreateUriPermissionLocked(String sourcePkg, 6144 String targetPkg, int targetUid, GrantUri grantUri) { 6145 ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6146 if (targetUris == null) { 6147 targetUris = Maps.newArrayMap(); 6148 mGrantedUriPermissions.put(targetUid, targetUris); 6149 } 6150 6151 UriPermission perm = targetUris.get(grantUri); 6152 if (perm == null) { 6153 perm = new UriPermission(sourcePkg, targetPkg, targetUid, grantUri); 6154 targetUris.put(grantUri, perm); 6155 } 6156 6157 return perm; 6158 } 6159 6160 private final boolean checkUriPermissionLocked(GrantUri grantUri, int uid, 6161 final int modeFlags) { 6162 final boolean persistable = (modeFlags & Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION) != 0; 6163 final int minStrength = persistable ? UriPermission.STRENGTH_PERSISTABLE 6164 : UriPermission.STRENGTH_OWNED; 6165 6166 // Root gets to do everything. 6167 if (uid == 0) { 6168 return true; 6169 } 6170 6171 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 6172 if (perms == null) return false; 6173 6174 // First look for exact match 6175 final UriPermission exactPerm = perms.get(grantUri); 6176 if (exactPerm != null && exactPerm.getStrength(modeFlags) >= minStrength) { 6177 return true; 6178 } 6179 6180 // No exact match, look for prefixes 6181 final int N = perms.size(); 6182 for (int i = 0; i < N; i++) { 6183 final UriPermission perm = perms.valueAt(i); 6184 if (perm.uri.prefix && grantUri.uri.isPathPrefixMatch(perm.uri.uri) 6185 && perm.getStrength(modeFlags) >= minStrength) { 6186 return true; 6187 } 6188 } 6189 6190 return false; 6191 } 6192 6193 @Override 6194 public int checkUriPermission(Uri uri, int pid, int uid, 6195 final int modeFlags, int userId) { 6196 enforceNotIsolatedCaller("checkUriPermission"); 6197 6198 // Another redirected-binder-call permissions check as in 6199 // {@link checkComponentPermission}. 6200 Identity tlsIdentity = sCallerIdentity.get(); 6201 if (tlsIdentity != null) { 6202 uid = tlsIdentity.uid; 6203 pid = tlsIdentity.pid; 6204 } 6205 6206 // Our own process gets to do everything. 6207 if (pid == MY_PID) { 6208 return PackageManager.PERMISSION_GRANTED; 6209 } 6210 synchronized (this) { 6211 return checkUriPermissionLocked(new GrantUri(userId, uri, false), uid, modeFlags) 6212 ? PackageManager.PERMISSION_GRANTED 6213 : PackageManager.PERMISSION_DENIED; 6214 } 6215 } 6216 6217 /** 6218 * Check if the targetPkg can be granted permission to access uri by 6219 * the callingUid using the given modeFlags. Throws a security exception 6220 * if callingUid is not allowed to do this. Returns the uid of the target 6221 * if the URI permission grant should be performed; returns -1 if it is not 6222 * needed (for example targetPkg already has permission to access the URI). 6223 * If you already know the uid of the target, you can supply it in 6224 * lastTargetUid else set that to -1. 6225 */ 6226 int checkGrantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 6227 final int modeFlags, int lastTargetUid) { 6228 if (!Intent.isAccessUriMode(modeFlags)) { 6229 return -1; 6230 } 6231 6232 if (targetPkg != null) { 6233 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6234 "Checking grant " + targetPkg + " permission to " + grantUri); 6235 } 6236 6237 final IPackageManager pm = AppGlobals.getPackageManager(); 6238 6239 // If this is not a content: uri, we can't do anything with it. 6240 if (!ContentResolver.SCHEME_CONTENT.equals(grantUri.uri.getScheme())) { 6241 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6242 "Can't grant URI permission for non-content URI: " + grantUri); 6243 return -1; 6244 } 6245 6246 final String authority = grantUri.uri.getAuthority(); 6247 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6248 if (pi == null) { 6249 Slog.w(TAG, "No content provider found for permission check: " + 6250 grantUri.uri.toSafeString()); 6251 return -1; 6252 } 6253 6254 int targetUid = lastTargetUid; 6255 if (targetUid < 0 && targetPkg != null) { 6256 try { 6257 targetUid = pm.getPackageUid(targetPkg, UserHandle.getUserId(callingUid)); 6258 if (targetUid < 0) { 6259 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6260 "Can't grant URI permission no uid for: " + targetPkg); 6261 return -1; 6262 } 6263 } catch (RemoteException ex) { 6264 return -1; 6265 } 6266 } 6267 6268 if (targetUid >= 0) { 6269 // First... does the target actually need this permission? 6270 if (checkHoldingPermissionsLocked(pm, pi, grantUri, targetUid, modeFlags)) { 6271 // No need to grant the target this permission. 6272 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6273 "Target " + targetPkg + " already has full permission to " + grantUri); 6274 return -1; 6275 } 6276 } else { 6277 // First... there is no target package, so can anyone access it? 6278 boolean allowed = pi.exported; 6279 if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) { 6280 if (pi.readPermission != null) { 6281 allowed = false; 6282 } 6283 } 6284 if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) { 6285 if (pi.writePermission != null) { 6286 allowed = false; 6287 } 6288 } 6289 if (allowed) { 6290 return -1; 6291 } 6292 } 6293 6294 // Second... is the provider allowing granting of URI permissions? 6295 if (!pi.grantUriPermissions) { 6296 throw new SecurityException("Provider " + pi.packageName 6297 + "/" + pi.name 6298 + " does not allow granting of Uri permissions (uri " 6299 + grantUri + ")"); 6300 } 6301 if (pi.uriPermissionPatterns != null) { 6302 final int N = pi.uriPermissionPatterns.length; 6303 boolean allowed = false; 6304 for (int i=0; i<N; i++) { 6305 if (pi.uriPermissionPatterns[i] != null 6306 && pi.uriPermissionPatterns[i].match(grantUri.uri.getPath())) { 6307 allowed = true; 6308 break; 6309 } 6310 } 6311 if (!allowed) { 6312 throw new SecurityException("Provider " + pi.packageName 6313 + "/" + pi.name 6314 + " does not allow granting of permission to path of Uri " 6315 + grantUri); 6316 } 6317 } 6318 6319 // Third... does the caller itself have permission to access 6320 // this uri? 6321 if (UserHandle.getAppId(callingUid) != Process.SYSTEM_UID) { 6322 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 6323 // Require they hold a strong enough Uri permission 6324 if (!checkUriPermissionLocked(grantUri, callingUid, modeFlags)) { 6325 throw new SecurityException("Uid " + callingUid 6326 + " does not have permission to uri " + grantUri); 6327 } 6328 } 6329 } 6330 return targetUid; 6331 } 6332 6333 @Override 6334 public int checkGrantUriPermission(int callingUid, String targetPkg, Uri uri, 6335 final int modeFlags, int userId) { 6336 enforceNotIsolatedCaller("checkGrantUriPermission"); 6337 synchronized(this) { 6338 return checkGrantUriPermissionLocked(callingUid, targetPkg, 6339 new GrantUri(userId, uri, false), modeFlags, -1); 6340 } 6341 } 6342 6343 void grantUriPermissionUncheckedLocked(int targetUid, String targetPkg, GrantUri grantUri, 6344 final int modeFlags, UriPermissionOwner owner) { 6345 if (!Intent.isAccessUriMode(modeFlags)) { 6346 return; 6347 } 6348 6349 // So here we are: the caller has the assumed permission 6350 // to the uri, and the target doesn't. Let's now give this to 6351 // the target. 6352 6353 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6354 "Granting " + targetPkg + "/" + targetUid + " permission to " + grantUri); 6355 6356 final String authority = grantUri.uri.getAuthority(); 6357 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6358 if (pi == null) { 6359 Slog.w(TAG, "No content provider found for grant: " + grantUri.toSafeString()); 6360 return; 6361 } 6362 6363 if ((modeFlags & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0) { 6364 grantUri.prefix = true; 6365 } 6366 final UriPermission perm = findOrCreateUriPermissionLocked( 6367 pi.packageName, targetPkg, targetUid, grantUri); 6368 perm.grantModes(modeFlags, owner); 6369 } 6370 6371 void grantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 6372 final int modeFlags, UriPermissionOwner owner) { 6373 if (targetPkg == null) { 6374 throw new NullPointerException("targetPkg"); 6375 } 6376 6377 int targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, modeFlags, 6378 -1); 6379 if (targetUid < 0) { 6380 return; 6381 } 6382 6383 grantUriPermissionUncheckedLocked(targetUid, targetPkg, grantUri, modeFlags, 6384 owner); 6385 } 6386 6387 static class NeededUriGrants extends ArrayList<GrantUri> { 6388 final String targetPkg; 6389 final int targetUid; 6390 final int flags; 6391 6392 NeededUriGrants(String targetPkg, int targetUid, int flags) { 6393 this.targetPkg = targetPkg; 6394 this.targetUid = targetUid; 6395 this.flags = flags; 6396 } 6397 } 6398 6399 /** 6400 * Like checkGrantUriPermissionLocked, but takes an Intent. 6401 */ 6402 NeededUriGrants checkGrantUriPermissionFromIntentLocked(int callingUid, 6403 String targetPkg, Intent intent, int mode, NeededUriGrants needed, int targetUserId) { 6404 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6405 "Checking URI perm to data=" + (intent != null ? intent.getData() : null) 6406 + " clip=" + (intent != null ? intent.getClipData() : null) 6407 + " from " + intent + "; flags=0x" 6408 + Integer.toHexString(intent != null ? intent.getFlags() : 0)); 6409 6410 if (targetPkg == null) { 6411 throw new NullPointerException("targetPkg"); 6412 } 6413 6414 if (intent == null) { 6415 return null; 6416 } 6417 Uri data = intent.getData(); 6418 ClipData clip = intent.getClipData(); 6419 if (data == null && clip == null) { 6420 return null; 6421 } 6422 final IPackageManager pm = AppGlobals.getPackageManager(); 6423 int targetUid; 6424 if (needed != null) { 6425 targetUid = needed.targetUid; 6426 } else { 6427 try { 6428 targetUid = pm.getPackageUid(targetPkg, targetUserId); 6429 } catch (RemoteException ex) { 6430 return null; 6431 } 6432 if (targetUid < 0) { 6433 if (DEBUG_URI_PERMISSION) { 6434 Slog.v(TAG, "Can't grant URI permission no uid for: " + targetPkg 6435 + " on user " + targetUserId); 6436 } 6437 return null; 6438 } 6439 } 6440 if (data != null) { 6441 GrantUri grantUri = GrantUri.resolve(UserHandle.getUserId(callingUid), data); 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 } 6451 if (clip != null) { 6452 for (int i=0; i<clip.getItemCount(); i++) { 6453 Uri uri = clip.getItemAt(i).getUri(); 6454 if (uri != null) { 6455 GrantUri grantUri = GrantUri.resolve(UserHandle.getUserId(callingUid), uri); 6456 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 6457 targetUid); 6458 if (targetUid > 0) { 6459 if (needed == null) { 6460 needed = new NeededUriGrants(targetPkg, targetUid, mode); 6461 } 6462 needed.add(grantUri); 6463 } 6464 } else { 6465 Intent clipIntent = clip.getItemAt(i).getIntent(); 6466 if (clipIntent != null) { 6467 NeededUriGrants newNeeded = checkGrantUriPermissionFromIntentLocked( 6468 callingUid, targetPkg, clipIntent, mode, needed, targetUserId); 6469 if (newNeeded != null) { 6470 needed = newNeeded; 6471 } 6472 } 6473 } 6474 } 6475 } 6476 6477 return needed; 6478 } 6479 6480 /** 6481 * Like grantUriPermissionUncheckedLocked, but takes an Intent. 6482 */ 6483 void grantUriPermissionUncheckedFromIntentLocked(NeededUriGrants needed, 6484 UriPermissionOwner owner) { 6485 if (needed != null) { 6486 for (int i=0; i<needed.size(); i++) { 6487 GrantUri grantUri = needed.get(i); 6488 grantUriPermissionUncheckedLocked(needed.targetUid, needed.targetPkg, 6489 grantUri, needed.flags, owner); 6490 } 6491 } 6492 } 6493 6494 void grantUriPermissionFromIntentLocked(int callingUid, 6495 String targetPkg, Intent intent, UriPermissionOwner owner, int targetUserId) { 6496 NeededUriGrants needed = checkGrantUriPermissionFromIntentLocked(callingUid, targetPkg, 6497 intent, intent != null ? intent.getFlags() : 0, null, targetUserId); 6498 if (needed == null) { 6499 return; 6500 } 6501 6502 grantUriPermissionUncheckedFromIntentLocked(needed, owner); 6503 } 6504 6505 @Override 6506 public void grantUriPermission(IApplicationThread caller, String targetPkg, Uri uri, 6507 final int modeFlags, int userId) { 6508 enforceNotIsolatedCaller("grantUriPermission"); 6509 GrantUri grantUri = new GrantUri(userId, uri, false); 6510 synchronized(this) { 6511 final ProcessRecord r = getRecordForAppLocked(caller); 6512 if (r == null) { 6513 throw new SecurityException("Unable to find app for caller " 6514 + caller 6515 + " when granting permission to uri " + grantUri); 6516 } 6517 if (targetPkg == null) { 6518 throw new IllegalArgumentException("null target"); 6519 } 6520 if (grantUri == null) { 6521 throw new IllegalArgumentException("null uri"); 6522 } 6523 6524 Preconditions.checkFlagsArgument(modeFlags, Intent.FLAG_GRANT_READ_URI_PERMISSION 6525 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION 6526 | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION 6527 | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION); 6528 6529 grantUriPermissionLocked(r.uid, targetPkg, grantUri, modeFlags, null); 6530 } 6531 } 6532 6533 void removeUriPermissionIfNeededLocked(UriPermission perm) { 6534 if (perm.modeFlags == 0) { 6535 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 6536 perm.targetUid); 6537 if (perms != null) { 6538 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6539 "Removing " + perm.targetUid + " permission to " + perm.uri); 6540 6541 perms.remove(perm.uri); 6542 if (perms.isEmpty()) { 6543 mGrantedUriPermissions.remove(perm.targetUid); 6544 } 6545 } 6546 } 6547 } 6548 6549 private void revokeUriPermissionLocked(int callingUid, GrantUri grantUri, final int modeFlags) { 6550 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Revoking all granted permissions to " + grantUri); 6551 6552 final IPackageManager pm = AppGlobals.getPackageManager(); 6553 final String authority = grantUri.uri.getAuthority(); 6554 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6555 if (pi == null) { 6556 Slog.w(TAG, "No content provider found for permission revoke: " 6557 + grantUri.toSafeString()); 6558 return; 6559 } 6560 6561 // Does the caller have this permission on the URI? 6562 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 6563 // Right now, if you are not the original owner of the permission, 6564 // you are not allowed to revoke it. 6565 //if (!checkUriPermissionLocked(uri, callingUid, modeFlags)) { 6566 throw new SecurityException("Uid " + callingUid 6567 + " does not have permission to uri " + grantUri); 6568 //} 6569 } 6570 6571 boolean persistChanged = false; 6572 6573 // Go through all of the permissions and remove any that match. 6574 int N = mGrantedUriPermissions.size(); 6575 for (int i = 0; i < N; i++) { 6576 final int targetUid = mGrantedUriPermissions.keyAt(i); 6577 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6578 6579 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 6580 final UriPermission perm = it.next(); 6581 if (perm.uri.sourceUserId == grantUri.sourceUserId 6582 && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) { 6583 if (DEBUG_URI_PERMISSION) 6584 Slog.v(TAG, 6585 "Revoking " + perm.targetUid + " permission to " + perm.uri); 6586 persistChanged |= perm.revokeModes( 6587 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 6588 if (perm.modeFlags == 0) { 6589 it.remove(); 6590 } 6591 } 6592 } 6593 6594 if (perms.isEmpty()) { 6595 mGrantedUriPermissions.remove(targetUid); 6596 N--; 6597 i--; 6598 } 6599 } 6600 6601 if (persistChanged) { 6602 schedulePersistUriGrants(); 6603 } 6604 } 6605 6606 @Override 6607 public void revokeUriPermission(IApplicationThread caller, Uri uri, final int modeFlags, 6608 int userId) { 6609 enforceNotIsolatedCaller("revokeUriPermission"); 6610 synchronized(this) { 6611 final ProcessRecord r = getRecordForAppLocked(caller); 6612 if (r == null) { 6613 throw new SecurityException("Unable to find app for caller " 6614 + caller 6615 + " when revoking permission to uri " + uri); 6616 } 6617 if (uri == null) { 6618 Slog.w(TAG, "revokeUriPermission: null uri"); 6619 return; 6620 } 6621 6622 if (!Intent.isAccessUriMode(modeFlags)) { 6623 return; 6624 } 6625 6626 final IPackageManager pm = AppGlobals.getPackageManager(); 6627 final String authority = uri.getAuthority(); 6628 final ProviderInfo pi = getProviderInfoLocked(authority, userId); 6629 if (pi == null) { 6630 Slog.w(TAG, "No content provider found for permission revoke: " 6631 + uri.toSafeString()); 6632 return; 6633 } 6634 6635 revokeUriPermissionLocked(r.uid, new GrantUri(userId, uri, false), modeFlags); 6636 } 6637 } 6638 6639 /** 6640 * Remove any {@link UriPermission} granted <em>from</em> or <em>to</em> the 6641 * given package. 6642 * 6643 * @param packageName Package name to match, or {@code null} to apply to all 6644 * packages. 6645 * @param userHandle User to match, or {@link UserHandle#USER_ALL} to apply 6646 * to all users. 6647 * @param persistable If persistable grants should be removed. 6648 */ 6649 private void removeUriPermissionsForPackageLocked( 6650 String packageName, int userHandle, boolean persistable) { 6651 if (userHandle == UserHandle.USER_ALL && packageName == null) { 6652 throw new IllegalArgumentException("Must narrow by either package or user"); 6653 } 6654 6655 boolean persistChanged = false; 6656 6657 int N = mGrantedUriPermissions.size(); 6658 for (int i = 0; i < N; i++) { 6659 final int targetUid = mGrantedUriPermissions.keyAt(i); 6660 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6661 6662 // Only inspect grants matching user 6663 if (userHandle == UserHandle.USER_ALL 6664 || userHandle == UserHandle.getUserId(targetUid)) { 6665 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 6666 final UriPermission perm = it.next(); 6667 6668 // Only inspect grants matching package 6669 if (packageName == null || perm.sourcePkg.equals(packageName) 6670 || perm.targetPkg.equals(packageName)) { 6671 persistChanged |= perm.revokeModes( 6672 persistable ? ~0 : ~Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 6673 6674 // Only remove when no modes remain; any persisted grants 6675 // will keep this alive. 6676 if (perm.modeFlags == 0) { 6677 it.remove(); 6678 } 6679 } 6680 } 6681 6682 if (perms.isEmpty()) { 6683 mGrantedUriPermissions.remove(targetUid); 6684 N--; 6685 i--; 6686 } 6687 } 6688 } 6689 6690 if (persistChanged) { 6691 schedulePersistUriGrants(); 6692 } 6693 } 6694 6695 @Override 6696 public IBinder newUriPermissionOwner(String name) { 6697 enforceNotIsolatedCaller("newUriPermissionOwner"); 6698 synchronized(this) { 6699 UriPermissionOwner owner = new UriPermissionOwner(this, name); 6700 return owner.getExternalTokenLocked(); 6701 } 6702 } 6703 6704 @Override 6705 public void grantUriPermissionFromOwner(IBinder token, int fromUid, String targetPkg, Uri uri, 6706 final int modeFlags, int userId) { 6707 synchronized(this) { 6708 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 6709 if (owner == null) { 6710 throw new IllegalArgumentException("Unknown owner: " + token); 6711 } 6712 if (fromUid != Binder.getCallingUid()) { 6713 if (Binder.getCallingUid() != Process.myUid()) { 6714 // Only system code can grant URI permissions on behalf 6715 // of other users. 6716 throw new SecurityException("nice try"); 6717 } 6718 } 6719 if (targetPkg == null) { 6720 throw new IllegalArgumentException("null target"); 6721 } 6722 if (uri == null) { 6723 throw new IllegalArgumentException("null uri"); 6724 } 6725 6726 grantUriPermissionLocked(fromUid, targetPkg, new GrantUri(userId, uri, false), 6727 modeFlags, owner); 6728 } 6729 } 6730 6731 @Override 6732 public void revokeUriPermissionFromOwner(IBinder token, Uri uri, int mode, int userId) { 6733 synchronized(this) { 6734 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 6735 if (owner == null) { 6736 throw new IllegalArgumentException("Unknown owner: " + token); 6737 } 6738 6739 if (uri == null) { 6740 owner.removeUriPermissionsLocked(mode); 6741 } else { 6742 owner.removeUriPermissionLocked(new GrantUri(userId, uri, false), mode); 6743 } 6744 } 6745 } 6746 6747 private void schedulePersistUriGrants() { 6748 if (!mHandler.hasMessages(PERSIST_URI_GRANTS_MSG)) { 6749 mHandler.sendMessageDelayed(mHandler.obtainMessage(PERSIST_URI_GRANTS_MSG), 6750 10 * DateUtils.SECOND_IN_MILLIS); 6751 } 6752 } 6753 6754 private void writeGrantedUriPermissions() { 6755 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "writeGrantedUriPermissions()"); 6756 6757 // Snapshot permissions so we can persist without lock 6758 ArrayList<UriPermission.Snapshot> persist = Lists.newArrayList(); 6759 synchronized (this) { 6760 final int size = mGrantedUriPermissions.size(); 6761 for (int i = 0; i < size; i++) { 6762 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6763 for (UriPermission perm : perms.values()) { 6764 if (perm.persistedModeFlags != 0) { 6765 persist.add(perm.snapshot()); 6766 } 6767 } 6768 } 6769 } 6770 6771 FileOutputStream fos = null; 6772 try { 6773 fos = mGrantFile.startWrite(); 6774 6775 XmlSerializer out = new FastXmlSerializer(); 6776 out.setOutput(fos, "utf-8"); 6777 out.startDocument(null, true); 6778 out.startTag(null, TAG_URI_GRANTS); 6779 for (UriPermission.Snapshot perm : persist) { 6780 out.startTag(null, TAG_URI_GRANT); 6781 writeIntAttribute(out, ATTR_SOURCE_USER_ID, perm.uri.sourceUserId); 6782 writeIntAttribute(out, ATTR_TARGET_USER_ID, perm.targetUserId); 6783 out.attribute(null, ATTR_SOURCE_PKG, perm.sourcePkg); 6784 out.attribute(null, ATTR_TARGET_PKG, perm.targetPkg); 6785 out.attribute(null, ATTR_URI, String.valueOf(perm.uri.uri)); 6786 writeBooleanAttribute(out, ATTR_PREFIX, perm.uri.prefix); 6787 writeIntAttribute(out, ATTR_MODE_FLAGS, perm.persistedModeFlags); 6788 writeLongAttribute(out, ATTR_CREATED_TIME, perm.persistedCreateTime); 6789 out.endTag(null, TAG_URI_GRANT); 6790 } 6791 out.endTag(null, TAG_URI_GRANTS); 6792 out.endDocument(); 6793 6794 mGrantFile.finishWrite(fos); 6795 } catch (IOException e) { 6796 if (fos != null) { 6797 mGrantFile.failWrite(fos); 6798 } 6799 } 6800 } 6801 6802 private void readGrantedUriPermissionsLocked() { 6803 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "readGrantedUriPermissions()"); 6804 6805 final long now = System.currentTimeMillis(); 6806 6807 FileInputStream fis = null; 6808 try { 6809 fis = mGrantFile.openRead(); 6810 final XmlPullParser in = Xml.newPullParser(); 6811 in.setInput(fis, null); 6812 6813 int type; 6814 while ((type = in.next()) != END_DOCUMENT) { 6815 final String tag = in.getName(); 6816 if (type == START_TAG) { 6817 if (TAG_URI_GRANT.equals(tag)) { 6818 final int sourceUserId; 6819 final int targetUserId; 6820 final int userHandle = readIntAttribute(in, 6821 ATTR_USER_HANDLE, UserHandle.USER_NULL); 6822 if (userHandle != UserHandle.USER_NULL) { 6823 // For backwards compatibility. 6824 sourceUserId = userHandle; 6825 targetUserId = userHandle; 6826 } else { 6827 sourceUserId = readIntAttribute(in, ATTR_SOURCE_USER_ID); 6828 targetUserId = readIntAttribute(in, ATTR_TARGET_USER_ID); 6829 } 6830 final String sourcePkg = in.getAttributeValue(null, ATTR_SOURCE_PKG); 6831 final String targetPkg = in.getAttributeValue(null, ATTR_TARGET_PKG); 6832 final Uri uri = Uri.parse(in.getAttributeValue(null, ATTR_URI)); 6833 final boolean prefix = readBooleanAttribute(in, ATTR_PREFIX); 6834 final int modeFlags = readIntAttribute(in, ATTR_MODE_FLAGS); 6835 final long createdTime = readLongAttribute(in, ATTR_CREATED_TIME, now); 6836 6837 // Sanity check that provider still belongs to source package 6838 final ProviderInfo pi = getProviderInfoLocked( 6839 uri.getAuthority(), sourceUserId); 6840 if (pi != null && sourcePkg.equals(pi.packageName)) { 6841 int targetUid = -1; 6842 try { 6843 targetUid = AppGlobals.getPackageManager() 6844 .getPackageUid(targetPkg, targetUserId); 6845 } catch (RemoteException e) { 6846 } 6847 if (targetUid != -1) { 6848 final UriPermission perm = findOrCreateUriPermissionLocked( 6849 sourcePkg, targetPkg, targetUid, 6850 new GrantUri(sourceUserId, uri, prefix)); 6851 perm.initPersistedModes(modeFlags, createdTime); 6852 } 6853 } else { 6854 Slog.w(TAG, "Persisted grant for " + uri + " had source " + sourcePkg 6855 + " but instead found " + pi); 6856 } 6857 } 6858 } 6859 } 6860 } catch (FileNotFoundException e) { 6861 // Missing grants is okay 6862 } catch (IOException e) { 6863 Log.wtf(TAG, "Failed reading Uri grants", e); 6864 } catch (XmlPullParserException e) { 6865 Log.wtf(TAG, "Failed reading Uri grants", e); 6866 } finally { 6867 IoUtils.closeQuietly(fis); 6868 } 6869 } 6870 6871 @Override 6872 public void takePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 6873 enforceNotIsolatedCaller("takePersistableUriPermission"); 6874 6875 Preconditions.checkFlagsArgument(modeFlags, 6876 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 6877 6878 synchronized (this) { 6879 final int callingUid = Binder.getCallingUid(); 6880 boolean persistChanged = false; 6881 GrantUri grantUri = new GrantUri(userId, uri, false); 6882 6883 UriPermission exactPerm = findUriPermissionLocked(callingUid, 6884 new GrantUri(userId, uri, false)); 6885 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 6886 new GrantUri(userId, uri, true)); 6887 6888 final boolean exactValid = (exactPerm != null) 6889 && ((modeFlags & exactPerm.persistableModeFlags) == modeFlags); 6890 final boolean prefixValid = (prefixPerm != null) 6891 && ((modeFlags & prefixPerm.persistableModeFlags) == modeFlags); 6892 6893 if (!(exactValid || prefixValid)) { 6894 throw new SecurityException("No persistable permission grants found for UID " 6895 + callingUid + " and Uri " + grantUri.toSafeString()); 6896 } 6897 6898 if (exactValid) { 6899 persistChanged |= exactPerm.takePersistableModes(modeFlags); 6900 } 6901 if (prefixValid) { 6902 persistChanged |= prefixPerm.takePersistableModes(modeFlags); 6903 } 6904 6905 persistChanged |= maybePrunePersistedUriGrantsLocked(callingUid); 6906 6907 if (persistChanged) { 6908 schedulePersistUriGrants(); 6909 } 6910 } 6911 } 6912 6913 @Override 6914 public void releasePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 6915 enforceNotIsolatedCaller("releasePersistableUriPermission"); 6916 6917 Preconditions.checkFlagsArgument(modeFlags, 6918 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 6919 6920 synchronized (this) { 6921 final int callingUid = Binder.getCallingUid(); 6922 boolean persistChanged = false; 6923 6924 UriPermission exactPerm = findUriPermissionLocked(callingUid, 6925 new GrantUri(userId, uri, false)); 6926 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 6927 new GrantUri(userId, uri, true)); 6928 if (exactPerm == null && prefixPerm == null) { 6929 throw new SecurityException("No permission grants found for UID " + callingUid 6930 + " and Uri " + uri.toSafeString()); 6931 } 6932 6933 if (exactPerm != null) { 6934 persistChanged |= exactPerm.releasePersistableModes(modeFlags); 6935 removeUriPermissionIfNeededLocked(exactPerm); 6936 } 6937 if (prefixPerm != null) { 6938 persistChanged |= prefixPerm.releasePersistableModes(modeFlags); 6939 removeUriPermissionIfNeededLocked(prefixPerm); 6940 } 6941 6942 if (persistChanged) { 6943 schedulePersistUriGrants(); 6944 } 6945 } 6946 } 6947 6948 /** 6949 * Prune any older {@link UriPermission} for the given UID until outstanding 6950 * persisted grants are below {@link #MAX_PERSISTED_URI_GRANTS}. 6951 * 6952 * @return if any mutations occured that require persisting. 6953 */ 6954 private boolean maybePrunePersistedUriGrantsLocked(int uid) { 6955 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 6956 if (perms == null) return false; 6957 if (perms.size() < MAX_PERSISTED_URI_GRANTS) return false; 6958 6959 final ArrayList<UriPermission> persisted = Lists.newArrayList(); 6960 for (UriPermission perm : perms.values()) { 6961 if (perm.persistedModeFlags != 0) { 6962 persisted.add(perm); 6963 } 6964 } 6965 6966 final int trimCount = persisted.size() - MAX_PERSISTED_URI_GRANTS; 6967 if (trimCount <= 0) return false; 6968 6969 Collections.sort(persisted, new UriPermission.PersistedTimeComparator()); 6970 for (int i = 0; i < trimCount; i++) { 6971 final UriPermission perm = persisted.get(i); 6972 6973 if (DEBUG_URI_PERMISSION) { 6974 Slog.v(TAG, "Trimming grant created at " + perm.persistedCreateTime); 6975 } 6976 6977 perm.releasePersistableModes(~0); 6978 removeUriPermissionIfNeededLocked(perm); 6979 } 6980 6981 return true; 6982 } 6983 6984 @Override 6985 public ParceledListSlice<android.content.UriPermission> getPersistedUriPermissions( 6986 String packageName, boolean incoming) { 6987 enforceNotIsolatedCaller("getPersistedUriPermissions"); 6988 Preconditions.checkNotNull(packageName, "packageName"); 6989 6990 final int callingUid = Binder.getCallingUid(); 6991 final IPackageManager pm = AppGlobals.getPackageManager(); 6992 try { 6993 final int packageUid = pm.getPackageUid(packageName, UserHandle.getUserId(callingUid)); 6994 if (packageUid != callingUid) { 6995 throw new SecurityException( 6996 "Package " + packageName + " does not belong to calling UID " + callingUid); 6997 } 6998 } catch (RemoteException e) { 6999 throw new SecurityException("Failed to verify package name ownership"); 7000 } 7001 7002 final ArrayList<android.content.UriPermission> result = Lists.newArrayList(); 7003 synchronized (this) { 7004 if (incoming) { 7005 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 7006 callingUid); 7007 if (perms == null) { 7008 Slog.w(TAG, "No permission grants found for " + packageName); 7009 } else { 7010 for (UriPermission perm : perms.values()) { 7011 if (packageName.equals(perm.targetPkg) && perm.persistedModeFlags != 0) { 7012 result.add(perm.buildPersistedPublicApiObject()); 7013 } 7014 } 7015 } 7016 } else { 7017 final int size = mGrantedUriPermissions.size(); 7018 for (int i = 0; i < size; i++) { 7019 final ArrayMap<GrantUri, UriPermission> perms = 7020 mGrantedUriPermissions.valueAt(i); 7021 for (UriPermission perm : perms.values()) { 7022 if (packageName.equals(perm.sourcePkg) && perm.persistedModeFlags != 0) { 7023 result.add(perm.buildPersistedPublicApiObject()); 7024 } 7025 } 7026 } 7027 } 7028 } 7029 return new ParceledListSlice<android.content.UriPermission>(result); 7030 } 7031 7032 @Override 7033 public void showWaitingForDebugger(IApplicationThread who, boolean waiting) { 7034 synchronized (this) { 7035 ProcessRecord app = 7036 who != null ? getRecordForAppLocked(who) : null; 7037 if (app == null) return; 7038 7039 Message msg = Message.obtain(); 7040 msg.what = WAIT_FOR_DEBUGGER_MSG; 7041 msg.obj = app; 7042 msg.arg1 = waiting ? 1 : 0; 7043 mHandler.sendMessage(msg); 7044 } 7045 } 7046 7047 @Override 7048 public void getMemoryInfo(ActivityManager.MemoryInfo outInfo) { 7049 final long homeAppMem = mProcessList.getMemLevel(ProcessList.HOME_APP_ADJ); 7050 final long cachedAppMem = mProcessList.getMemLevel(ProcessList.CACHED_APP_MIN_ADJ); 7051 outInfo.availMem = Process.getFreeMemory(); 7052 outInfo.totalMem = Process.getTotalMemory(); 7053 outInfo.threshold = homeAppMem; 7054 outInfo.lowMemory = outInfo.availMem < (homeAppMem + ((cachedAppMem-homeAppMem)/2)); 7055 outInfo.hiddenAppThreshold = cachedAppMem; 7056 outInfo.secondaryServerThreshold = mProcessList.getMemLevel( 7057 ProcessList.SERVICE_ADJ); 7058 outInfo.visibleAppThreshold = mProcessList.getMemLevel( 7059 ProcessList.VISIBLE_APP_ADJ); 7060 outInfo.foregroundAppThreshold = mProcessList.getMemLevel( 7061 ProcessList.FOREGROUND_APP_ADJ); 7062 } 7063 7064 // ========================================================= 7065 // TASK MANAGEMENT 7066 // ========================================================= 7067 7068 @Override 7069 public List<IAppTask> getAppTasks() { 7070 int callingUid = Binder.getCallingUid(); 7071 long ident = Binder.clearCallingIdentity(); 7072 synchronized(this) { 7073 ArrayList<IAppTask> list = new ArrayList<IAppTask>(); 7074 try { 7075 if (localLOGV) Slog.v(TAG, "getAppTasks"); 7076 7077 final int N = mRecentTasks.size(); 7078 for (int i = 0; i < N; i++) { 7079 TaskRecord tr = mRecentTasks.get(i); 7080 // Skip tasks that are not created by the caller 7081 if (tr.creatorUid == callingUid) { 7082 ActivityManager.RecentTaskInfo taskInfo = 7083 createRecentTaskInfoFromTaskRecord(tr); 7084 AppTaskImpl taskImpl = new AppTaskImpl(taskInfo.persistentId, callingUid); 7085 list.add(taskImpl); 7086 } 7087 } 7088 } finally { 7089 Binder.restoreCallingIdentity(ident); 7090 } 7091 return list; 7092 } 7093 } 7094 7095 @Override 7096 public List<RunningTaskInfo> getTasks(int maxNum, int flags) { 7097 final int callingUid = Binder.getCallingUid(); 7098 ArrayList<RunningTaskInfo> list = new ArrayList<RunningTaskInfo>(); 7099 7100 synchronized(this) { 7101 if (localLOGV) Slog.v( 7102 TAG, "getTasks: max=" + maxNum + ", flags=" + flags); 7103 7104 final boolean allowed = checkCallingPermission( 7105 android.Manifest.permission.GET_TASKS) 7106 == PackageManager.PERMISSION_GRANTED; 7107 if (!allowed) { 7108 Slog.w(TAG, "getTasks: caller " + callingUid 7109 + " does not hold GET_TASKS; limiting output"); 7110 } 7111 7112 // TODO: Improve with MRU list from all ActivityStacks. 7113 mStackSupervisor.getTasksLocked(maxNum, list, callingUid, allowed); 7114 } 7115 7116 return list; 7117 } 7118 7119 TaskRecord getMostRecentTask() { 7120 return mRecentTasks.get(0); 7121 } 7122 7123 /** 7124 * Creates a new RecentTaskInfo from a TaskRecord. 7125 */ 7126 private ActivityManager.RecentTaskInfo createRecentTaskInfoFromTaskRecord(TaskRecord tr) { 7127 // Update the task description to reflect any changes in the task stack 7128 tr.updateTaskDescription(); 7129 7130 // Compose the recent task info 7131 ActivityManager.RecentTaskInfo rti 7132 = new ActivityManager.RecentTaskInfo(); 7133 rti.id = tr.mActivities.isEmpty() ? -1 : tr.taskId; 7134 rti.persistentId = tr.taskId; 7135 rti.baseIntent = new Intent(tr.getBaseIntent()); 7136 rti.origActivity = tr.origActivity; 7137 rti.description = tr.lastDescription; 7138 rti.stackId = tr.stack != null ? tr.stack.mStackId : -1; 7139 rti.userId = tr.userId; 7140 rti.taskDescription = new ActivityManager.TaskDescription(tr.lastTaskDescription); 7141 return rti; 7142 } 7143 7144 @Override 7145 public List<ActivityManager.RecentTaskInfo> getRecentTasks(int maxNum, 7146 int flags, int userId) { 7147 final int callingUid = Binder.getCallingUid(); 7148 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 7149 false, true, "getRecentTasks", null); 7150 7151 synchronized (this) { 7152 final boolean allowed = checkCallingPermission( 7153 android.Manifest.permission.GET_TASKS) 7154 == PackageManager.PERMISSION_GRANTED; 7155 if (!allowed) { 7156 Slog.w(TAG, "getRecentTasks: caller " + callingUid 7157 + " does not hold GET_TASKS; limiting output"); 7158 } 7159 final boolean detailed = checkCallingPermission( 7160 android.Manifest.permission.GET_DETAILED_TASKS) 7161 == PackageManager.PERMISSION_GRANTED; 7162 7163 IPackageManager pm = AppGlobals.getPackageManager(); 7164 7165 final int N = mRecentTasks.size(); 7166 ArrayList<ActivityManager.RecentTaskInfo> res 7167 = new ArrayList<ActivityManager.RecentTaskInfo>( 7168 maxNum < N ? maxNum : N); 7169 7170 final Set<Integer> includedUsers; 7171 if ((flags & ActivityManager.RECENT_INCLUDE_PROFILES) != 0) { 7172 includedUsers = getProfileIdsLocked(userId); 7173 } else { 7174 includedUsers = new HashSet<Integer>(); 7175 } 7176 includedUsers.add(Integer.valueOf(userId)); 7177 for (int i=0; i<N && maxNum > 0; i++) { 7178 TaskRecord tr = mRecentTasks.get(i); 7179 // Only add calling user or related users recent tasks 7180 if (!includedUsers.contains(Integer.valueOf(tr.userId))) continue; 7181 7182 // Return the entry if desired by the caller. We always return 7183 // the first entry, because callers always expect this to be the 7184 // foreground app. We may filter others if the caller has 7185 // not supplied RECENT_WITH_EXCLUDED and there is some reason 7186 // we should exclude the entry. 7187 7188 if (i == 0 7189 || ((flags&ActivityManager.RECENT_WITH_EXCLUDED) != 0) 7190 || (tr.intent == null) 7191 || ((tr.intent.getFlags() 7192 &Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS) == 0)) { 7193 if (!allowed) { 7194 // If the caller doesn't have the GET_TASKS permission, then only 7195 // allow them to see a small subset of tasks -- their own and home. 7196 if (!tr.isHomeTask() && tr.creatorUid != callingUid) { 7197 continue; 7198 } 7199 } 7200 7201 ActivityManager.RecentTaskInfo rti = createRecentTaskInfoFromTaskRecord(tr); 7202 if (!detailed) { 7203 rti.baseIntent.replaceExtras((Bundle)null); 7204 } 7205 7206 if ((flags&ActivityManager.RECENT_IGNORE_UNAVAILABLE) != 0) { 7207 // Check whether this activity is currently available. 7208 try { 7209 if (rti.origActivity != null) { 7210 if (pm.getActivityInfo(rti.origActivity, 0, userId) 7211 == null) { 7212 continue; 7213 } 7214 } else if (rti.baseIntent != null) { 7215 if (pm.queryIntentActivities(rti.baseIntent, 7216 null, 0, userId) == null) { 7217 continue; 7218 } 7219 } 7220 } catch (RemoteException e) { 7221 // Will never happen. 7222 } 7223 } 7224 7225 res.add(rti); 7226 maxNum--; 7227 } 7228 } 7229 return res; 7230 } 7231 } 7232 7233 private TaskRecord recentTaskForIdLocked(int id) { 7234 final int N = mRecentTasks.size(); 7235 for (int i=0; i<N; i++) { 7236 TaskRecord tr = mRecentTasks.get(i); 7237 if (tr.taskId == id) { 7238 return tr; 7239 } 7240 } 7241 return null; 7242 } 7243 7244 @Override 7245 public ActivityManager.TaskThumbnails getTaskThumbnails(int id) { 7246 synchronized (this) { 7247 enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER, 7248 "getTaskThumbnails()"); 7249 TaskRecord tr = recentTaskForIdLocked(id); 7250 if (tr != null) { 7251 return tr.getTaskThumbnailsLocked(); 7252 } 7253 } 7254 return null; 7255 } 7256 7257 @Override 7258 public Bitmap getTaskTopThumbnail(int id) { 7259 synchronized (this) { 7260 enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER, 7261 "getTaskTopThumbnail()"); 7262 TaskRecord tr = recentTaskForIdLocked(id); 7263 if (tr != null) { 7264 return tr.getTaskTopThumbnailLocked(); 7265 } 7266 } 7267 return null; 7268 } 7269 7270 @Override 7271 public void setTaskDescription(IBinder token, ActivityManager.TaskDescription td) { 7272 synchronized (this) { 7273 ActivityRecord r = ActivityRecord.isInStackLocked(token); 7274 if (r != null) { 7275 r.taskDescription = td; 7276 r.task.updateTaskDescription(); 7277 } 7278 } 7279 } 7280 7281 @Override 7282 public boolean removeSubTask(int taskId, int subTaskIndex) { 7283 synchronized (this) { 7284 enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, 7285 "removeSubTask()"); 7286 long ident = Binder.clearCallingIdentity(); 7287 try { 7288 TaskRecord tr = recentTaskForIdLocked(taskId); 7289 if (tr != null) { 7290 return tr.removeTaskActivitiesLocked(subTaskIndex, true) != null; 7291 } 7292 return false; 7293 } finally { 7294 Binder.restoreCallingIdentity(ident); 7295 } 7296 } 7297 } 7298 7299 private void killUnneededProcessLocked(ProcessRecord pr, String reason) { 7300 if (!pr.killedByAm) { 7301 Slog.i(TAG, "Killing " + pr.toShortString() + " (adj " + pr.setAdj + "): " + reason); 7302 EventLog.writeEvent(EventLogTags.AM_KILL, pr.userId, pr.pid, 7303 pr.processName, pr.setAdj, reason); 7304 pr.killedByAm = true; 7305 Process.killProcessQuiet(pr.pid); 7306 } 7307 } 7308 7309 private void cleanUpRemovedTaskLocked(TaskRecord tr, int flags) { 7310 tr.disposeThumbnail(); 7311 mRecentTasks.remove(tr); 7312 final boolean killProcesses = (flags&ActivityManager.REMOVE_TASK_KILL_PROCESS) != 0; 7313 Intent baseIntent = new Intent( 7314 tr.intent != null ? tr.intent : tr.affinityIntent); 7315 ComponentName component = baseIntent.getComponent(); 7316 if (component == null) { 7317 Slog.w(TAG, "Now component for base intent of task: " + tr); 7318 return; 7319 } 7320 7321 // Find any running services associated with this app. 7322 mServices.cleanUpRemovedTaskLocked(tr, component, baseIntent); 7323 7324 if (killProcesses) { 7325 // Find any running processes associated with this app. 7326 final String pkg = component.getPackageName(); 7327 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 7328 ArrayMap<String, SparseArray<ProcessRecord>> pmap = mProcessNames.getMap(); 7329 for (int i=0; i<pmap.size(); i++) { 7330 SparseArray<ProcessRecord> uids = pmap.valueAt(i); 7331 for (int j=0; j<uids.size(); j++) { 7332 ProcessRecord proc = uids.valueAt(j); 7333 if (proc.userId != tr.userId) { 7334 continue; 7335 } 7336 if (!proc.pkgList.containsKey(pkg)) { 7337 continue; 7338 } 7339 procs.add(proc); 7340 } 7341 } 7342 7343 // Kill the running processes. 7344 for (int i=0; i<procs.size(); i++) { 7345 ProcessRecord pr = procs.get(i); 7346 if (pr == mHomeProcess) { 7347 // Don't kill the home process along with tasks from the same package. 7348 continue; 7349 } 7350 if (pr.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 7351 killUnneededProcessLocked(pr, "remove task"); 7352 } else { 7353 pr.waitingToKill = "remove task"; 7354 } 7355 } 7356 } 7357 } 7358 7359 /** 7360 * Removes the task with the specified task id. 7361 * 7362 * @param taskId Identifier of the task to be removed. 7363 * @param flags Additional operational flags. May be 0 or 7364 * {@link ActivityManager#REMOVE_TASK_KILL_PROCESS}. 7365 * @return Returns true if the given task was found and removed. 7366 */ 7367 private boolean removeTaskByIdLocked(int taskId, int flags) { 7368 TaskRecord tr = recentTaskForIdLocked(taskId); 7369 if (tr != null) { 7370 tr.removeTaskActivitiesLocked(-1, false); 7371 cleanUpRemovedTaskLocked(tr, flags); 7372 if (tr.isPersistable) { 7373 notifyTaskPersisterLocked(tr, true); 7374 } 7375 return true; 7376 } 7377 return false; 7378 } 7379 7380 @Override 7381 public boolean removeTask(int taskId, int flags) { 7382 synchronized (this) { 7383 enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, 7384 "removeTask()"); 7385 long ident = Binder.clearCallingIdentity(); 7386 try { 7387 return removeTaskByIdLocked(taskId, flags); 7388 } finally { 7389 Binder.restoreCallingIdentity(ident); 7390 } 7391 } 7392 } 7393 7394 /** 7395 * TODO: Add mController hook 7396 */ 7397 @Override 7398 public void moveTaskToFront(int taskId, int flags, Bundle options) { 7399 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7400 "moveTaskToFront()"); 7401 7402 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToFront: moving taskId=" + taskId); 7403 synchronized(this) { 7404 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7405 Binder.getCallingUid(), "Task to front")) { 7406 ActivityOptions.abort(options); 7407 return; 7408 } 7409 final long origId = Binder.clearCallingIdentity(); 7410 try { 7411 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 7412 if (task == null) { 7413 return; 7414 } 7415 if (mStackSupervisor.isLockTaskModeViolation(task)) { 7416 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode"); 7417 return; 7418 } 7419 mStackSupervisor.findTaskToMoveToFrontLocked(task, flags, options); 7420 } finally { 7421 Binder.restoreCallingIdentity(origId); 7422 } 7423 ActivityOptions.abort(options); 7424 } 7425 } 7426 7427 @Override 7428 public void moveTaskToBack(int taskId) { 7429 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7430 "moveTaskToBack()"); 7431 7432 synchronized(this) { 7433 TaskRecord tr = recentTaskForIdLocked(taskId); 7434 if (tr != null) { 7435 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToBack: moving task=" + tr); 7436 ActivityStack stack = tr.stack; 7437 if (stack.mResumedActivity != null && stack.mResumedActivity.task == tr) { 7438 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7439 Binder.getCallingUid(), "Task to back")) { 7440 return; 7441 } 7442 } 7443 final long origId = Binder.clearCallingIdentity(); 7444 try { 7445 stack.moveTaskToBackLocked(taskId, null); 7446 } finally { 7447 Binder.restoreCallingIdentity(origId); 7448 } 7449 } 7450 } 7451 } 7452 7453 /** 7454 * Moves an activity, and all of the other activities within the same task, to the bottom 7455 * of the history stack. The activity's order within the task is unchanged. 7456 * 7457 * @param token A reference to the activity we wish to move 7458 * @param nonRoot If false then this only works if the activity is the root 7459 * of a task; if true it will work for any activity in a task. 7460 * @return Returns true if the move completed, false if not. 7461 */ 7462 @Override 7463 public boolean moveActivityTaskToBack(IBinder token, boolean nonRoot) { 7464 enforceNotIsolatedCaller("moveActivityTaskToBack"); 7465 synchronized(this) { 7466 final long origId = Binder.clearCallingIdentity(); 7467 int taskId = ActivityRecord.getTaskForActivityLocked(token, !nonRoot); 7468 if (taskId >= 0) { 7469 return ActivityRecord.getStackLocked(token).moveTaskToBackLocked(taskId, null); 7470 } 7471 Binder.restoreCallingIdentity(origId); 7472 } 7473 return false; 7474 } 7475 7476 @Override 7477 public void moveTaskBackwards(int task) { 7478 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7479 "moveTaskBackwards()"); 7480 7481 synchronized(this) { 7482 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7483 Binder.getCallingUid(), "Task backwards")) { 7484 return; 7485 } 7486 final long origId = Binder.clearCallingIdentity(); 7487 moveTaskBackwardsLocked(task); 7488 Binder.restoreCallingIdentity(origId); 7489 } 7490 } 7491 7492 private final void moveTaskBackwardsLocked(int task) { 7493 Slog.e(TAG, "moveTaskBackwards not yet implemented!"); 7494 } 7495 7496 @Override 7497 public IBinder getHomeActivityToken() throws RemoteException { 7498 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7499 "getHomeActivityToken()"); 7500 synchronized (this) { 7501 return mStackSupervisor.getHomeActivityToken(); 7502 } 7503 } 7504 7505 @Override 7506 public IActivityContainer createActivityContainer(IBinder parentActivityToken, 7507 IActivityContainerCallback callback) throws RemoteException { 7508 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7509 "createActivityContainer()"); 7510 synchronized (this) { 7511 if (parentActivityToken == null) { 7512 throw new IllegalArgumentException("parent token must not be null"); 7513 } 7514 ActivityRecord r = ActivityRecord.forToken(parentActivityToken); 7515 if (r == null) { 7516 return null; 7517 } 7518 if (callback == null) { 7519 throw new IllegalArgumentException("callback must not be null"); 7520 } 7521 return mStackSupervisor.createActivityContainer(r, callback); 7522 } 7523 } 7524 7525 @Override 7526 public void deleteActivityContainer(IActivityContainer container) throws RemoteException { 7527 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7528 "deleteActivityContainer()"); 7529 synchronized (this) { 7530 mStackSupervisor.deleteActivityContainer(container); 7531 } 7532 } 7533 7534 @Override 7535 public IActivityContainer getEnclosingActivityContainer(IBinder activityToken) 7536 throws RemoteException { 7537 synchronized (this) { 7538 ActivityStack stack = ActivityRecord.getStackLocked(activityToken); 7539 if (stack != null) { 7540 return stack.mActivityContainer; 7541 } 7542 return null; 7543 } 7544 } 7545 7546 @Override 7547 public void moveTaskToStack(int taskId, int stackId, boolean toTop) { 7548 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7549 "moveTaskToStack()"); 7550 if (stackId == HOME_STACK_ID) { 7551 Slog.e(TAG, "moveTaskToStack: Attempt to move task " + taskId + " to home stack", 7552 new RuntimeException("here").fillInStackTrace()); 7553 } 7554 synchronized (this) { 7555 long ident = Binder.clearCallingIdentity(); 7556 try { 7557 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToStack: moving task=" + taskId + " to stackId=" 7558 + stackId + " toTop=" + toTop); 7559 mStackSupervisor.moveTaskToStack(taskId, stackId, toTop); 7560 } finally { 7561 Binder.restoreCallingIdentity(ident); 7562 } 7563 } 7564 } 7565 7566 @Override 7567 public void resizeStack(int stackBoxId, Rect bounds) { 7568 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7569 "resizeStackBox()"); 7570 long ident = Binder.clearCallingIdentity(); 7571 try { 7572 mWindowManager.resizeStack(stackBoxId, bounds); 7573 } finally { 7574 Binder.restoreCallingIdentity(ident); 7575 } 7576 } 7577 7578 @Override 7579 public List<StackInfo> getAllStackInfos() { 7580 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7581 "getAllStackInfos()"); 7582 long ident = Binder.clearCallingIdentity(); 7583 try { 7584 synchronized (this) { 7585 return mStackSupervisor.getAllStackInfosLocked(); 7586 } 7587 } finally { 7588 Binder.restoreCallingIdentity(ident); 7589 } 7590 } 7591 7592 @Override 7593 public StackInfo getStackInfo(int stackId) { 7594 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7595 "getStackInfo()"); 7596 long ident = Binder.clearCallingIdentity(); 7597 try { 7598 synchronized (this) { 7599 return mStackSupervisor.getStackInfoLocked(stackId); 7600 } 7601 } finally { 7602 Binder.restoreCallingIdentity(ident); 7603 } 7604 } 7605 7606 @Override 7607 public boolean isInHomeStack(int taskId) { 7608 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7609 "getStackInfo()"); 7610 long ident = Binder.clearCallingIdentity(); 7611 try { 7612 synchronized (this) { 7613 TaskRecord tr = recentTaskForIdLocked(taskId); 7614 return tr != null && tr.stack != null && tr.stack.isHomeStack(); 7615 } 7616 } finally { 7617 Binder.restoreCallingIdentity(ident); 7618 } 7619 } 7620 7621 @Override 7622 public int getTaskForActivity(IBinder token, boolean onlyRoot) { 7623 synchronized(this) { 7624 return ActivityRecord.getTaskForActivityLocked(token, onlyRoot); 7625 } 7626 } 7627 7628 private boolean isLockTaskAuthorized(String pkg) { 7629 final DevicePolicyManager dpm = (DevicePolicyManager) 7630 mContext.getSystemService(Context.DEVICE_POLICY_SERVICE); 7631 try { 7632 int uid = mContext.getPackageManager().getPackageUid(pkg, 7633 Binder.getCallingUserHandle().getIdentifier()); 7634 return (uid == Binder.getCallingUid()) && dpm != null && dpm.isLockTaskPermitted(pkg); 7635 } catch (NameNotFoundException e) { 7636 return false; 7637 } 7638 } 7639 7640 private void startLockTaskMode(TaskRecord task) { 7641 final String pkg; 7642 synchronized (this) { 7643 pkg = task.intent.getComponent().getPackageName(); 7644 } 7645 if (!isLockTaskAuthorized(pkg)) { 7646 return; 7647 } 7648 long ident = Binder.clearCallingIdentity(); 7649 try { 7650 synchronized (this) { 7651 // Since we lost lock on task, make sure it is still there. 7652 task = mStackSupervisor.anyTaskForIdLocked(task.taskId); 7653 if (task != null) { 7654 if ((mFocusedActivity == null) || (task != mFocusedActivity.task)) { 7655 throw new IllegalArgumentException("Invalid task, not in foreground"); 7656 } 7657 mStackSupervisor.setLockTaskModeLocked(task); 7658 } 7659 } 7660 } finally { 7661 Binder.restoreCallingIdentity(ident); 7662 } 7663 } 7664 7665 @Override 7666 public void startLockTaskMode(int taskId) { 7667 final TaskRecord task; 7668 long ident = Binder.clearCallingIdentity(); 7669 try { 7670 synchronized (this) { 7671 task = mStackSupervisor.anyTaskForIdLocked(taskId); 7672 } 7673 } finally { 7674 Binder.restoreCallingIdentity(ident); 7675 } 7676 if (task != null) { 7677 startLockTaskMode(task); 7678 } 7679 } 7680 7681 @Override 7682 public void startLockTaskMode(IBinder token) { 7683 final TaskRecord task; 7684 long ident = Binder.clearCallingIdentity(); 7685 try { 7686 synchronized (this) { 7687 final ActivityRecord r = ActivityRecord.forToken(token); 7688 if (r == null) { 7689 return; 7690 } 7691 task = r.task; 7692 } 7693 } finally { 7694 Binder.restoreCallingIdentity(ident); 7695 } 7696 if (task != null) { 7697 startLockTaskMode(task); 7698 } 7699 } 7700 7701 @Override 7702 public void stopLockTaskMode() { 7703 // Verify that the user matches the package of the intent for the TaskRecord 7704 // we are locked to. This will ensure the same caller for startLockTaskMode and 7705 // stopLockTaskMode. 7706 try { 7707 String pkg = mStackSupervisor.mLockTaskModeTask.intent.getPackage(); 7708 int uid = mContext.getPackageManager().getPackageUid(pkg, 7709 Binder.getCallingUserHandle().getIdentifier()); 7710 if (uid != Binder.getCallingUid()) { 7711 throw new SecurityException("Invalid uid, expected " + uid); 7712 } 7713 } catch (NameNotFoundException e) { 7714 Log.d(TAG, "stopLockTaskMode " + e); 7715 return; 7716 } 7717 // Stop lock task 7718 synchronized (this) { 7719 mStackSupervisor.setLockTaskModeLocked(null); 7720 } 7721 } 7722 7723 @Override 7724 public boolean isInLockTaskMode() { 7725 synchronized (this) { 7726 return mStackSupervisor.isInLockTaskMode(); 7727 } 7728 } 7729 7730 // ========================================================= 7731 // CONTENT PROVIDERS 7732 // ========================================================= 7733 7734 private final List<ProviderInfo> generateApplicationProvidersLocked(ProcessRecord app) { 7735 List<ProviderInfo> providers = null; 7736 try { 7737 providers = AppGlobals.getPackageManager(). 7738 queryContentProviders(app.processName, app.uid, 7739 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS); 7740 } catch (RemoteException ex) { 7741 } 7742 if (DEBUG_MU) 7743 Slog.v(TAG_MU, "generateApplicationProvidersLocked, app.info.uid = " + app.uid); 7744 int userId = app.userId; 7745 if (providers != null) { 7746 int N = providers.size(); 7747 app.pubProviders.ensureCapacity(N + app.pubProviders.size()); 7748 for (int i=0; i<N; i++) { 7749 ProviderInfo cpi = 7750 (ProviderInfo)providers.get(i); 7751 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo, 7752 cpi.name, cpi.flags); 7753 if (singleton && UserHandle.getUserId(app.uid) != 0) { 7754 // This is a singleton provider, but a user besides the 7755 // default user is asking to initialize a process it runs 7756 // in... well, no, it doesn't actually run in this process, 7757 // it runs in the process of the default user. Get rid of it. 7758 providers.remove(i); 7759 N--; 7760 i--; 7761 continue; 7762 } 7763 7764 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 7765 ContentProviderRecord cpr = mProviderMap.getProviderByClass(comp, userId); 7766 if (cpr == null) { 7767 cpr = new ContentProviderRecord(this, cpi, app.info, comp, singleton); 7768 mProviderMap.putProviderByClass(comp, cpr); 7769 } 7770 if (DEBUG_MU) 7771 Slog.v(TAG_MU, "generateApplicationProvidersLocked, cpi.uid = " + cpr.uid); 7772 app.pubProviders.put(cpi.name, cpr); 7773 if (!cpi.multiprocess || !"android".equals(cpi.packageName)) { 7774 // Don't add this if it is a platform component that is marked 7775 // to run in multiple processes, because this is actually 7776 // part of the framework so doesn't make sense to track as a 7777 // separate apk in the process. 7778 app.addPackage(cpi.applicationInfo.packageName, mProcessStats); 7779 } 7780 ensurePackageDexOpt(cpi.applicationInfo.packageName); 7781 } 7782 } 7783 return providers; 7784 } 7785 7786 /** 7787 * Check if {@link ProcessRecord} has a possible chance at accessing the 7788 * given {@link ProviderInfo}. Final permission checking is always done 7789 * in {@link ContentProvider}. 7790 */ 7791 private final String checkContentProviderPermissionLocked( 7792 ProviderInfo cpi, ProcessRecord r, int userId, boolean checkUser) { 7793 final int callingPid = (r != null) ? r.pid : Binder.getCallingPid(); 7794 final int callingUid = (r != null) ? r.uid : Binder.getCallingUid(); 7795 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 7796 // Looking for cross-user grants before to enforce the typical cross-users permissions 7797 if (userId != UserHandle.getUserId(callingUid)) { 7798 if (perms != null) { 7799 for (GrantUri grantUri : perms.keySet()) { 7800 if (grantUri.sourceUserId == userId) { 7801 String authority = grantUri.uri.getAuthority(); 7802 if (authority.equals(cpi.authority)) { 7803 return null; 7804 } 7805 } 7806 } 7807 } 7808 } 7809 if (checkUser) { 7810 userId = handleIncomingUser(callingPid, callingUid, userId, 7811 false, true, "checkContentProviderPermissionLocked " + cpi.authority, null); 7812 } 7813 if (checkComponentPermission(cpi.readPermission, callingPid, callingUid, 7814 cpi.applicationInfo.uid, cpi.exported) 7815 == PackageManager.PERMISSION_GRANTED) { 7816 return null; 7817 } 7818 if (checkComponentPermission(cpi.writePermission, callingPid, callingUid, 7819 cpi.applicationInfo.uid, cpi.exported) 7820 == PackageManager.PERMISSION_GRANTED) { 7821 return null; 7822 } 7823 7824 PathPermission[] pps = cpi.pathPermissions; 7825 if (pps != null) { 7826 int i = pps.length; 7827 while (i > 0) { 7828 i--; 7829 PathPermission pp = pps[i]; 7830 if (checkComponentPermission(pp.getReadPermission(), callingPid, callingUid, 7831 cpi.applicationInfo.uid, cpi.exported) 7832 == PackageManager.PERMISSION_GRANTED) { 7833 return null; 7834 } 7835 if (checkComponentPermission(pp.getWritePermission(), callingPid, callingUid, 7836 cpi.applicationInfo.uid, cpi.exported) 7837 == PackageManager.PERMISSION_GRANTED) { 7838 return null; 7839 } 7840 } 7841 } 7842 7843 if (perms != null) { 7844 for (GrantUri grantUri : perms.keySet()) { 7845 if (grantUri.uri.getAuthority().equals(cpi.authority)) { 7846 return null; 7847 } 7848 } 7849 } 7850 7851 String msg; 7852 if (!cpi.exported) { 7853 msg = "Permission Denial: opening provider " + cpi.name 7854 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 7855 + ", uid=" + callingUid + ") that is not exported from uid " 7856 + cpi.applicationInfo.uid; 7857 } else { 7858 msg = "Permission Denial: opening provider " + cpi.name 7859 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 7860 + ", uid=" + callingUid + ") requires " 7861 + cpi.readPermission + " or " + cpi.writePermission; 7862 } 7863 Slog.w(TAG, msg); 7864 return msg; 7865 } 7866 7867 ContentProviderConnection incProviderCountLocked(ProcessRecord r, 7868 final ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 7869 if (r != null) { 7870 for (int i=0; i<r.conProviders.size(); i++) { 7871 ContentProviderConnection conn = r.conProviders.get(i); 7872 if (conn.provider == cpr) { 7873 if (DEBUG_PROVIDER) Slog.v(TAG, 7874 "Adding provider requested by " 7875 + r.processName + " from process " 7876 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 7877 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 7878 if (stable) { 7879 conn.stableCount++; 7880 conn.numStableIncs++; 7881 } else { 7882 conn.unstableCount++; 7883 conn.numUnstableIncs++; 7884 } 7885 return conn; 7886 } 7887 } 7888 ContentProviderConnection conn = new ContentProviderConnection(cpr, r); 7889 if (stable) { 7890 conn.stableCount = 1; 7891 conn.numStableIncs = 1; 7892 } else { 7893 conn.unstableCount = 1; 7894 conn.numUnstableIncs = 1; 7895 } 7896 cpr.connections.add(conn); 7897 r.conProviders.add(conn); 7898 return conn; 7899 } 7900 cpr.addExternalProcessHandleLocked(externalProcessToken); 7901 return null; 7902 } 7903 7904 boolean decProviderCountLocked(ContentProviderConnection conn, 7905 ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 7906 if (conn != null) { 7907 cpr = conn.provider; 7908 if (DEBUG_PROVIDER) Slog.v(TAG, 7909 "Removing provider requested by " 7910 + conn.client.processName + " from process " 7911 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 7912 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 7913 if (stable) { 7914 conn.stableCount--; 7915 } else { 7916 conn.unstableCount--; 7917 } 7918 if (conn.stableCount == 0 && conn.unstableCount == 0) { 7919 cpr.connections.remove(conn); 7920 conn.client.conProviders.remove(conn); 7921 return true; 7922 } 7923 return false; 7924 } 7925 cpr.removeExternalProcessHandleLocked(externalProcessToken); 7926 return false; 7927 } 7928 7929 private final ContentProviderHolder getContentProviderImpl(IApplicationThread caller, 7930 String name, IBinder token, boolean stable, int userId) { 7931 ContentProviderRecord cpr; 7932 ContentProviderConnection conn = null; 7933 ProviderInfo cpi = null; 7934 7935 synchronized(this) { 7936 ProcessRecord r = null; 7937 if (caller != null) { 7938 r = getRecordForAppLocked(caller); 7939 if (r == null) { 7940 throw new SecurityException( 7941 "Unable to find app for caller " + caller 7942 + " (pid=" + Binder.getCallingPid() 7943 + ") when getting content provider " + name); 7944 } 7945 } 7946 7947 boolean checkCrossUser = true; 7948 7949 // First check if this content provider has been published... 7950 cpr = mProviderMap.getProviderByName(name, userId); 7951 // If that didn't work, check if it exists for user 0 and then 7952 // verify that it's a singleton provider before using it. 7953 if (cpr == null && userId != UserHandle.USER_OWNER) { 7954 cpr = mProviderMap.getProviderByName(name, UserHandle.USER_OWNER); 7955 if (cpr != null) { 7956 cpi = cpr.info; 7957 if (isSingleton(cpi.processName, cpi.applicationInfo, 7958 cpi.name, cpi.flags) 7959 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid)) { 7960 userId = UserHandle.USER_OWNER; 7961 checkCrossUser = false; 7962 } else { 7963 cpr = null; 7964 cpi = null; 7965 } 7966 } 7967 } 7968 7969 boolean providerRunning = cpr != null; 7970 if (providerRunning) { 7971 cpi = cpr.info; 7972 String msg; 7973 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, checkCrossUser)) 7974 != null) { 7975 throw new SecurityException(msg); 7976 } 7977 7978 if (r != null && cpr.canRunHere(r)) { 7979 // This provider has been published or is in the process 7980 // of being published... but it is also allowed to run 7981 // in the caller's process, so don't make a connection 7982 // and just let the caller instantiate its own instance. 7983 ContentProviderHolder holder = cpr.newHolder(null); 7984 // don't give caller the provider object, it needs 7985 // to make its own. 7986 holder.provider = null; 7987 return holder; 7988 } 7989 7990 final long origId = Binder.clearCallingIdentity(); 7991 7992 // In this case the provider instance already exists, so we can 7993 // return it right away. 7994 conn = incProviderCountLocked(r, cpr, token, stable); 7995 if (conn != null && (conn.stableCount+conn.unstableCount) == 1) { 7996 if (cpr.proc != null && r.setAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 7997 // If this is a perceptible app accessing the provider, 7998 // make sure to count it as being accessed and thus 7999 // back up on the LRU list. This is good because 8000 // content providers are often expensive to start. 8001 updateLruProcessLocked(cpr.proc, false, null); 8002 } 8003 } 8004 8005 if (cpr.proc != null) { 8006 if (false) { 8007 if (cpr.name.flattenToShortString().equals( 8008 "com.android.providers.calendar/.CalendarProvider2")) { 8009 Slog.v(TAG, "****************** KILLING " 8010 + cpr.name.flattenToShortString()); 8011 Process.killProcess(cpr.proc.pid); 8012 } 8013 } 8014 boolean success = updateOomAdjLocked(cpr.proc); 8015 if (DEBUG_PROVIDER) Slog.i(TAG, "Adjust success: " + success); 8016 // NOTE: there is still a race here where a signal could be 8017 // pending on the process even though we managed to update its 8018 // adj level. Not sure what to do about this, but at least 8019 // the race is now smaller. 8020 if (!success) { 8021 // Uh oh... it looks like the provider's process 8022 // has been killed on us. We need to wait for a new 8023 // process to be started, and make sure its death 8024 // doesn't kill our process. 8025 Slog.i(TAG, 8026 "Existing provider " + cpr.name.flattenToShortString() 8027 + " is crashing; detaching " + r); 8028 boolean lastRef = decProviderCountLocked(conn, cpr, token, stable); 8029 appDiedLocked(cpr.proc, cpr.proc.pid, cpr.proc.thread); 8030 if (!lastRef) { 8031 // This wasn't the last ref our process had on 8032 // the provider... we have now been killed, bail. 8033 return null; 8034 } 8035 providerRunning = false; 8036 conn = null; 8037 } 8038 } 8039 8040 Binder.restoreCallingIdentity(origId); 8041 } 8042 8043 boolean singleton; 8044 if (!providerRunning) { 8045 try { 8046 cpi = AppGlobals.getPackageManager(). 8047 resolveContentProvider(name, 8048 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS, userId); 8049 } catch (RemoteException ex) { 8050 } 8051 if (cpi == null) { 8052 return null; 8053 } 8054 // If the provider is a singleton AND 8055 // (it's a call within the same user || the provider is a 8056 // privileged app) 8057 // Then allow connecting to the singleton provider 8058 singleton = isSingleton(cpi.processName, cpi.applicationInfo, 8059 cpi.name, cpi.flags) 8060 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid); 8061 if (singleton) { 8062 userId = UserHandle.USER_OWNER; 8063 } 8064 cpi.applicationInfo = getAppInfoForUser(cpi.applicationInfo, userId); 8065 8066 String msg; 8067 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, !singleton)) 8068 != null) { 8069 throw new SecurityException(msg); 8070 } 8071 8072 if (!mProcessesReady && !mDidUpdate && !mWaitingUpdate 8073 && !cpi.processName.equals("system")) { 8074 // If this content provider does not run in the system 8075 // process, and the system is not yet ready to run other 8076 // processes, then fail fast instead of hanging. 8077 throw new IllegalArgumentException( 8078 "Attempt to launch content provider before system ready"); 8079 } 8080 8081 // Make sure that the user who owns this provider is started. If not, 8082 // we don't want to allow it to run. 8083 if (mStartedUsers.get(userId) == null) { 8084 Slog.w(TAG, "Unable to launch app " 8085 + cpi.applicationInfo.packageName + "/" 8086 + cpi.applicationInfo.uid + " for provider " 8087 + name + ": user " + userId + " is stopped"); 8088 return null; 8089 } 8090 8091 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 8092 cpr = mProviderMap.getProviderByClass(comp, userId); 8093 final boolean firstClass = cpr == null; 8094 if (firstClass) { 8095 try { 8096 ApplicationInfo ai = 8097 AppGlobals.getPackageManager(). 8098 getApplicationInfo( 8099 cpi.applicationInfo.packageName, 8100 STOCK_PM_FLAGS, userId); 8101 if (ai == null) { 8102 Slog.w(TAG, "No package info for content provider " 8103 + cpi.name); 8104 return null; 8105 } 8106 ai = getAppInfoForUser(ai, userId); 8107 cpr = new ContentProviderRecord(this, cpi, ai, comp, singleton); 8108 } catch (RemoteException ex) { 8109 // pm is in same process, this will never happen. 8110 } 8111 } 8112 8113 if (r != null && cpr.canRunHere(r)) { 8114 // If this is a multiprocess provider, then just return its 8115 // info and allow the caller to instantiate it. Only do 8116 // this if the provider is the same user as the caller's 8117 // process, or can run as root (so can be in any process). 8118 return cpr.newHolder(null); 8119 } 8120 8121 if (DEBUG_PROVIDER) { 8122 RuntimeException e = new RuntimeException("here"); 8123 Slog.w(TAG, "LAUNCHING REMOTE PROVIDER (myuid " + (r != null ? r.uid : null) 8124 + " pruid " + cpr.appInfo.uid + "): " + cpr.info.name, e); 8125 } 8126 8127 // This is single process, and our app is now connecting to it. 8128 // See if we are already in the process of launching this 8129 // provider. 8130 final int N = mLaunchingProviders.size(); 8131 int i; 8132 for (i=0; i<N; i++) { 8133 if (mLaunchingProviders.get(i) == cpr) { 8134 break; 8135 } 8136 } 8137 8138 // If the provider is not already being launched, then get it 8139 // started. 8140 if (i >= N) { 8141 final long origId = Binder.clearCallingIdentity(); 8142 8143 try { 8144 // Content provider is now in use, its package can't be stopped. 8145 try { 8146 AppGlobals.getPackageManager().setPackageStoppedState( 8147 cpr.appInfo.packageName, false, userId); 8148 } catch (RemoteException e) { 8149 } catch (IllegalArgumentException e) { 8150 Slog.w(TAG, "Failed trying to unstop package " 8151 + cpr.appInfo.packageName + ": " + e); 8152 } 8153 8154 // Use existing process if already started 8155 ProcessRecord proc = getProcessRecordLocked( 8156 cpi.processName, cpr.appInfo.uid, false); 8157 if (proc != null && proc.thread != null) { 8158 if (DEBUG_PROVIDER) { 8159 Slog.d(TAG, "Installing in existing process " + proc); 8160 } 8161 proc.pubProviders.put(cpi.name, cpr); 8162 try { 8163 proc.thread.scheduleInstallProvider(cpi); 8164 } catch (RemoteException e) { 8165 } 8166 } else { 8167 proc = startProcessLocked(cpi.processName, 8168 cpr.appInfo, false, 0, "content provider", 8169 new ComponentName(cpi.applicationInfo.packageName, 8170 cpi.name), false, false, false); 8171 if (proc == null) { 8172 Slog.w(TAG, "Unable to launch app " 8173 + cpi.applicationInfo.packageName + "/" 8174 + cpi.applicationInfo.uid + " for provider " 8175 + name + ": process is bad"); 8176 return null; 8177 } 8178 } 8179 cpr.launchingApp = proc; 8180 mLaunchingProviders.add(cpr); 8181 } finally { 8182 Binder.restoreCallingIdentity(origId); 8183 } 8184 } 8185 8186 // Make sure the provider is published (the same provider class 8187 // may be published under multiple names). 8188 if (firstClass) { 8189 mProviderMap.putProviderByClass(comp, cpr); 8190 } 8191 8192 mProviderMap.putProviderByName(name, cpr); 8193 conn = incProviderCountLocked(r, cpr, token, stable); 8194 if (conn != null) { 8195 conn.waiting = true; 8196 } 8197 } 8198 } 8199 8200 // Wait for the provider to be published... 8201 synchronized (cpr) { 8202 while (cpr.provider == null) { 8203 if (cpr.launchingApp == null) { 8204 Slog.w(TAG, "Unable to launch app " 8205 + cpi.applicationInfo.packageName + "/" 8206 + cpi.applicationInfo.uid + " for provider " 8207 + name + ": launching app became null"); 8208 EventLog.writeEvent(EventLogTags.AM_PROVIDER_LOST_PROCESS, 8209 UserHandle.getUserId(cpi.applicationInfo.uid), 8210 cpi.applicationInfo.packageName, 8211 cpi.applicationInfo.uid, name); 8212 return null; 8213 } 8214 try { 8215 if (DEBUG_MU) { 8216 Slog.v(TAG_MU, "Waiting to start provider " + cpr + " launchingApp=" 8217 + cpr.launchingApp); 8218 } 8219 if (conn != null) { 8220 conn.waiting = true; 8221 } 8222 cpr.wait(); 8223 } catch (InterruptedException ex) { 8224 } finally { 8225 if (conn != null) { 8226 conn.waiting = false; 8227 } 8228 } 8229 } 8230 } 8231 return cpr != null ? cpr.newHolder(conn) : null; 8232 } 8233 8234 @Override 8235 public final ContentProviderHolder getContentProvider( 8236 IApplicationThread caller, String name, int userId, boolean stable) { 8237 enforceNotIsolatedCaller("getContentProvider"); 8238 if (caller == null) { 8239 String msg = "null IApplicationThread when getting content provider " 8240 + name; 8241 Slog.w(TAG, msg); 8242 throw new SecurityException(msg); 8243 } 8244 // The incoming user check is now handled in checkContentProviderPermissionLocked() to deal 8245 // with cross-user grant. 8246 return getContentProviderImpl(caller, name, null, stable, userId); 8247 } 8248 8249 public ContentProviderHolder getContentProviderExternal( 8250 String name, int userId, IBinder token) { 8251 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 8252 "Do not have permission in call getContentProviderExternal()"); 8253 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 8254 false, true, "getContentProvider", null); 8255 return getContentProviderExternalUnchecked(name, token, userId); 8256 } 8257 8258 private ContentProviderHolder getContentProviderExternalUnchecked(String name, 8259 IBinder token, int userId) { 8260 return getContentProviderImpl(null, name, token, true, userId); 8261 } 8262 8263 /** 8264 * Drop a content provider from a ProcessRecord's bookkeeping 8265 */ 8266 public void removeContentProvider(IBinder connection, boolean stable) { 8267 enforceNotIsolatedCaller("removeContentProvider"); 8268 long ident = Binder.clearCallingIdentity(); 8269 try { 8270 synchronized (this) { 8271 ContentProviderConnection conn; 8272 try { 8273 conn = (ContentProviderConnection)connection; 8274 } catch (ClassCastException e) { 8275 String msg ="removeContentProvider: " + connection 8276 + " not a ContentProviderConnection"; 8277 Slog.w(TAG, msg); 8278 throw new IllegalArgumentException(msg); 8279 } 8280 if (conn == null) { 8281 throw new NullPointerException("connection is null"); 8282 } 8283 if (decProviderCountLocked(conn, null, null, stable)) { 8284 updateOomAdjLocked(); 8285 } 8286 } 8287 } finally { 8288 Binder.restoreCallingIdentity(ident); 8289 } 8290 } 8291 8292 public void removeContentProviderExternal(String name, IBinder token) { 8293 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 8294 "Do not have permission in call removeContentProviderExternal()"); 8295 removeContentProviderExternalUnchecked(name, token, UserHandle.getCallingUserId()); 8296 } 8297 8298 private void removeContentProviderExternalUnchecked(String name, IBinder token, int userId) { 8299 synchronized (this) { 8300 ContentProviderRecord cpr = mProviderMap.getProviderByName(name, userId); 8301 if(cpr == null) { 8302 //remove from mProvidersByClass 8303 if(localLOGV) Slog.v(TAG, name+" content provider not found in providers list"); 8304 return; 8305 } 8306 8307 //update content provider record entry info 8308 ComponentName comp = new ComponentName(cpr.info.packageName, cpr.info.name); 8309 ContentProviderRecord localCpr = mProviderMap.getProviderByClass(comp, userId); 8310 if (localCpr.hasExternalProcessHandles()) { 8311 if (localCpr.removeExternalProcessHandleLocked(token)) { 8312 updateOomAdjLocked(); 8313 } else { 8314 Slog.e(TAG, "Attmpt to remove content provider " + localCpr 8315 + " with no external reference for token: " 8316 + token + "."); 8317 } 8318 } else { 8319 Slog.e(TAG, "Attmpt to remove content provider: " + localCpr 8320 + " with no external references."); 8321 } 8322 } 8323 } 8324 8325 public final void publishContentProviders(IApplicationThread caller, 8326 List<ContentProviderHolder> providers) { 8327 if (providers == null) { 8328 return; 8329 } 8330 8331 enforceNotIsolatedCaller("publishContentProviders"); 8332 synchronized (this) { 8333 final ProcessRecord r = getRecordForAppLocked(caller); 8334 if (DEBUG_MU) 8335 Slog.v(TAG_MU, "ProcessRecord uid = " + r.uid); 8336 if (r == null) { 8337 throw new SecurityException( 8338 "Unable to find app for caller " + caller 8339 + " (pid=" + Binder.getCallingPid() 8340 + ") when publishing content providers"); 8341 } 8342 8343 final long origId = Binder.clearCallingIdentity(); 8344 8345 final int N = providers.size(); 8346 for (int i=0; i<N; i++) { 8347 ContentProviderHolder src = providers.get(i); 8348 if (src == null || src.info == null || src.provider == null) { 8349 continue; 8350 } 8351 ContentProviderRecord dst = r.pubProviders.get(src.info.name); 8352 if (DEBUG_MU) 8353 Slog.v(TAG_MU, "ContentProviderRecord uid = " + dst.uid); 8354 if (dst != null) { 8355 ComponentName comp = new ComponentName(dst.info.packageName, dst.info.name); 8356 mProviderMap.putProviderByClass(comp, dst); 8357 String names[] = dst.info.authority.split(";"); 8358 for (int j = 0; j < names.length; j++) { 8359 mProviderMap.putProviderByName(names[j], dst); 8360 } 8361 8362 int NL = mLaunchingProviders.size(); 8363 int j; 8364 for (j=0; j<NL; j++) { 8365 if (mLaunchingProviders.get(j) == dst) { 8366 mLaunchingProviders.remove(j); 8367 j--; 8368 NL--; 8369 } 8370 } 8371 synchronized (dst) { 8372 dst.provider = src.provider; 8373 dst.proc = r; 8374 dst.notifyAll(); 8375 } 8376 updateOomAdjLocked(r); 8377 } 8378 } 8379 8380 Binder.restoreCallingIdentity(origId); 8381 } 8382 } 8383 8384 public boolean refContentProvider(IBinder connection, int stable, int unstable) { 8385 ContentProviderConnection conn; 8386 try { 8387 conn = (ContentProviderConnection)connection; 8388 } catch (ClassCastException e) { 8389 String msg ="refContentProvider: " + connection 8390 + " not a ContentProviderConnection"; 8391 Slog.w(TAG, msg); 8392 throw new IllegalArgumentException(msg); 8393 } 8394 if (conn == null) { 8395 throw new NullPointerException("connection is null"); 8396 } 8397 8398 synchronized (this) { 8399 if (stable > 0) { 8400 conn.numStableIncs += stable; 8401 } 8402 stable = conn.stableCount + stable; 8403 if (stable < 0) { 8404 throw new IllegalStateException("stableCount < 0: " + stable); 8405 } 8406 8407 if (unstable > 0) { 8408 conn.numUnstableIncs += unstable; 8409 } 8410 unstable = conn.unstableCount + unstable; 8411 if (unstable < 0) { 8412 throw new IllegalStateException("unstableCount < 0: " + unstable); 8413 } 8414 8415 if ((stable+unstable) <= 0) { 8416 throw new IllegalStateException("ref counts can't go to zero here: stable=" 8417 + stable + " unstable=" + unstable); 8418 } 8419 conn.stableCount = stable; 8420 conn.unstableCount = unstable; 8421 return !conn.dead; 8422 } 8423 } 8424 8425 public void unstableProviderDied(IBinder connection) { 8426 ContentProviderConnection conn; 8427 try { 8428 conn = (ContentProviderConnection)connection; 8429 } catch (ClassCastException e) { 8430 String msg ="refContentProvider: " + connection 8431 + " not a ContentProviderConnection"; 8432 Slog.w(TAG, msg); 8433 throw new IllegalArgumentException(msg); 8434 } 8435 if (conn == null) { 8436 throw new NullPointerException("connection is null"); 8437 } 8438 8439 // Safely retrieve the content provider associated with the connection. 8440 IContentProvider provider; 8441 synchronized (this) { 8442 provider = conn.provider.provider; 8443 } 8444 8445 if (provider == null) { 8446 // Um, yeah, we're way ahead of you. 8447 return; 8448 } 8449 8450 // Make sure the caller is being honest with us. 8451 if (provider.asBinder().pingBinder()) { 8452 // Er, no, still looks good to us. 8453 synchronized (this) { 8454 Slog.w(TAG, "unstableProviderDied: caller " + Binder.getCallingUid() 8455 + " says " + conn + " died, but we don't agree"); 8456 return; 8457 } 8458 } 8459 8460 // Well look at that! It's dead! 8461 synchronized (this) { 8462 if (conn.provider.provider != provider) { 8463 // But something changed... good enough. 8464 return; 8465 } 8466 8467 ProcessRecord proc = conn.provider.proc; 8468 if (proc == null || proc.thread == null) { 8469 // Seems like the process is already cleaned up. 8470 return; 8471 } 8472 8473 // As far as we're concerned, this is just like receiving a 8474 // death notification... just a bit prematurely. 8475 Slog.i(TAG, "Process " + proc.processName + " (pid " + proc.pid 8476 + ") early provider death"); 8477 final long ident = Binder.clearCallingIdentity(); 8478 try { 8479 appDiedLocked(proc, proc.pid, proc.thread); 8480 } finally { 8481 Binder.restoreCallingIdentity(ident); 8482 } 8483 } 8484 } 8485 8486 @Override 8487 public void appNotRespondingViaProvider(IBinder connection) { 8488 enforceCallingPermission( 8489 android.Manifest.permission.REMOVE_TASKS, "appNotRespondingViaProvider()"); 8490 8491 final ContentProviderConnection conn = (ContentProviderConnection) connection; 8492 if (conn == null) { 8493 Slog.w(TAG, "ContentProviderConnection is null"); 8494 return; 8495 } 8496 8497 final ProcessRecord host = conn.provider.proc; 8498 if (host == null) { 8499 Slog.w(TAG, "Failed to find hosting ProcessRecord"); 8500 return; 8501 } 8502 8503 final long token = Binder.clearCallingIdentity(); 8504 try { 8505 appNotResponding(host, null, null, false, "ContentProvider not responding"); 8506 } finally { 8507 Binder.restoreCallingIdentity(token); 8508 } 8509 } 8510 8511 public final void installSystemProviders() { 8512 List<ProviderInfo> providers; 8513 synchronized (this) { 8514 ProcessRecord app = mProcessNames.get("system", Process.SYSTEM_UID); 8515 providers = generateApplicationProvidersLocked(app); 8516 if (providers != null) { 8517 for (int i=providers.size()-1; i>=0; i--) { 8518 ProviderInfo pi = (ProviderInfo)providers.get(i); 8519 if ((pi.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) == 0) { 8520 Slog.w(TAG, "Not installing system proc provider " + pi.name 8521 + ": not system .apk"); 8522 providers.remove(i); 8523 } 8524 } 8525 } 8526 } 8527 if (providers != null) { 8528 mSystemThread.installSystemProviders(providers); 8529 } 8530 8531 mCoreSettingsObserver = new CoreSettingsObserver(this); 8532 8533 mUsageStatsService.monitorPackages(); 8534 } 8535 8536 /** 8537 * Allows app to retrieve the MIME type of a URI without having permission 8538 * to access its content provider. 8539 * 8540 * CTS tests for this functionality can be run with "runtest cts-appsecurity". 8541 * 8542 * Test cases are at cts/tests/appsecurity-tests/test-apps/UsePermissionDiffCert/ 8543 * src/com/android/cts/usespermissiondiffcertapp/AccessPermissionWithDiffSigTest.java 8544 */ 8545 public String getProviderMimeType(Uri uri, int userId) { 8546 enforceNotIsolatedCaller("getProviderMimeType"); 8547 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 8548 userId, false, true, "getProviderMimeType", null); 8549 final String name = uri.getAuthority(); 8550 final long ident = Binder.clearCallingIdentity(); 8551 ContentProviderHolder holder = null; 8552 8553 try { 8554 holder = getContentProviderExternalUnchecked(name, null, userId); 8555 if (holder != null) { 8556 return holder.provider.getType(uri); 8557 } 8558 } catch (RemoteException e) { 8559 Log.w(TAG, "Content provider dead retrieving " + uri, e); 8560 return null; 8561 } finally { 8562 if (holder != null) { 8563 removeContentProviderExternalUnchecked(name, null, userId); 8564 } 8565 Binder.restoreCallingIdentity(ident); 8566 } 8567 8568 return null; 8569 } 8570 8571 // ========================================================= 8572 // GLOBAL MANAGEMENT 8573 // ========================================================= 8574 8575 final ProcessRecord newProcessRecordLocked(ApplicationInfo info, String customProcess, 8576 boolean isolated) { 8577 String proc = customProcess != null ? customProcess : info.processName; 8578 BatteryStatsImpl.Uid.Proc ps = null; 8579 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 8580 int uid = info.uid; 8581 if (isolated) { 8582 int userId = UserHandle.getUserId(uid); 8583 int stepsLeft = Process.LAST_ISOLATED_UID - Process.FIRST_ISOLATED_UID + 1; 8584 while (true) { 8585 if (mNextIsolatedProcessUid < Process.FIRST_ISOLATED_UID 8586 || mNextIsolatedProcessUid > Process.LAST_ISOLATED_UID) { 8587 mNextIsolatedProcessUid = Process.FIRST_ISOLATED_UID; 8588 } 8589 uid = UserHandle.getUid(userId, mNextIsolatedProcessUid); 8590 mNextIsolatedProcessUid++; 8591 if (mIsolatedProcesses.indexOfKey(uid) < 0) { 8592 // No process for this uid, use it. 8593 break; 8594 } 8595 stepsLeft--; 8596 if (stepsLeft <= 0) { 8597 return null; 8598 } 8599 } 8600 } 8601 return new ProcessRecord(stats, info, proc, uid); 8602 } 8603 8604 final ProcessRecord addAppLocked(ApplicationInfo info, boolean isolated, 8605 String abiOverride) { 8606 ProcessRecord app; 8607 if (!isolated) { 8608 app = getProcessRecordLocked(info.processName, info.uid, true); 8609 } else { 8610 app = null; 8611 } 8612 8613 if (app == null) { 8614 app = newProcessRecordLocked(info, null, isolated); 8615 mProcessNames.put(info.processName, app.uid, app); 8616 if (isolated) { 8617 mIsolatedProcesses.put(app.uid, app); 8618 } 8619 updateLruProcessLocked(app, false, null); 8620 updateOomAdjLocked(); 8621 } 8622 8623 // This package really, really can not be stopped. 8624 try { 8625 AppGlobals.getPackageManager().setPackageStoppedState( 8626 info.packageName, false, UserHandle.getUserId(app.uid)); 8627 } catch (RemoteException e) { 8628 } catch (IllegalArgumentException e) { 8629 Slog.w(TAG, "Failed trying to unstop package " 8630 + info.packageName + ": " + e); 8631 } 8632 8633 if ((info.flags&(ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) 8634 == (ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) { 8635 app.persistent = true; 8636 app.maxAdj = ProcessList.PERSISTENT_PROC_ADJ; 8637 } 8638 if (app.thread == null && mPersistentStartingProcesses.indexOf(app) < 0) { 8639 mPersistentStartingProcesses.add(app); 8640 startProcessLocked(app, "added application", app.processName, 8641 abiOverride); 8642 } 8643 8644 return app; 8645 } 8646 8647 public void unhandledBack() { 8648 enforceCallingPermission(android.Manifest.permission.FORCE_BACK, 8649 "unhandledBack()"); 8650 8651 synchronized(this) { 8652 final long origId = Binder.clearCallingIdentity(); 8653 try { 8654 getFocusedStack().unhandledBackLocked(); 8655 } finally { 8656 Binder.restoreCallingIdentity(origId); 8657 } 8658 } 8659 } 8660 8661 public ParcelFileDescriptor openContentUri(Uri uri) throws RemoteException { 8662 enforceNotIsolatedCaller("openContentUri"); 8663 final int userId = UserHandle.getCallingUserId(); 8664 String name = uri.getAuthority(); 8665 ContentProviderHolder cph = getContentProviderExternalUnchecked(name, null, userId); 8666 ParcelFileDescriptor pfd = null; 8667 if (cph != null) { 8668 // We record the binder invoker's uid in thread-local storage before 8669 // going to the content provider to open the file. Later, in the code 8670 // that handles all permissions checks, we look for this uid and use 8671 // that rather than the Activity Manager's own uid. The effect is that 8672 // we do the check against the caller's permissions even though it looks 8673 // to the content provider like the Activity Manager itself is making 8674 // the request. 8675 sCallerIdentity.set(new Identity( 8676 Binder.getCallingPid(), Binder.getCallingUid())); 8677 try { 8678 pfd = cph.provider.openFile(null, uri, "r", null); 8679 } catch (FileNotFoundException e) { 8680 // do nothing; pfd will be returned null 8681 } finally { 8682 // Ensure that whatever happens, we clean up the identity state 8683 sCallerIdentity.remove(); 8684 } 8685 8686 // We've got the fd now, so we're done with the provider. 8687 removeContentProviderExternalUnchecked(name, null, userId); 8688 } else { 8689 Slog.d(TAG, "Failed to get provider for authority '" + name + "'"); 8690 } 8691 return pfd; 8692 } 8693 8694 // Actually is sleeping or shutting down or whatever else in the future 8695 // is an inactive state. 8696 public boolean isSleepingOrShuttingDown() { 8697 return mSleeping || mShuttingDown; 8698 } 8699 8700 public boolean isSleeping() { 8701 return mSleeping; 8702 } 8703 8704 void goingToSleep() { 8705 synchronized(this) { 8706 mWentToSleep = true; 8707 updateEventDispatchingLocked(); 8708 goToSleepIfNeededLocked(); 8709 } 8710 } 8711 8712 void finishRunningVoiceLocked() { 8713 if (mRunningVoice) { 8714 mRunningVoice = false; 8715 goToSleepIfNeededLocked(); 8716 } 8717 } 8718 8719 void goToSleepIfNeededLocked() { 8720 if (mWentToSleep && !mRunningVoice) { 8721 if (!mSleeping) { 8722 mSleeping = true; 8723 mStackSupervisor.goingToSleepLocked(); 8724 8725 // Initialize the wake times of all processes. 8726 checkExcessivePowerUsageLocked(false); 8727 mHandler.removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 8728 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 8729 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 8730 } 8731 } 8732 } 8733 8734 void notifyTaskPersisterLocked(TaskRecord task, boolean flush) { 8735 mTaskPersister.notify(task, flush); 8736 } 8737 8738 @Override 8739 public boolean shutdown(int timeout) { 8740 if (checkCallingPermission(android.Manifest.permission.SHUTDOWN) 8741 != PackageManager.PERMISSION_GRANTED) { 8742 throw new SecurityException("Requires permission " 8743 + android.Manifest.permission.SHUTDOWN); 8744 } 8745 8746 boolean timedout = false; 8747 8748 synchronized(this) { 8749 mShuttingDown = true; 8750 updateEventDispatchingLocked(); 8751 timedout = mStackSupervisor.shutdownLocked(timeout); 8752 } 8753 8754 mAppOpsService.shutdown(); 8755 mUsageStatsService.shutdown(); 8756 mBatteryStatsService.shutdown(); 8757 synchronized (this) { 8758 mProcessStats.shutdownLocked(); 8759 } 8760 notifyTaskPersisterLocked(null, true); 8761 8762 return timedout; 8763 } 8764 8765 public final void activitySlept(IBinder token) { 8766 if (localLOGV) Slog.v(TAG, "Activity slept: token=" + token); 8767 8768 final long origId = Binder.clearCallingIdentity(); 8769 8770 synchronized (this) { 8771 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 8772 if (r != null) { 8773 mStackSupervisor.activitySleptLocked(r); 8774 } 8775 } 8776 8777 Binder.restoreCallingIdentity(origId); 8778 } 8779 8780 void logLockScreen(String msg) { 8781 if (DEBUG_LOCKSCREEN) Slog.d(TAG, Debug.getCallers(2) + ":" + msg + 8782 " mLockScreenShown=" + mLockScreenShown + " mWentToSleep=" + 8783 mWentToSleep + " mSleeping=" + mSleeping + " mDismissKeyguardOnNextActivity=" + 8784 mStackSupervisor.mDismissKeyguardOnNextActivity); 8785 } 8786 8787 private void comeOutOfSleepIfNeededLocked() { 8788 if ((!mWentToSleep && !mLockScreenShown) || mRunningVoice) { 8789 if (mSleeping) { 8790 mSleeping = false; 8791 mStackSupervisor.comeOutOfSleepIfNeededLocked(); 8792 } 8793 } 8794 } 8795 8796 void wakingUp() { 8797 synchronized(this) { 8798 mWentToSleep = false; 8799 updateEventDispatchingLocked(); 8800 comeOutOfSleepIfNeededLocked(); 8801 } 8802 } 8803 8804 void startRunningVoiceLocked() { 8805 if (!mRunningVoice) { 8806 mRunningVoice = true; 8807 comeOutOfSleepIfNeededLocked(); 8808 } 8809 } 8810 8811 private void updateEventDispatchingLocked() { 8812 mWindowManager.setEventDispatching(mBooted && !mWentToSleep && !mShuttingDown); 8813 } 8814 8815 public void setLockScreenShown(boolean shown) { 8816 if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER) 8817 != PackageManager.PERMISSION_GRANTED) { 8818 throw new SecurityException("Requires permission " 8819 + android.Manifest.permission.DEVICE_POWER); 8820 } 8821 8822 synchronized(this) { 8823 long ident = Binder.clearCallingIdentity(); 8824 try { 8825 if (DEBUG_LOCKSCREEN) logLockScreen(" shown=" + shown); 8826 mLockScreenShown = shown; 8827 comeOutOfSleepIfNeededLocked(); 8828 } finally { 8829 Binder.restoreCallingIdentity(ident); 8830 } 8831 } 8832 } 8833 8834 public void stopAppSwitches() { 8835 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 8836 != PackageManager.PERMISSION_GRANTED) { 8837 throw new SecurityException("Requires permission " 8838 + android.Manifest.permission.STOP_APP_SWITCHES); 8839 } 8840 8841 synchronized(this) { 8842 mAppSwitchesAllowedTime = SystemClock.uptimeMillis() 8843 + APP_SWITCH_DELAY_TIME; 8844 mDidAppSwitch = false; 8845 mHandler.removeMessages(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 8846 Message msg = mHandler.obtainMessage(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 8847 mHandler.sendMessageDelayed(msg, APP_SWITCH_DELAY_TIME); 8848 } 8849 } 8850 8851 public void resumeAppSwitches() { 8852 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 8853 != PackageManager.PERMISSION_GRANTED) { 8854 throw new SecurityException("Requires permission " 8855 + android.Manifest.permission.STOP_APP_SWITCHES); 8856 } 8857 8858 synchronized(this) { 8859 // Note that we don't execute any pending app switches... we will 8860 // let those wait until either the timeout, or the next start 8861 // activity request. 8862 mAppSwitchesAllowedTime = 0; 8863 } 8864 } 8865 8866 boolean checkAppSwitchAllowedLocked(int callingPid, int callingUid, 8867 String name) { 8868 if (mAppSwitchesAllowedTime < SystemClock.uptimeMillis()) { 8869 return true; 8870 } 8871 8872 final int perm = checkComponentPermission( 8873 android.Manifest.permission.STOP_APP_SWITCHES, callingPid, 8874 callingUid, -1, true); 8875 if (perm == PackageManager.PERMISSION_GRANTED) { 8876 return true; 8877 } 8878 8879 Slog.w(TAG, name + " request from " + callingUid + " stopped"); 8880 return false; 8881 } 8882 8883 public void setDebugApp(String packageName, boolean waitForDebugger, 8884 boolean persistent) { 8885 enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP, 8886 "setDebugApp()"); 8887 8888 long ident = Binder.clearCallingIdentity(); 8889 try { 8890 // Note that this is not really thread safe if there are multiple 8891 // callers into it at the same time, but that's not a situation we 8892 // care about. 8893 if (persistent) { 8894 final ContentResolver resolver = mContext.getContentResolver(); 8895 Settings.Global.putString( 8896 resolver, Settings.Global.DEBUG_APP, 8897 packageName); 8898 Settings.Global.putInt( 8899 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 8900 waitForDebugger ? 1 : 0); 8901 } 8902 8903 synchronized (this) { 8904 if (!persistent) { 8905 mOrigDebugApp = mDebugApp; 8906 mOrigWaitForDebugger = mWaitForDebugger; 8907 } 8908 mDebugApp = packageName; 8909 mWaitForDebugger = waitForDebugger; 8910 mDebugTransient = !persistent; 8911 if (packageName != null) { 8912 forceStopPackageLocked(packageName, -1, false, false, true, true, 8913 false, UserHandle.USER_ALL, "set debug app"); 8914 } 8915 } 8916 } finally { 8917 Binder.restoreCallingIdentity(ident); 8918 } 8919 } 8920 8921 void setOpenGlTraceApp(ApplicationInfo app, String processName) { 8922 synchronized (this) { 8923 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 8924 if (!isDebuggable) { 8925 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 8926 throw new SecurityException("Process not debuggable: " + app.packageName); 8927 } 8928 } 8929 8930 mOpenGlTraceApp = processName; 8931 } 8932 } 8933 8934 void setProfileApp(ApplicationInfo app, String processName, String profileFile, 8935 ParcelFileDescriptor profileFd, boolean autoStopProfiler) { 8936 synchronized (this) { 8937 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 8938 if (!isDebuggable) { 8939 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 8940 throw new SecurityException("Process not debuggable: " + app.packageName); 8941 } 8942 } 8943 mProfileApp = processName; 8944 mProfileFile = profileFile; 8945 if (mProfileFd != null) { 8946 try { 8947 mProfileFd.close(); 8948 } catch (IOException e) { 8949 } 8950 mProfileFd = null; 8951 } 8952 mProfileFd = profileFd; 8953 mProfileType = 0; 8954 mAutoStopProfiler = autoStopProfiler; 8955 } 8956 } 8957 8958 @Override 8959 public void setAlwaysFinish(boolean enabled) { 8960 enforceCallingPermission(android.Manifest.permission.SET_ALWAYS_FINISH, 8961 "setAlwaysFinish()"); 8962 8963 Settings.Global.putInt( 8964 mContext.getContentResolver(), 8965 Settings.Global.ALWAYS_FINISH_ACTIVITIES, enabled ? 1 : 0); 8966 8967 synchronized (this) { 8968 mAlwaysFinishActivities = enabled; 8969 } 8970 } 8971 8972 @Override 8973 public void setActivityController(IActivityController controller) { 8974 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 8975 "setActivityController()"); 8976 synchronized (this) { 8977 mController = controller; 8978 Watchdog.getInstance().setActivityController(controller); 8979 } 8980 } 8981 8982 @Override 8983 public void setUserIsMonkey(boolean userIsMonkey) { 8984 synchronized (this) { 8985 synchronized (mPidsSelfLocked) { 8986 final int callingPid = Binder.getCallingPid(); 8987 ProcessRecord precessRecord = mPidsSelfLocked.get(callingPid); 8988 if (precessRecord == null) { 8989 throw new SecurityException("Unknown process: " + callingPid); 8990 } 8991 if (precessRecord.instrumentationUiAutomationConnection == null) { 8992 throw new SecurityException("Only an instrumentation process " 8993 + "with a UiAutomation can call setUserIsMonkey"); 8994 } 8995 } 8996 mUserIsMonkey = userIsMonkey; 8997 } 8998 } 8999 9000 @Override 9001 public boolean isUserAMonkey() { 9002 synchronized (this) { 9003 // If there is a controller also implies the user is a monkey. 9004 return (mUserIsMonkey || mController != null); 9005 } 9006 } 9007 9008 public void requestBugReport() { 9009 enforceCallingPermission(android.Manifest.permission.DUMP, "requestBugReport"); 9010 SystemProperties.set("ctl.start", "bugreport"); 9011 } 9012 9013 public static long getInputDispatchingTimeoutLocked(ActivityRecord r) { 9014 return r != null ? getInputDispatchingTimeoutLocked(r.app) : KEY_DISPATCHING_TIMEOUT; 9015 } 9016 9017 public static long getInputDispatchingTimeoutLocked(ProcessRecord r) { 9018 if (r != null && (r.instrumentationClass != null || r.usingWrapper)) { 9019 return INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT; 9020 } 9021 return KEY_DISPATCHING_TIMEOUT; 9022 } 9023 9024 @Override 9025 public long inputDispatchingTimedOut(int pid, final boolean aboveSystem, String reason) { 9026 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 9027 != PackageManager.PERMISSION_GRANTED) { 9028 throw new SecurityException("Requires permission " 9029 + android.Manifest.permission.FILTER_EVENTS); 9030 } 9031 ProcessRecord proc; 9032 long timeout; 9033 synchronized (this) { 9034 synchronized (mPidsSelfLocked) { 9035 proc = mPidsSelfLocked.get(pid); 9036 } 9037 timeout = getInputDispatchingTimeoutLocked(proc); 9038 } 9039 9040 if (!inputDispatchingTimedOut(proc, null, null, aboveSystem, reason)) { 9041 return -1; 9042 } 9043 9044 return timeout; 9045 } 9046 9047 /** 9048 * Handle input dispatching timeouts. 9049 * Returns whether input dispatching should be aborted or not. 9050 */ 9051 public boolean inputDispatchingTimedOut(final ProcessRecord proc, 9052 final ActivityRecord activity, final ActivityRecord parent, 9053 final boolean aboveSystem, String reason) { 9054 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 9055 != PackageManager.PERMISSION_GRANTED) { 9056 throw new SecurityException("Requires permission " 9057 + android.Manifest.permission.FILTER_EVENTS); 9058 } 9059 9060 final String annotation; 9061 if (reason == null) { 9062 annotation = "Input dispatching timed out"; 9063 } else { 9064 annotation = "Input dispatching timed out (" + reason + ")"; 9065 } 9066 9067 if (proc != null) { 9068 synchronized (this) { 9069 if (proc.debugging) { 9070 return false; 9071 } 9072 9073 if (mDidDexOpt) { 9074 // Give more time since we were dexopting. 9075 mDidDexOpt = false; 9076 return false; 9077 } 9078 9079 if (proc.instrumentationClass != null) { 9080 Bundle info = new Bundle(); 9081 info.putString("shortMsg", "keyDispatchingTimedOut"); 9082 info.putString("longMsg", annotation); 9083 finishInstrumentationLocked(proc, Activity.RESULT_CANCELED, info); 9084 return true; 9085 } 9086 } 9087 mHandler.post(new Runnable() { 9088 @Override 9089 public void run() { 9090 appNotResponding(proc, activity, parent, aboveSystem, annotation); 9091 } 9092 }); 9093 } 9094 9095 return true; 9096 } 9097 9098 public Bundle getAssistContextExtras(int requestType) { 9099 enforceCallingPermission(android.Manifest.permission.GET_TOP_ACTIVITY_INFO, 9100 "getAssistContextExtras()"); 9101 PendingAssistExtras pae; 9102 Bundle extras = new Bundle(); 9103 synchronized (this) { 9104 ActivityRecord activity = getFocusedStack().mResumedActivity; 9105 if (activity == null) { 9106 Slog.w(TAG, "getAssistContextExtras failed: no resumed activity"); 9107 return null; 9108 } 9109 extras.putString(Intent.EXTRA_ASSIST_PACKAGE, activity.packageName); 9110 if (activity.app == null || activity.app.thread == null) { 9111 Slog.w(TAG, "getAssistContextExtras failed: no process for " + activity); 9112 return extras; 9113 } 9114 if (activity.app.pid == Binder.getCallingPid()) { 9115 Slog.w(TAG, "getAssistContextExtras failed: request process same as " + activity); 9116 return extras; 9117 } 9118 pae = new PendingAssistExtras(activity); 9119 try { 9120 activity.app.thread.requestAssistContextExtras(activity.appToken, pae, 9121 requestType); 9122 mPendingAssistExtras.add(pae); 9123 mHandler.postDelayed(pae, PENDING_ASSIST_EXTRAS_TIMEOUT); 9124 } catch (RemoteException e) { 9125 Slog.w(TAG, "getAssistContextExtras failed: crash calling " + activity); 9126 return extras; 9127 } 9128 } 9129 synchronized (pae) { 9130 while (!pae.haveResult) { 9131 try { 9132 pae.wait(); 9133 } catch (InterruptedException e) { 9134 } 9135 } 9136 if (pae.result != null) { 9137 extras.putBundle(Intent.EXTRA_ASSIST_CONTEXT, pae.result); 9138 } 9139 } 9140 synchronized (this) { 9141 mPendingAssistExtras.remove(pae); 9142 mHandler.removeCallbacks(pae); 9143 } 9144 return extras; 9145 } 9146 9147 public void reportAssistContextExtras(IBinder token, Bundle extras) { 9148 PendingAssistExtras pae = (PendingAssistExtras)token; 9149 synchronized (pae) { 9150 pae.result = extras; 9151 pae.haveResult = true; 9152 pae.notifyAll(); 9153 } 9154 } 9155 9156 public void registerProcessObserver(IProcessObserver observer) { 9157 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 9158 "registerProcessObserver()"); 9159 synchronized (this) { 9160 mProcessObservers.register(observer); 9161 } 9162 } 9163 9164 @Override 9165 public void unregisterProcessObserver(IProcessObserver observer) { 9166 synchronized (this) { 9167 mProcessObservers.unregister(observer); 9168 } 9169 } 9170 9171 @Override 9172 public boolean convertFromTranslucent(IBinder token) { 9173 final long origId = Binder.clearCallingIdentity(); 9174 try { 9175 synchronized (this) { 9176 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9177 if (r == null) { 9178 return false; 9179 } 9180 if (r.changeWindowTranslucency(true)) { 9181 mWindowManager.setAppFullscreen(token, true); 9182 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9183 return true; 9184 } 9185 return false; 9186 } 9187 } finally { 9188 Binder.restoreCallingIdentity(origId); 9189 } 9190 } 9191 9192 @Override 9193 public boolean convertToTranslucent(IBinder token, ActivityOptions options) { 9194 final long origId = Binder.clearCallingIdentity(); 9195 try { 9196 synchronized (this) { 9197 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9198 if (r == null) { 9199 return false; 9200 } 9201 if (r.changeWindowTranslucency(false)) { 9202 r.task.stack.convertToTranslucent(r, options); 9203 mWindowManager.setAppFullscreen(token, false); 9204 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9205 return true; 9206 } 9207 return false; 9208 } 9209 } finally { 9210 Binder.restoreCallingIdentity(origId); 9211 } 9212 } 9213 9214 @Override 9215 public ActivityOptions getActivityOptions(IBinder token) { 9216 final long origId = Binder.clearCallingIdentity(); 9217 try { 9218 synchronized (this) { 9219 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9220 if (r != null) { 9221 final ActivityOptions activityOptions = r.pendingOptions; 9222 r.pendingOptions = null; 9223 return activityOptions; 9224 } 9225 return null; 9226 } 9227 } finally { 9228 Binder.restoreCallingIdentity(origId); 9229 } 9230 } 9231 9232 @Override 9233 public void setImmersive(IBinder token, boolean immersive) { 9234 synchronized(this) { 9235 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9236 if (r == null) { 9237 throw new IllegalArgumentException(); 9238 } 9239 r.immersive = immersive; 9240 9241 // update associated state if we're frontmost 9242 if (r == mFocusedActivity) { 9243 if (DEBUG_IMMERSIVE) { 9244 Slog.d(TAG, "Frontmost changed immersion: "+ r); 9245 } 9246 applyUpdateLockStateLocked(r); 9247 } 9248 } 9249 } 9250 9251 @Override 9252 public boolean isImmersive(IBinder token) { 9253 synchronized (this) { 9254 ActivityRecord r = ActivityRecord.isInStackLocked(token); 9255 if (r == null) { 9256 throw new IllegalArgumentException(); 9257 } 9258 return r.immersive; 9259 } 9260 } 9261 9262 public boolean isTopActivityImmersive() { 9263 enforceNotIsolatedCaller("startActivity"); 9264 synchronized (this) { 9265 ActivityRecord r = getFocusedStack().topRunningActivityLocked(null); 9266 return (r != null) ? r.immersive : false; 9267 } 9268 } 9269 9270 public final void enterSafeMode() { 9271 synchronized(this) { 9272 // It only makes sense to do this before the system is ready 9273 // and started launching other packages. 9274 if (!mSystemReady) { 9275 try { 9276 AppGlobals.getPackageManager().enterSafeMode(); 9277 } catch (RemoteException e) { 9278 } 9279 } 9280 9281 mSafeMode = true; 9282 } 9283 } 9284 9285 public final void showSafeModeOverlay() { 9286 View v = LayoutInflater.from(mContext).inflate( 9287 com.android.internal.R.layout.safe_mode, null); 9288 WindowManager.LayoutParams lp = new WindowManager.LayoutParams(); 9289 lp.type = WindowManager.LayoutParams.TYPE_SECURE_SYSTEM_OVERLAY; 9290 lp.width = WindowManager.LayoutParams.WRAP_CONTENT; 9291 lp.height = WindowManager.LayoutParams.WRAP_CONTENT; 9292 lp.gravity = Gravity.BOTTOM | Gravity.START; 9293 lp.format = v.getBackground().getOpacity(); 9294 lp.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE 9295 | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE; 9296 lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; 9297 ((WindowManager)mContext.getSystemService( 9298 Context.WINDOW_SERVICE)).addView(v, lp); 9299 } 9300 9301 public void noteWakeupAlarm(IIntentSender sender, int sourceUid, String sourcePkg) { 9302 if (!(sender instanceof PendingIntentRecord)) { 9303 return; 9304 } 9305 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 9306 synchronized (stats) { 9307 if (mBatteryStatsService.isOnBattery()) { 9308 mBatteryStatsService.enforceCallingPermission(); 9309 PendingIntentRecord rec = (PendingIntentRecord)sender; 9310 int MY_UID = Binder.getCallingUid(); 9311 int uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid; 9312 BatteryStatsImpl.Uid.Pkg pkg = 9313 stats.getPackageStatsLocked(sourceUid >= 0 ? sourceUid : uid, 9314 sourcePkg != null ? sourcePkg : rec.key.packageName); 9315 pkg.incWakeupsLocked(); 9316 } 9317 } 9318 } 9319 9320 public boolean killPids(int[] pids, String pReason, boolean secure) { 9321 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9322 throw new SecurityException("killPids only available to the system"); 9323 } 9324 String reason = (pReason == null) ? "Unknown" : pReason; 9325 // XXX Note: don't acquire main activity lock here, because the window 9326 // manager calls in with its locks held. 9327 9328 boolean killed = false; 9329 synchronized (mPidsSelfLocked) { 9330 int[] types = new int[pids.length]; 9331 int worstType = 0; 9332 for (int i=0; i<pids.length; i++) { 9333 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 9334 if (proc != null) { 9335 int type = proc.setAdj; 9336 types[i] = type; 9337 if (type > worstType) { 9338 worstType = type; 9339 } 9340 } 9341 } 9342 9343 // If the worst oom_adj is somewhere in the cached proc LRU range, 9344 // then constrain it so we will kill all cached procs. 9345 if (worstType < ProcessList.CACHED_APP_MAX_ADJ 9346 && worstType > ProcessList.CACHED_APP_MIN_ADJ) { 9347 worstType = ProcessList.CACHED_APP_MIN_ADJ; 9348 } 9349 9350 // If this is not a secure call, don't let it kill processes that 9351 // are important. 9352 if (!secure && worstType < ProcessList.SERVICE_ADJ) { 9353 worstType = ProcessList.SERVICE_ADJ; 9354 } 9355 9356 Slog.w(TAG, "Killing processes " + reason + " at adjustment " + worstType); 9357 for (int i=0; i<pids.length; i++) { 9358 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 9359 if (proc == null) { 9360 continue; 9361 } 9362 int adj = proc.setAdj; 9363 if (adj >= worstType && !proc.killedByAm) { 9364 killUnneededProcessLocked(proc, reason); 9365 killed = true; 9366 } 9367 } 9368 } 9369 return killed; 9370 } 9371 9372 @Override 9373 public void killUid(int uid, String reason) { 9374 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9375 throw new SecurityException("killUid only available to the system"); 9376 } 9377 synchronized (this) { 9378 killPackageProcessesLocked(null, UserHandle.getAppId(uid), UserHandle.getUserId(uid), 9379 ProcessList.FOREGROUND_APP_ADJ-1, false, true, true, false, 9380 reason != null ? reason : "kill uid"); 9381 } 9382 } 9383 9384 @Override 9385 public boolean killProcessesBelowForeground(String reason) { 9386 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9387 throw new SecurityException("killProcessesBelowForeground() only available to system"); 9388 } 9389 9390 return killProcessesBelowAdj(ProcessList.FOREGROUND_APP_ADJ, reason); 9391 } 9392 9393 private boolean killProcessesBelowAdj(int belowAdj, String reason) { 9394 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9395 throw new SecurityException("killProcessesBelowAdj() only available to system"); 9396 } 9397 9398 boolean killed = false; 9399 synchronized (mPidsSelfLocked) { 9400 final int size = mPidsSelfLocked.size(); 9401 for (int i = 0; i < size; i++) { 9402 final int pid = mPidsSelfLocked.keyAt(i); 9403 final ProcessRecord proc = mPidsSelfLocked.valueAt(i); 9404 if (proc == null) continue; 9405 9406 final int adj = proc.setAdj; 9407 if (adj > belowAdj && !proc.killedByAm) { 9408 killUnneededProcessLocked(proc, reason); 9409 killed = true; 9410 } 9411 } 9412 } 9413 return killed; 9414 } 9415 9416 @Override 9417 public void hang(final IBinder who, boolean allowRestart) { 9418 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9419 != PackageManager.PERMISSION_GRANTED) { 9420 throw new SecurityException("Requires permission " 9421 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9422 } 9423 9424 final IBinder.DeathRecipient death = new DeathRecipient() { 9425 @Override 9426 public void binderDied() { 9427 synchronized (this) { 9428 notifyAll(); 9429 } 9430 } 9431 }; 9432 9433 try { 9434 who.linkToDeath(death, 0); 9435 } catch (RemoteException e) { 9436 Slog.w(TAG, "hang: given caller IBinder is already dead."); 9437 return; 9438 } 9439 9440 synchronized (this) { 9441 Watchdog.getInstance().setAllowRestart(allowRestart); 9442 Slog.i(TAG, "Hanging system process at request of pid " + Binder.getCallingPid()); 9443 synchronized (death) { 9444 while (who.isBinderAlive()) { 9445 try { 9446 death.wait(); 9447 } catch (InterruptedException e) { 9448 } 9449 } 9450 } 9451 Watchdog.getInstance().setAllowRestart(true); 9452 } 9453 } 9454 9455 @Override 9456 public void restart() { 9457 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9458 != PackageManager.PERMISSION_GRANTED) { 9459 throw new SecurityException("Requires permission " 9460 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9461 } 9462 9463 Log.i(TAG, "Sending shutdown broadcast..."); 9464 9465 BroadcastReceiver br = new BroadcastReceiver() { 9466 @Override public void onReceive(Context context, Intent intent) { 9467 // Now the broadcast is done, finish up the low-level shutdown. 9468 Log.i(TAG, "Shutting down activity manager..."); 9469 shutdown(10000); 9470 Log.i(TAG, "Shutdown complete, restarting!"); 9471 Process.killProcess(Process.myPid()); 9472 System.exit(10); 9473 } 9474 }; 9475 9476 // First send the high-level shut down broadcast. 9477 Intent intent = new Intent(Intent.ACTION_SHUTDOWN); 9478 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 9479 intent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 9480 /* For now we are not doing a clean shutdown, because things seem to get unhappy. 9481 mContext.sendOrderedBroadcastAsUser(intent, 9482 UserHandle.ALL, null, br, mHandler, 0, null, null); 9483 */ 9484 br.onReceive(mContext, intent); 9485 } 9486 9487 private long getLowRamTimeSinceIdle(long now) { 9488 return mLowRamTimeSinceLastIdle + (mLowRamStartTime > 0 ? (now-mLowRamStartTime) : 0); 9489 } 9490 9491 @Override 9492 public void performIdleMaintenance() { 9493 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9494 != PackageManager.PERMISSION_GRANTED) { 9495 throw new SecurityException("Requires permission " 9496 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9497 } 9498 9499 synchronized (this) { 9500 final long now = SystemClock.uptimeMillis(); 9501 final long timeSinceLastIdle = now - mLastIdleTime; 9502 final long lowRamSinceLastIdle = getLowRamTimeSinceIdle(now); 9503 mLastIdleTime = now; 9504 mLowRamTimeSinceLastIdle = 0; 9505 if (mLowRamStartTime != 0) { 9506 mLowRamStartTime = now; 9507 } 9508 9509 StringBuilder sb = new StringBuilder(128); 9510 sb.append("Idle maintenance over "); 9511 TimeUtils.formatDuration(timeSinceLastIdle, sb); 9512 sb.append(" low RAM for "); 9513 TimeUtils.formatDuration(lowRamSinceLastIdle, sb); 9514 Slog.i(TAG, sb.toString()); 9515 9516 // If at least 1/3 of our time since the last idle period has been spent 9517 // with RAM low, then we want to kill processes. 9518 boolean doKilling = lowRamSinceLastIdle > (timeSinceLastIdle/3); 9519 9520 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 9521 ProcessRecord proc = mLruProcesses.get(i); 9522 if (proc.notCachedSinceIdle) { 9523 if (proc.setProcState > ActivityManager.PROCESS_STATE_TOP 9524 && proc.setProcState <= ActivityManager.PROCESS_STATE_SERVICE) { 9525 if (doKilling && proc.initialIdlePss != 0 9526 && proc.lastPss > ((proc.initialIdlePss*3)/2)) { 9527 killUnneededProcessLocked(proc, "idle maint (pss " + proc.lastPss 9528 + " from " + proc.initialIdlePss + ")"); 9529 } 9530 } 9531 } else if (proc.setProcState < ActivityManager.PROCESS_STATE_HOME) { 9532 proc.notCachedSinceIdle = true; 9533 proc.initialIdlePss = 0; 9534 proc.nextPssTime = ProcessList.computeNextPssTime(proc.curProcState, true, 9535 isSleeping(), now); 9536 } 9537 } 9538 9539 mHandler.removeMessages(REQUEST_ALL_PSS_MSG); 9540 mHandler.sendEmptyMessageDelayed(REQUEST_ALL_PSS_MSG, 2*60*1000); 9541 } 9542 } 9543 9544 private void retrieveSettings() { 9545 final ContentResolver resolver = mContext.getContentResolver(); 9546 String debugApp = Settings.Global.getString( 9547 resolver, Settings.Global.DEBUG_APP); 9548 boolean waitForDebugger = Settings.Global.getInt( 9549 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 0) != 0; 9550 boolean alwaysFinishActivities = Settings.Global.getInt( 9551 resolver, Settings.Global.ALWAYS_FINISH_ACTIVITIES, 0) != 0; 9552 boolean forceRtl = Settings.Global.getInt( 9553 resolver, Settings.Global.DEVELOPMENT_FORCE_RTL, 0) != 0; 9554 // Transfer any global setting for forcing RTL layout, into a System Property 9555 SystemProperties.set(Settings.Global.DEVELOPMENT_FORCE_RTL, forceRtl ? "1":"0"); 9556 9557 Configuration configuration = new Configuration(); 9558 Settings.System.getConfiguration(resolver, configuration); 9559 if (forceRtl) { 9560 // This will take care of setting the correct layout direction flags 9561 configuration.setLayoutDirection(configuration.locale); 9562 } 9563 9564 synchronized (this) { 9565 mDebugApp = mOrigDebugApp = debugApp; 9566 mWaitForDebugger = mOrigWaitForDebugger = waitForDebugger; 9567 mAlwaysFinishActivities = alwaysFinishActivities; 9568 // This happens before any activities are started, so we can 9569 // change mConfiguration in-place. 9570 updateConfigurationLocked(configuration, null, false, true); 9571 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Initial config: " + mConfiguration); 9572 } 9573 } 9574 9575 public boolean testIsSystemReady() { 9576 // no need to synchronize(this) just to read & return the value 9577 return mSystemReady; 9578 } 9579 9580 private static File getCalledPreBootReceiversFile() { 9581 File dataDir = Environment.getDataDirectory(); 9582 File systemDir = new File(dataDir, "system"); 9583 File fname = new File(systemDir, "called_pre_boots.dat"); 9584 return fname; 9585 } 9586 9587 static final int LAST_DONE_VERSION = 10000; 9588 9589 private static ArrayList<ComponentName> readLastDonePreBootReceivers() { 9590 ArrayList<ComponentName> lastDoneReceivers = new ArrayList<ComponentName>(); 9591 File file = getCalledPreBootReceiversFile(); 9592 FileInputStream fis = null; 9593 try { 9594 fis = new FileInputStream(file); 9595 DataInputStream dis = new DataInputStream(new BufferedInputStream(fis, 2048)); 9596 int fvers = dis.readInt(); 9597 if (fvers == LAST_DONE_VERSION) { 9598 String vers = dis.readUTF(); 9599 String codename = dis.readUTF(); 9600 String build = dis.readUTF(); 9601 if (android.os.Build.VERSION.RELEASE.equals(vers) 9602 && android.os.Build.VERSION.CODENAME.equals(codename) 9603 && android.os.Build.VERSION.INCREMENTAL.equals(build)) { 9604 int num = dis.readInt(); 9605 while (num > 0) { 9606 num--; 9607 String pkg = dis.readUTF(); 9608 String cls = dis.readUTF(); 9609 lastDoneReceivers.add(new ComponentName(pkg, cls)); 9610 } 9611 } 9612 } 9613 } catch (FileNotFoundException e) { 9614 } catch (IOException e) { 9615 Slog.w(TAG, "Failure reading last done pre-boot receivers", e); 9616 } finally { 9617 if (fis != null) { 9618 try { 9619 fis.close(); 9620 } catch (IOException e) { 9621 } 9622 } 9623 } 9624 return lastDoneReceivers; 9625 } 9626 9627 private static void writeLastDonePreBootReceivers(ArrayList<ComponentName> list) { 9628 File file = getCalledPreBootReceiversFile(); 9629 FileOutputStream fos = null; 9630 DataOutputStream dos = null; 9631 try { 9632 Slog.i(TAG, "Writing new set of last done pre-boot receivers..."); 9633 fos = new FileOutputStream(file); 9634 dos = new DataOutputStream(new BufferedOutputStream(fos, 2048)); 9635 dos.writeInt(LAST_DONE_VERSION); 9636 dos.writeUTF(android.os.Build.VERSION.RELEASE); 9637 dos.writeUTF(android.os.Build.VERSION.CODENAME); 9638 dos.writeUTF(android.os.Build.VERSION.INCREMENTAL); 9639 dos.writeInt(list.size()); 9640 for (int i=0; i<list.size(); i++) { 9641 dos.writeUTF(list.get(i).getPackageName()); 9642 dos.writeUTF(list.get(i).getClassName()); 9643 } 9644 } catch (IOException e) { 9645 Slog.w(TAG, "Failure writing last done pre-boot receivers", e); 9646 file.delete(); 9647 } finally { 9648 FileUtils.sync(fos); 9649 if (dos != null) { 9650 try { 9651 dos.close(); 9652 } catch (IOException e) { 9653 // TODO Auto-generated catch block 9654 e.printStackTrace(); 9655 } 9656 } 9657 } 9658 } 9659 9660 public void systemReady(final Runnable goingCallback) { 9661 synchronized(this) { 9662 if (mSystemReady) { 9663 if (goingCallback != null) goingCallback.run(); 9664 return; 9665 } 9666 9667 if (mRecentTasks == null) { 9668 mRecentTasks = mTaskPersister.restoreTasksLocked(); 9669 if (!mRecentTasks.isEmpty()) { 9670 mStackSupervisor.createStackForRestoredTaskHistory(mRecentTasks); 9671 } 9672 mTaskPersister.startPersisting(); 9673 } 9674 9675 // Check to see if there are any update receivers to run. 9676 if (!mDidUpdate) { 9677 if (mWaitingUpdate) { 9678 return; 9679 } 9680 Intent intent = new Intent(Intent.ACTION_PRE_BOOT_COMPLETED); 9681 List<ResolveInfo> ris = null; 9682 try { 9683 ris = AppGlobals.getPackageManager().queryIntentReceivers( 9684 intent, null, 0, 0); 9685 } catch (RemoteException e) { 9686 } 9687 if (ris != null) { 9688 for (int i=ris.size()-1; i>=0; i--) { 9689 if ((ris.get(i).activityInfo.applicationInfo.flags 9690 &ApplicationInfo.FLAG_SYSTEM) == 0) { 9691 ris.remove(i); 9692 } 9693 } 9694 intent.addFlags(Intent.FLAG_RECEIVER_BOOT_UPGRADE); 9695 9696 ArrayList<ComponentName> lastDoneReceivers = readLastDonePreBootReceivers(); 9697 9698 final ArrayList<ComponentName> doneReceivers = new ArrayList<ComponentName>(); 9699 for (int i=0; i<ris.size(); i++) { 9700 ActivityInfo ai = ris.get(i).activityInfo; 9701 ComponentName comp = new ComponentName(ai.packageName, ai.name); 9702 if (lastDoneReceivers.contains(comp)) { 9703 // We already did the pre boot receiver for this app with the current 9704 // platform version, so don't do it again... 9705 ris.remove(i); 9706 i--; 9707 // ...however, do keep it as one that has been done, so we don't 9708 // forget about it when rewriting the file of last done receivers. 9709 doneReceivers.add(comp); 9710 } 9711 } 9712 9713 final int[] users = getUsersLocked(); 9714 for (int i=0; i<ris.size(); i++) { 9715 ActivityInfo ai = ris.get(i).activityInfo; 9716 ComponentName comp = new ComponentName(ai.packageName, ai.name); 9717 doneReceivers.add(comp); 9718 intent.setComponent(comp); 9719 for (int j=0; j<users.length; j++) { 9720 IIntentReceiver finisher = null; 9721 if (i == ris.size()-1 && j == users.length-1) { 9722 finisher = new IIntentReceiver.Stub() { 9723 public void performReceive(Intent intent, int resultCode, 9724 String data, Bundle extras, boolean ordered, 9725 boolean sticky, int sendingUser) { 9726 // The raw IIntentReceiver interface is called 9727 // with the AM lock held, so redispatch to 9728 // execute our code without the lock. 9729 mHandler.post(new Runnable() { 9730 public void run() { 9731 synchronized (ActivityManagerService.this) { 9732 mDidUpdate = true; 9733 } 9734 writeLastDonePreBootReceivers(doneReceivers); 9735 showBootMessage(mContext.getText( 9736 R.string.android_upgrading_complete), 9737 false); 9738 systemReady(goingCallback); 9739 } 9740 }); 9741 } 9742 }; 9743 } 9744 Slog.i(TAG, "Sending system update to " + intent.getComponent() 9745 + " for user " + users[j]); 9746 broadcastIntentLocked(null, null, intent, null, finisher, 9747 0, null, null, null, AppOpsManager.OP_NONE, 9748 true, false, MY_PID, Process.SYSTEM_UID, 9749 users[j]); 9750 if (finisher != null) { 9751 mWaitingUpdate = true; 9752 } 9753 } 9754 } 9755 } 9756 if (mWaitingUpdate) { 9757 return; 9758 } 9759 mDidUpdate = true; 9760 } 9761 9762 mAppOpsService.systemReady(); 9763 mUsageStatsService.systemReady(); 9764 mSystemReady = true; 9765 } 9766 9767 ArrayList<ProcessRecord> procsToKill = null; 9768 synchronized(mPidsSelfLocked) { 9769 for (int i=mPidsSelfLocked.size()-1; i>=0; i--) { 9770 ProcessRecord proc = mPidsSelfLocked.valueAt(i); 9771 if (!isAllowedWhileBooting(proc.info)){ 9772 if (procsToKill == null) { 9773 procsToKill = new ArrayList<ProcessRecord>(); 9774 } 9775 procsToKill.add(proc); 9776 } 9777 } 9778 } 9779 9780 synchronized(this) { 9781 if (procsToKill != null) { 9782 for (int i=procsToKill.size()-1; i>=0; i--) { 9783 ProcessRecord proc = procsToKill.get(i); 9784 Slog.i(TAG, "Removing system update proc: " + proc); 9785 removeProcessLocked(proc, true, false, "system update done"); 9786 } 9787 } 9788 9789 // Now that we have cleaned up any update processes, we 9790 // are ready to start launching real processes and know that 9791 // we won't trample on them any more. 9792 mProcessesReady = true; 9793 } 9794 9795 Slog.i(TAG, "System now ready"); 9796 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_AMS_READY, 9797 SystemClock.uptimeMillis()); 9798 9799 synchronized(this) { 9800 // Make sure we have no pre-ready processes sitting around. 9801 9802 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) { 9803 ResolveInfo ri = mContext.getPackageManager() 9804 .resolveActivity(new Intent(Intent.ACTION_FACTORY_TEST), 9805 STOCK_PM_FLAGS); 9806 CharSequence errorMsg = null; 9807 if (ri != null) { 9808 ActivityInfo ai = ri.activityInfo; 9809 ApplicationInfo app = ai.applicationInfo; 9810 if ((app.flags&ApplicationInfo.FLAG_SYSTEM) != 0) { 9811 mTopAction = Intent.ACTION_FACTORY_TEST; 9812 mTopData = null; 9813 mTopComponent = new ComponentName(app.packageName, 9814 ai.name); 9815 } else { 9816 errorMsg = mContext.getResources().getText( 9817 com.android.internal.R.string.factorytest_not_system); 9818 } 9819 } else { 9820 errorMsg = mContext.getResources().getText( 9821 com.android.internal.R.string.factorytest_no_action); 9822 } 9823 if (errorMsg != null) { 9824 mTopAction = null; 9825 mTopData = null; 9826 mTopComponent = null; 9827 Message msg = Message.obtain(); 9828 msg.what = SHOW_FACTORY_ERROR_MSG; 9829 msg.getData().putCharSequence("msg", errorMsg); 9830 mHandler.sendMessage(msg); 9831 } 9832 } 9833 } 9834 9835 retrieveSettings(); 9836 9837 synchronized (this) { 9838 readGrantedUriPermissionsLocked(); 9839 } 9840 9841 if (goingCallback != null) goingCallback.run(); 9842 9843 mSystemServiceManager.startUser(mCurrentUserId); 9844 9845 synchronized (this) { 9846 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 9847 try { 9848 List apps = AppGlobals.getPackageManager(). 9849 getPersistentApplications(STOCK_PM_FLAGS); 9850 if (apps != null) { 9851 int N = apps.size(); 9852 int i; 9853 for (i=0; i<N; i++) { 9854 ApplicationInfo info 9855 = (ApplicationInfo)apps.get(i); 9856 if (info != null && 9857 !info.packageName.equals("android")) { 9858 addAppLocked(info, false, null /* ABI override */); 9859 } 9860 } 9861 } 9862 } catch (RemoteException ex) { 9863 // pm is in same process, this will never happen. 9864 } 9865 } 9866 9867 // Start up initial activity. 9868 mBooting = true; 9869 9870 try { 9871 if (AppGlobals.getPackageManager().hasSystemUidErrors()) { 9872 Message msg = Message.obtain(); 9873 msg.what = SHOW_UID_ERROR_MSG; 9874 mHandler.sendMessage(msg); 9875 } 9876 } catch (RemoteException e) { 9877 } 9878 9879 long ident = Binder.clearCallingIdentity(); 9880 try { 9881 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 9882 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 9883 | Intent.FLAG_RECEIVER_FOREGROUND); 9884 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 9885 broadcastIntentLocked(null, null, intent, 9886 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 9887 false, false, MY_PID, Process.SYSTEM_UID, mCurrentUserId); 9888 intent = new Intent(Intent.ACTION_USER_STARTING); 9889 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 9890 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 9891 broadcastIntentLocked(null, null, intent, 9892 null, new IIntentReceiver.Stub() { 9893 @Override 9894 public void performReceive(Intent intent, int resultCode, String data, 9895 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 9896 throws RemoteException { 9897 } 9898 }, 0, null, null, 9899 android.Manifest.permission.INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 9900 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 9901 } catch (Throwable t) { 9902 Slog.wtf(TAG, "Failed sending first user broadcasts", t); 9903 } finally { 9904 Binder.restoreCallingIdentity(ident); 9905 } 9906 mStackSupervisor.resumeTopActivitiesLocked(); 9907 sendUserSwitchBroadcastsLocked(-1, mCurrentUserId); 9908 } 9909 } 9910 9911 private boolean makeAppCrashingLocked(ProcessRecord app, 9912 String shortMsg, String longMsg, String stackTrace) { 9913 app.crashing = true; 9914 app.crashingReport = generateProcessError(app, 9915 ActivityManager.ProcessErrorStateInfo.CRASHED, null, shortMsg, longMsg, stackTrace); 9916 startAppProblemLocked(app); 9917 app.stopFreezingAllLocked(); 9918 return handleAppCrashLocked(app, shortMsg, longMsg, stackTrace); 9919 } 9920 9921 private void makeAppNotRespondingLocked(ProcessRecord app, 9922 String activity, String shortMsg, String longMsg) { 9923 app.notResponding = true; 9924 app.notRespondingReport = generateProcessError(app, 9925 ActivityManager.ProcessErrorStateInfo.NOT_RESPONDING, 9926 activity, shortMsg, longMsg, null); 9927 startAppProblemLocked(app); 9928 app.stopFreezingAllLocked(); 9929 } 9930 9931 /** 9932 * Generate a process error record, suitable for attachment to a ProcessRecord. 9933 * 9934 * @param app The ProcessRecord in which the error occurred. 9935 * @param condition Crashing, Application Not Responding, etc. Values are defined in 9936 * ActivityManager.AppErrorStateInfo 9937 * @param activity The activity associated with the crash, if known. 9938 * @param shortMsg Short message describing the crash. 9939 * @param longMsg Long message describing the crash. 9940 * @param stackTrace Full crash stack trace, may be null. 9941 * 9942 * @return Returns a fully-formed AppErrorStateInfo record. 9943 */ 9944 private ActivityManager.ProcessErrorStateInfo generateProcessError(ProcessRecord app, 9945 int condition, String activity, String shortMsg, String longMsg, String stackTrace) { 9946 ActivityManager.ProcessErrorStateInfo report = new ActivityManager.ProcessErrorStateInfo(); 9947 9948 report.condition = condition; 9949 report.processName = app.processName; 9950 report.pid = app.pid; 9951 report.uid = app.info.uid; 9952 report.tag = activity; 9953 report.shortMsg = shortMsg; 9954 report.longMsg = longMsg; 9955 report.stackTrace = stackTrace; 9956 9957 return report; 9958 } 9959 9960 void killAppAtUsersRequest(ProcessRecord app, Dialog fromDialog) { 9961 synchronized (this) { 9962 app.crashing = false; 9963 app.crashingReport = null; 9964 app.notResponding = false; 9965 app.notRespondingReport = null; 9966 if (app.anrDialog == fromDialog) { 9967 app.anrDialog = null; 9968 } 9969 if (app.waitDialog == fromDialog) { 9970 app.waitDialog = null; 9971 } 9972 if (app.pid > 0 && app.pid != MY_PID) { 9973 handleAppCrashLocked(app, null, null, null); 9974 killUnneededProcessLocked(app, "user request after error"); 9975 } 9976 } 9977 } 9978 9979 private boolean handleAppCrashLocked(ProcessRecord app, String shortMsg, String longMsg, 9980 String stackTrace) { 9981 long now = SystemClock.uptimeMillis(); 9982 9983 Long crashTime; 9984 if (!app.isolated) { 9985 crashTime = mProcessCrashTimes.get(app.info.processName, app.uid); 9986 } else { 9987 crashTime = null; 9988 } 9989 if (crashTime != null && now < crashTime+ProcessList.MIN_CRASH_INTERVAL) { 9990 // This process loses! 9991 Slog.w(TAG, "Process " + app.info.processName 9992 + " has crashed too many times: killing!"); 9993 EventLog.writeEvent(EventLogTags.AM_PROCESS_CRASHED_TOO_MUCH, 9994 app.userId, app.info.processName, app.uid); 9995 mStackSupervisor.handleAppCrashLocked(app); 9996 if (!app.persistent) { 9997 // We don't want to start this process again until the user 9998 // explicitly does so... but for persistent process, we really 9999 // need to keep it running. If a persistent process is actually 10000 // repeatedly crashing, then badness for everyone. 10001 EventLog.writeEvent(EventLogTags.AM_PROC_BAD, app.userId, app.uid, 10002 app.info.processName); 10003 if (!app.isolated) { 10004 // XXX We don't have a way to mark isolated processes 10005 // as bad, since they don't have a peristent identity. 10006 mBadProcesses.put(app.info.processName, app.uid, 10007 new BadProcessInfo(now, shortMsg, longMsg, stackTrace)); 10008 mProcessCrashTimes.remove(app.info.processName, app.uid); 10009 } 10010 app.bad = true; 10011 app.removed = true; 10012 // Don't let services in this process be restarted and potentially 10013 // annoy the user repeatedly. Unless it is persistent, since those 10014 // processes run critical code. 10015 removeProcessLocked(app, false, false, "crash"); 10016 mStackSupervisor.resumeTopActivitiesLocked(); 10017 return false; 10018 } 10019 mStackSupervisor.resumeTopActivitiesLocked(); 10020 } else { 10021 mStackSupervisor.finishTopRunningActivityLocked(app); 10022 } 10023 10024 // Bump up the crash count of any services currently running in the proc. 10025 for (int i=app.services.size()-1; i>=0; i--) { 10026 // Any services running in the application need to be placed 10027 // back in the pending list. 10028 ServiceRecord sr = app.services.valueAt(i); 10029 sr.crashCount++; 10030 } 10031 10032 // If the crashing process is what we consider to be the "home process" and it has been 10033 // replaced by a third-party app, clear the package preferred activities from packages 10034 // with a home activity running in the process to prevent a repeatedly crashing app 10035 // from blocking the user to manually clear the list. 10036 final ArrayList<ActivityRecord> activities = app.activities; 10037 if (app == mHomeProcess && activities.size() > 0 10038 && (mHomeProcess.info.flags & ApplicationInfo.FLAG_SYSTEM) == 0) { 10039 for (int activityNdx = activities.size() - 1; activityNdx >= 0; --activityNdx) { 10040 final ActivityRecord r = activities.get(activityNdx); 10041 if (r.isHomeActivity()) { 10042 Log.i(TAG, "Clearing package preferred activities from " + r.packageName); 10043 try { 10044 ActivityThread.getPackageManager() 10045 .clearPackagePreferredActivities(r.packageName); 10046 } catch (RemoteException c) { 10047 // pm is in same process, this will never happen. 10048 } 10049 } 10050 } 10051 } 10052 10053 if (!app.isolated) { 10054 // XXX Can't keep track of crash times for isolated processes, 10055 // because they don't have a perisistent identity. 10056 mProcessCrashTimes.put(app.info.processName, app.uid, now); 10057 } 10058 10059 return true; 10060 } 10061 10062 void startAppProblemLocked(ProcessRecord app) { 10063 if (app.userId == mCurrentUserId) { 10064 app.errorReportReceiver = ApplicationErrorReport.getErrorReportReceiver( 10065 mContext, app.info.packageName, app.info.flags); 10066 } else { 10067 // If this app is not running under the current user, then we 10068 // can't give it a report button because that would require 10069 // launching the report UI under a different user. 10070 app.errorReportReceiver = null; 10071 } 10072 skipCurrentReceiverLocked(app); 10073 } 10074 10075 void skipCurrentReceiverLocked(ProcessRecord app) { 10076 for (BroadcastQueue queue : mBroadcastQueues) { 10077 queue.skipCurrentReceiverLocked(app); 10078 } 10079 } 10080 10081 /** 10082 * Used by {@link com.android.internal.os.RuntimeInit} to report when an application crashes. 10083 * The application process will exit immediately after this call returns. 10084 * @param app object of the crashing app, null for the system server 10085 * @param crashInfo describing the exception 10086 */ 10087 public void handleApplicationCrash(IBinder app, ApplicationErrorReport.CrashInfo crashInfo) { 10088 ProcessRecord r = findAppProcess(app, "Crash"); 10089 final String processName = app == null ? "system_server" 10090 : (r == null ? "unknown" : r.processName); 10091 10092 handleApplicationCrashInner("crash", r, processName, crashInfo); 10093 } 10094 10095 /* Native crash reporting uses this inner version because it needs to be somewhat 10096 * decoupled from the AM-managed cleanup lifecycle 10097 */ 10098 void handleApplicationCrashInner(String eventType, ProcessRecord r, String processName, 10099 ApplicationErrorReport.CrashInfo crashInfo) { 10100 EventLog.writeEvent(EventLogTags.AM_CRASH, Binder.getCallingPid(), 10101 UserHandle.getUserId(Binder.getCallingUid()), processName, 10102 r == null ? -1 : r.info.flags, 10103 crashInfo.exceptionClassName, 10104 crashInfo.exceptionMessage, 10105 crashInfo.throwFileName, 10106 crashInfo.throwLineNumber); 10107 10108 addErrorToDropBox(eventType, r, processName, null, null, null, null, null, crashInfo); 10109 10110 crashApplication(r, crashInfo); 10111 } 10112 10113 public void handleApplicationStrictModeViolation( 10114 IBinder app, 10115 int violationMask, 10116 StrictMode.ViolationInfo info) { 10117 ProcessRecord r = findAppProcess(app, "StrictMode"); 10118 if (r == null) { 10119 return; 10120 } 10121 10122 if ((violationMask & StrictMode.PENALTY_DROPBOX) != 0) { 10123 Integer stackFingerprint = info.hashCode(); 10124 boolean logIt = true; 10125 synchronized (mAlreadyLoggedViolatedStacks) { 10126 if (mAlreadyLoggedViolatedStacks.contains(stackFingerprint)) { 10127 logIt = false; 10128 // TODO: sub-sample into EventLog for these, with 10129 // the info.durationMillis? Then we'd get 10130 // the relative pain numbers, without logging all 10131 // the stack traces repeatedly. We'd want to do 10132 // likewise in the client code, which also does 10133 // dup suppression, before the Binder call. 10134 } else { 10135 if (mAlreadyLoggedViolatedStacks.size() >= MAX_DUP_SUPPRESSED_STACKS) { 10136 mAlreadyLoggedViolatedStacks.clear(); 10137 } 10138 mAlreadyLoggedViolatedStacks.add(stackFingerprint); 10139 } 10140 } 10141 if (logIt) { 10142 logStrictModeViolationToDropBox(r, info); 10143 } 10144 } 10145 10146 if ((violationMask & StrictMode.PENALTY_DIALOG) != 0) { 10147 AppErrorResult result = new AppErrorResult(); 10148 synchronized (this) { 10149 final long origId = Binder.clearCallingIdentity(); 10150 10151 Message msg = Message.obtain(); 10152 msg.what = SHOW_STRICT_MODE_VIOLATION_MSG; 10153 HashMap<String, Object> data = new HashMap<String, Object>(); 10154 data.put("result", result); 10155 data.put("app", r); 10156 data.put("violationMask", violationMask); 10157 data.put("info", info); 10158 msg.obj = data; 10159 mHandler.sendMessage(msg); 10160 10161 Binder.restoreCallingIdentity(origId); 10162 } 10163 int res = result.get(); 10164 Slog.w(TAG, "handleApplicationStrictModeViolation; res=" + res); 10165 } 10166 } 10167 10168 // Depending on the policy in effect, there could be a bunch of 10169 // these in quick succession so we try to batch these together to 10170 // minimize disk writes, number of dropbox entries, and maximize 10171 // compression, by having more fewer, larger records. 10172 private void logStrictModeViolationToDropBox( 10173 ProcessRecord process, 10174 StrictMode.ViolationInfo info) { 10175 if (info == null) { 10176 return; 10177 } 10178 final boolean isSystemApp = process == null || 10179 (process.info.flags & (ApplicationInfo.FLAG_SYSTEM | 10180 ApplicationInfo.FLAG_UPDATED_SYSTEM_APP)) != 0; 10181 final String processName = process == null ? "unknown" : process.processName; 10182 final String dropboxTag = isSystemApp ? "system_app_strictmode" : "data_app_strictmode"; 10183 final DropBoxManager dbox = (DropBoxManager) 10184 mContext.getSystemService(Context.DROPBOX_SERVICE); 10185 10186 // Exit early if the dropbox isn't configured to accept this report type. 10187 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 10188 10189 boolean bufferWasEmpty; 10190 boolean needsFlush; 10191 final StringBuilder sb = isSystemApp ? mStrictModeBuffer : new StringBuilder(1024); 10192 synchronized (sb) { 10193 bufferWasEmpty = sb.length() == 0; 10194 appendDropBoxProcessHeaders(process, processName, sb); 10195 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 10196 sb.append("System-App: ").append(isSystemApp).append("\n"); 10197 sb.append("Uptime-Millis: ").append(info.violationUptimeMillis).append("\n"); 10198 if (info.violationNumThisLoop != 0) { 10199 sb.append("Loop-Violation-Number: ").append(info.violationNumThisLoop).append("\n"); 10200 } 10201 if (info.numAnimationsRunning != 0) { 10202 sb.append("Animations-Running: ").append(info.numAnimationsRunning).append("\n"); 10203 } 10204 if (info.broadcastIntentAction != null) { 10205 sb.append("Broadcast-Intent-Action: ").append(info.broadcastIntentAction).append("\n"); 10206 } 10207 if (info.durationMillis != -1) { 10208 sb.append("Duration-Millis: ").append(info.durationMillis).append("\n"); 10209 } 10210 if (info.numInstances != -1) { 10211 sb.append("Instance-Count: ").append(info.numInstances).append("\n"); 10212 } 10213 if (info.tags != null) { 10214 for (String tag : info.tags) { 10215 sb.append("Span-Tag: ").append(tag).append("\n"); 10216 } 10217 } 10218 sb.append("\n"); 10219 if (info.crashInfo != null && info.crashInfo.stackTrace != null) { 10220 sb.append(info.crashInfo.stackTrace); 10221 } 10222 sb.append("\n"); 10223 10224 // Only buffer up to ~64k. Various logging bits truncate 10225 // things at 128k. 10226 needsFlush = (sb.length() > 64 * 1024); 10227 } 10228 10229 // Flush immediately if the buffer's grown too large, or this 10230 // is a non-system app. Non-system apps are isolated with a 10231 // different tag & policy and not batched. 10232 // 10233 // Batching is useful during internal testing with 10234 // StrictMode settings turned up high. Without batching, 10235 // thousands of separate files could be created on boot. 10236 if (!isSystemApp || needsFlush) { 10237 new Thread("Error dump: " + dropboxTag) { 10238 @Override 10239 public void run() { 10240 String report; 10241 synchronized (sb) { 10242 report = sb.toString(); 10243 sb.delete(0, sb.length()); 10244 sb.trimToSize(); 10245 } 10246 if (report.length() != 0) { 10247 dbox.addText(dropboxTag, report); 10248 } 10249 } 10250 }.start(); 10251 return; 10252 } 10253 10254 // System app batching: 10255 if (!bufferWasEmpty) { 10256 // An existing dropbox-writing thread is outstanding, so 10257 // we don't need to start it up. The existing thread will 10258 // catch the buffer appends we just did. 10259 return; 10260 } 10261 10262 // Worker thread to both batch writes and to avoid blocking the caller on I/O. 10263 // (After this point, we shouldn't access AMS internal data structures.) 10264 new Thread("Error dump: " + dropboxTag) { 10265 @Override 10266 public void run() { 10267 // 5 second sleep to let stacks arrive and be batched together 10268 try { 10269 Thread.sleep(5000); // 5 seconds 10270 } catch (InterruptedException e) {} 10271 10272 String errorReport; 10273 synchronized (mStrictModeBuffer) { 10274 errorReport = mStrictModeBuffer.toString(); 10275 if (errorReport.length() == 0) { 10276 return; 10277 } 10278 mStrictModeBuffer.delete(0, mStrictModeBuffer.length()); 10279 mStrictModeBuffer.trimToSize(); 10280 } 10281 dbox.addText(dropboxTag, errorReport); 10282 } 10283 }.start(); 10284 } 10285 10286 /** 10287 * Used by {@link Log} via {@link com.android.internal.os.RuntimeInit} to report serious errors. 10288 * @param app object of the crashing app, null for the system server 10289 * @param tag reported by the caller 10290 * @param crashInfo describing the context of the error 10291 * @return true if the process should exit immediately (WTF is fatal) 10292 */ 10293 public boolean handleApplicationWtf(IBinder app, String tag, 10294 ApplicationErrorReport.CrashInfo crashInfo) { 10295 ProcessRecord r = findAppProcess(app, "WTF"); 10296 final String processName = app == null ? "system_server" 10297 : (r == null ? "unknown" : r.processName); 10298 10299 EventLog.writeEvent(EventLogTags.AM_WTF, 10300 UserHandle.getUserId(Binder.getCallingUid()), Binder.getCallingPid(), 10301 processName, 10302 r == null ? -1 : r.info.flags, 10303 tag, crashInfo.exceptionMessage); 10304 10305 addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, crashInfo); 10306 10307 if (r != null && r.pid != Process.myPid() && 10308 Settings.Global.getInt(mContext.getContentResolver(), 10309 Settings.Global.WTF_IS_FATAL, 0) != 0) { 10310 crashApplication(r, crashInfo); 10311 return true; 10312 } else { 10313 return false; 10314 } 10315 } 10316 10317 /** 10318 * @param app object of some object (as stored in {@link com.android.internal.os.RuntimeInit}) 10319 * @return the corresponding {@link ProcessRecord} object, or null if none could be found 10320 */ 10321 private ProcessRecord findAppProcess(IBinder app, String reason) { 10322 if (app == null) { 10323 return null; 10324 } 10325 10326 synchronized (this) { 10327 final int NP = mProcessNames.getMap().size(); 10328 for (int ip=0; ip<NP; ip++) { 10329 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 10330 final int NA = apps.size(); 10331 for (int ia=0; ia<NA; ia++) { 10332 ProcessRecord p = apps.valueAt(ia); 10333 if (p.thread != null && p.thread.asBinder() == app) { 10334 return p; 10335 } 10336 } 10337 } 10338 10339 Slog.w(TAG, "Can't find mystery application for " + reason 10340 + " from pid=" + Binder.getCallingPid() 10341 + " uid=" + Binder.getCallingUid() + ": " + app); 10342 return null; 10343 } 10344 } 10345 10346 /** 10347 * Utility function for addErrorToDropBox and handleStrictModeViolation's logging 10348 * to append various headers to the dropbox log text. 10349 */ 10350 private void appendDropBoxProcessHeaders(ProcessRecord process, String processName, 10351 StringBuilder sb) { 10352 // Watchdog thread ends up invoking this function (with 10353 // a null ProcessRecord) to add the stack file to dropbox. 10354 // Do not acquire a lock on this (am) in such cases, as it 10355 // could cause a potential deadlock, if and when watchdog 10356 // is invoked due to unavailability of lock on am and it 10357 // would prevent watchdog from killing system_server. 10358 if (process == null) { 10359 sb.append("Process: ").append(processName).append("\n"); 10360 return; 10361 } 10362 // Note: ProcessRecord 'process' is guarded by the service 10363 // instance. (notably process.pkgList, which could otherwise change 10364 // concurrently during execution of this method) 10365 synchronized (this) { 10366 sb.append("Process: ").append(processName).append("\n"); 10367 int flags = process.info.flags; 10368 IPackageManager pm = AppGlobals.getPackageManager(); 10369 sb.append("Flags: 0x").append(Integer.toString(flags, 16)).append("\n"); 10370 for (int ip=0; ip<process.pkgList.size(); ip++) { 10371 String pkg = process.pkgList.keyAt(ip); 10372 sb.append("Package: ").append(pkg); 10373 try { 10374 PackageInfo pi = pm.getPackageInfo(pkg, 0, UserHandle.getCallingUserId()); 10375 if (pi != null) { 10376 sb.append(" v").append(pi.versionCode); 10377 if (pi.versionName != null) { 10378 sb.append(" (").append(pi.versionName).append(")"); 10379 } 10380 } 10381 } catch (RemoteException e) { 10382 Slog.e(TAG, "Error getting package info: " + pkg, e); 10383 } 10384 sb.append("\n"); 10385 } 10386 } 10387 } 10388 10389 private static String processClass(ProcessRecord process) { 10390 if (process == null || process.pid == MY_PID) { 10391 return "system_server"; 10392 } else if ((process.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 10393 return "system_app"; 10394 } else { 10395 return "data_app"; 10396 } 10397 } 10398 10399 /** 10400 * Write a description of an error (crash, WTF, ANR) to the drop box. 10401 * @param eventType to include in the drop box tag ("crash", "wtf", etc.) 10402 * @param process which caused the error, null means the system server 10403 * @param activity which triggered the error, null if unknown 10404 * @param parent activity related to the error, null if unknown 10405 * @param subject line related to the error, null if absent 10406 * @param report in long form describing the error, null if absent 10407 * @param logFile to include in the report, null if none 10408 * @param crashInfo giving an application stack trace, null if absent 10409 */ 10410 public void addErrorToDropBox(String eventType, 10411 ProcessRecord process, String processName, ActivityRecord activity, 10412 ActivityRecord parent, String subject, 10413 final String report, final File logFile, 10414 final ApplicationErrorReport.CrashInfo crashInfo) { 10415 // NOTE -- this must never acquire the ActivityManagerService lock, 10416 // otherwise the watchdog may be prevented from resetting the system. 10417 10418 final String dropboxTag = processClass(process) + "_" + eventType; 10419 final DropBoxManager dbox = (DropBoxManager) 10420 mContext.getSystemService(Context.DROPBOX_SERVICE); 10421 10422 // Exit early if the dropbox isn't configured to accept this report type. 10423 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 10424 10425 final StringBuilder sb = new StringBuilder(1024); 10426 appendDropBoxProcessHeaders(process, processName, sb); 10427 if (activity != null) { 10428 sb.append("Activity: ").append(activity.shortComponentName).append("\n"); 10429 } 10430 if (parent != null && parent.app != null && parent.app.pid != process.pid) { 10431 sb.append("Parent-Process: ").append(parent.app.processName).append("\n"); 10432 } 10433 if (parent != null && parent != activity) { 10434 sb.append("Parent-Activity: ").append(parent.shortComponentName).append("\n"); 10435 } 10436 if (subject != null) { 10437 sb.append("Subject: ").append(subject).append("\n"); 10438 } 10439 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 10440 if (Debug.isDebuggerConnected()) { 10441 sb.append("Debugger: Connected\n"); 10442 } 10443 sb.append("\n"); 10444 10445 // Do the rest in a worker thread to avoid blocking the caller on I/O 10446 // (After this point, we shouldn't access AMS internal data structures.) 10447 Thread worker = new Thread("Error dump: " + dropboxTag) { 10448 @Override 10449 public void run() { 10450 if (report != null) { 10451 sb.append(report); 10452 } 10453 if (logFile != null) { 10454 try { 10455 sb.append(FileUtils.readTextFile(logFile, DROPBOX_MAX_SIZE, 10456 "\n\n[[TRUNCATED]]")); 10457 } catch (IOException e) { 10458 Slog.e(TAG, "Error reading " + logFile, e); 10459 } 10460 } 10461 if (crashInfo != null && crashInfo.stackTrace != null) { 10462 sb.append(crashInfo.stackTrace); 10463 } 10464 10465 String setting = Settings.Global.ERROR_LOGCAT_PREFIX + dropboxTag; 10466 int lines = Settings.Global.getInt(mContext.getContentResolver(), setting, 0); 10467 if (lines > 0) { 10468 sb.append("\n"); 10469 10470 // Merge several logcat streams, and take the last N lines 10471 InputStreamReader input = null; 10472 try { 10473 java.lang.Process logcat = new ProcessBuilder("/system/bin/logcat", 10474 "-v", "time", "-b", "events", "-b", "system", "-b", "main", 10475 "-t", String.valueOf(lines)).redirectErrorStream(true).start(); 10476 10477 try { logcat.getOutputStream().close(); } catch (IOException e) {} 10478 try { logcat.getErrorStream().close(); } catch (IOException e) {} 10479 input = new InputStreamReader(logcat.getInputStream()); 10480 10481 int num; 10482 char[] buf = new char[8192]; 10483 while ((num = input.read(buf)) > 0) sb.append(buf, 0, num); 10484 } catch (IOException e) { 10485 Slog.e(TAG, "Error running logcat", e); 10486 } finally { 10487 if (input != null) try { input.close(); } catch (IOException e) {} 10488 } 10489 } 10490 10491 dbox.addText(dropboxTag, sb.toString()); 10492 } 10493 }; 10494 10495 if (process == null) { 10496 // If process is null, we are being called from some internal code 10497 // and may be about to die -- run this synchronously. 10498 worker.run(); 10499 } else { 10500 worker.start(); 10501 } 10502 } 10503 10504 /** 10505 * Bring up the "unexpected error" dialog box for a crashing app. 10506 * Deal with edge cases (intercepts from instrumented applications, 10507 * ActivityController, error intent receivers, that sort of thing). 10508 * @param r the application crashing 10509 * @param crashInfo describing the failure 10510 */ 10511 private void crashApplication(ProcessRecord r, ApplicationErrorReport.CrashInfo crashInfo) { 10512 long timeMillis = System.currentTimeMillis(); 10513 String shortMsg = crashInfo.exceptionClassName; 10514 String longMsg = crashInfo.exceptionMessage; 10515 String stackTrace = crashInfo.stackTrace; 10516 if (shortMsg != null && longMsg != null) { 10517 longMsg = shortMsg + ": " + longMsg; 10518 } else if (shortMsg != null) { 10519 longMsg = shortMsg; 10520 } 10521 10522 AppErrorResult result = new AppErrorResult(); 10523 synchronized (this) { 10524 if (mController != null) { 10525 try { 10526 String name = r != null ? r.processName : null; 10527 int pid = r != null ? r.pid : Binder.getCallingPid(); 10528 if (!mController.appCrashed(name, pid, 10529 shortMsg, longMsg, timeMillis, crashInfo.stackTrace)) { 10530 Slog.w(TAG, "Force-killing crashed app " + name 10531 + " at watcher's request"); 10532 Process.killProcess(pid); 10533 return; 10534 } 10535 } catch (RemoteException e) { 10536 mController = null; 10537 Watchdog.getInstance().setActivityController(null); 10538 } 10539 } 10540 10541 final long origId = Binder.clearCallingIdentity(); 10542 10543 // If this process is running instrumentation, finish it. 10544 if (r != null && r.instrumentationClass != null) { 10545 Slog.w(TAG, "Error in app " + r.processName 10546 + " running instrumentation " + r.instrumentationClass + ":"); 10547 if (shortMsg != null) Slog.w(TAG, " " + shortMsg); 10548 if (longMsg != null) Slog.w(TAG, " " + longMsg); 10549 Bundle info = new Bundle(); 10550 info.putString("shortMsg", shortMsg); 10551 info.putString("longMsg", longMsg); 10552 finishInstrumentationLocked(r, Activity.RESULT_CANCELED, info); 10553 Binder.restoreCallingIdentity(origId); 10554 return; 10555 } 10556 10557 // If we can't identify the process or it's already exceeded its crash quota, 10558 // quit right away without showing a crash dialog. 10559 if (r == null || !makeAppCrashingLocked(r, shortMsg, longMsg, stackTrace)) { 10560 Binder.restoreCallingIdentity(origId); 10561 return; 10562 } 10563 10564 Message msg = Message.obtain(); 10565 msg.what = SHOW_ERROR_MSG; 10566 HashMap data = new HashMap(); 10567 data.put("result", result); 10568 data.put("app", r); 10569 msg.obj = data; 10570 mHandler.sendMessage(msg); 10571 10572 Binder.restoreCallingIdentity(origId); 10573 } 10574 10575 int res = result.get(); 10576 10577 Intent appErrorIntent = null; 10578 synchronized (this) { 10579 if (r != null && !r.isolated) { 10580 // XXX Can't keep track of crash time for isolated processes, 10581 // since they don't have a persistent identity. 10582 mProcessCrashTimes.put(r.info.processName, r.uid, 10583 SystemClock.uptimeMillis()); 10584 } 10585 if (res == AppErrorDialog.FORCE_QUIT_AND_REPORT) { 10586 appErrorIntent = createAppErrorIntentLocked(r, timeMillis, crashInfo); 10587 } 10588 } 10589 10590 if (appErrorIntent != null) { 10591 try { 10592 mContext.startActivityAsUser(appErrorIntent, new UserHandle(r.userId)); 10593 } catch (ActivityNotFoundException e) { 10594 Slog.w(TAG, "bug report receiver dissappeared", e); 10595 } 10596 } 10597 } 10598 10599 Intent createAppErrorIntentLocked(ProcessRecord r, 10600 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 10601 ApplicationErrorReport report = createAppErrorReportLocked(r, timeMillis, crashInfo); 10602 if (report == null) { 10603 return null; 10604 } 10605 Intent result = new Intent(Intent.ACTION_APP_ERROR); 10606 result.setComponent(r.errorReportReceiver); 10607 result.putExtra(Intent.EXTRA_BUG_REPORT, report); 10608 result.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 10609 return result; 10610 } 10611 10612 private ApplicationErrorReport createAppErrorReportLocked(ProcessRecord r, 10613 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 10614 if (r.errorReportReceiver == null) { 10615 return null; 10616 } 10617 10618 if (!r.crashing && !r.notResponding && !r.forceCrashReport) { 10619 return null; 10620 } 10621 10622 ApplicationErrorReport report = new ApplicationErrorReport(); 10623 report.packageName = r.info.packageName; 10624 report.installerPackageName = r.errorReportReceiver.getPackageName(); 10625 report.processName = r.processName; 10626 report.time = timeMillis; 10627 report.systemApp = (r.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0; 10628 10629 if (r.crashing || r.forceCrashReport) { 10630 report.type = ApplicationErrorReport.TYPE_CRASH; 10631 report.crashInfo = crashInfo; 10632 } else if (r.notResponding) { 10633 report.type = ApplicationErrorReport.TYPE_ANR; 10634 report.anrInfo = new ApplicationErrorReport.AnrInfo(); 10635 10636 report.anrInfo.activity = r.notRespondingReport.tag; 10637 report.anrInfo.cause = r.notRespondingReport.shortMsg; 10638 report.anrInfo.info = r.notRespondingReport.longMsg; 10639 } 10640 10641 return report; 10642 } 10643 10644 public List<ActivityManager.ProcessErrorStateInfo> getProcessesInErrorState() { 10645 enforceNotIsolatedCaller("getProcessesInErrorState"); 10646 // assume our apps are happy - lazy create the list 10647 List<ActivityManager.ProcessErrorStateInfo> errList = null; 10648 10649 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 10650 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 10651 int userId = UserHandle.getUserId(Binder.getCallingUid()); 10652 10653 synchronized (this) { 10654 10655 // iterate across all processes 10656 for (int i=mLruProcesses.size()-1; i>=0; i--) { 10657 ProcessRecord app = mLruProcesses.get(i); 10658 if (!allUsers && app.userId != userId) { 10659 continue; 10660 } 10661 if ((app.thread != null) && (app.crashing || app.notResponding)) { 10662 // This one's in trouble, so we'll generate a report for it 10663 // crashes are higher priority (in case there's a crash *and* an anr) 10664 ActivityManager.ProcessErrorStateInfo report = null; 10665 if (app.crashing) { 10666 report = app.crashingReport; 10667 } else if (app.notResponding) { 10668 report = app.notRespondingReport; 10669 } 10670 10671 if (report != null) { 10672 if (errList == null) { 10673 errList = new ArrayList<ActivityManager.ProcessErrorStateInfo>(1); 10674 } 10675 errList.add(report); 10676 } else { 10677 Slog.w(TAG, "Missing app error report, app = " + app.processName + 10678 " crashing = " + app.crashing + 10679 " notResponding = " + app.notResponding); 10680 } 10681 } 10682 } 10683 } 10684 10685 return errList; 10686 } 10687 10688 static int oomAdjToImportance(int adj, ActivityManager.RunningAppProcessInfo currApp) { 10689 if (adj >= ProcessList.CACHED_APP_MIN_ADJ) { 10690 if (currApp != null) { 10691 currApp.lru = adj - ProcessList.CACHED_APP_MIN_ADJ + 1; 10692 } 10693 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND; 10694 } else if (adj >= ProcessList.SERVICE_B_ADJ) { 10695 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_SERVICE; 10696 } else if (adj >= ProcessList.HOME_APP_ADJ) { 10697 if (currApp != null) { 10698 currApp.lru = 0; 10699 } 10700 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND; 10701 } else if (adj >= ProcessList.SERVICE_ADJ) { 10702 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_SERVICE; 10703 } else if (adj >= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 10704 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_CANT_SAVE_STATE; 10705 } else if (adj >= ProcessList.PERCEPTIBLE_APP_ADJ) { 10706 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_PERCEPTIBLE; 10707 } else if (adj >= ProcessList.VISIBLE_APP_ADJ) { 10708 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_VISIBLE; 10709 } else { 10710 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND; 10711 } 10712 } 10713 10714 private void fillInProcMemInfo(ProcessRecord app, 10715 ActivityManager.RunningAppProcessInfo outInfo) { 10716 outInfo.pid = app.pid; 10717 outInfo.uid = app.info.uid; 10718 if (mHeavyWeightProcess == app) { 10719 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_CANT_SAVE_STATE; 10720 } 10721 if (app.persistent) { 10722 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_PERSISTENT; 10723 } 10724 if (app.activities.size() > 0) { 10725 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_HAS_ACTIVITIES; 10726 } 10727 outInfo.lastTrimLevel = app.trimMemoryLevel; 10728 int adj = app.curAdj; 10729 outInfo.importance = oomAdjToImportance(adj, outInfo); 10730 outInfo.importanceReasonCode = app.adjTypeCode; 10731 outInfo.processState = app.curProcState; 10732 } 10733 10734 public List<ActivityManager.RunningAppProcessInfo> getRunningAppProcesses() { 10735 enforceNotIsolatedCaller("getRunningAppProcesses"); 10736 // Lazy instantiation of list 10737 List<ActivityManager.RunningAppProcessInfo> runList = null; 10738 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 10739 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 10740 int userId = UserHandle.getUserId(Binder.getCallingUid()); 10741 synchronized (this) { 10742 // Iterate across all processes 10743 for (int i=mLruProcesses.size()-1; i>=0; i--) { 10744 ProcessRecord app = mLruProcesses.get(i); 10745 if (!allUsers && app.userId != userId) { 10746 continue; 10747 } 10748 if ((app.thread != null) && (!app.crashing && !app.notResponding)) { 10749 // Generate process state info for running application 10750 ActivityManager.RunningAppProcessInfo currApp = 10751 new ActivityManager.RunningAppProcessInfo(app.processName, 10752 app.pid, app.getPackageList()); 10753 fillInProcMemInfo(app, currApp); 10754 if (app.adjSource instanceof ProcessRecord) { 10755 currApp.importanceReasonPid = ((ProcessRecord)app.adjSource).pid; 10756 currApp.importanceReasonImportance = oomAdjToImportance( 10757 app.adjSourceOom, null); 10758 } else if (app.adjSource instanceof ActivityRecord) { 10759 ActivityRecord r = (ActivityRecord)app.adjSource; 10760 if (r.app != null) currApp.importanceReasonPid = r.app.pid; 10761 } 10762 if (app.adjTarget instanceof ComponentName) { 10763 currApp.importanceReasonComponent = (ComponentName)app.adjTarget; 10764 } 10765 //Slog.v(TAG, "Proc " + app.processName + ": imp=" + currApp.importance 10766 // + " lru=" + currApp.lru); 10767 if (runList == null) { 10768 runList = new ArrayList<ActivityManager.RunningAppProcessInfo>(); 10769 } 10770 runList.add(currApp); 10771 } 10772 } 10773 } 10774 return runList; 10775 } 10776 10777 public List<ApplicationInfo> getRunningExternalApplications() { 10778 enforceNotIsolatedCaller("getRunningExternalApplications"); 10779 List<ActivityManager.RunningAppProcessInfo> runningApps = getRunningAppProcesses(); 10780 List<ApplicationInfo> retList = new ArrayList<ApplicationInfo>(); 10781 if (runningApps != null && runningApps.size() > 0) { 10782 Set<String> extList = new HashSet<String>(); 10783 for (ActivityManager.RunningAppProcessInfo app : runningApps) { 10784 if (app.pkgList != null) { 10785 for (String pkg : app.pkgList) { 10786 extList.add(pkg); 10787 } 10788 } 10789 } 10790 IPackageManager pm = AppGlobals.getPackageManager(); 10791 for (String pkg : extList) { 10792 try { 10793 ApplicationInfo info = pm.getApplicationInfo(pkg, 0, UserHandle.getCallingUserId()); 10794 if ((info.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0) { 10795 retList.add(info); 10796 } 10797 } catch (RemoteException e) { 10798 } 10799 } 10800 } 10801 return retList; 10802 } 10803 10804 @Override 10805 public void getMyMemoryState(ActivityManager.RunningAppProcessInfo outInfo) { 10806 enforceNotIsolatedCaller("getMyMemoryState"); 10807 synchronized (this) { 10808 ProcessRecord proc; 10809 synchronized (mPidsSelfLocked) { 10810 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 10811 } 10812 fillInProcMemInfo(proc, outInfo); 10813 } 10814 } 10815 10816 @Override 10817 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 10818 if (checkCallingPermission(android.Manifest.permission.DUMP) 10819 != PackageManager.PERMISSION_GRANTED) { 10820 pw.println("Permission Denial: can't dump ActivityManager from from pid=" 10821 + Binder.getCallingPid() 10822 + ", uid=" + Binder.getCallingUid() 10823 + " without permission " 10824 + android.Manifest.permission.DUMP); 10825 return; 10826 } 10827 10828 boolean dumpAll = false; 10829 boolean dumpClient = false; 10830 String dumpPackage = null; 10831 10832 int opti = 0; 10833 while (opti < args.length) { 10834 String opt = args[opti]; 10835 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 10836 break; 10837 } 10838 opti++; 10839 if ("-a".equals(opt)) { 10840 dumpAll = true; 10841 } else if ("-c".equals(opt)) { 10842 dumpClient = true; 10843 } else if ("-h".equals(opt)) { 10844 pw.println("Activity manager dump options:"); 10845 pw.println(" [-a] [-c] [-h] [cmd] ..."); 10846 pw.println(" cmd may be one of:"); 10847 pw.println(" a[ctivities]: activity stack state"); 10848 pw.println(" b[roadcasts] [PACKAGE_NAME] [history [-s]]: broadcast state"); 10849 pw.println(" i[ntents] [PACKAGE_NAME]: pending intent state"); 10850 pw.println(" p[rocesses] [PACKAGE_NAME]: process state"); 10851 pw.println(" o[om]: out of memory management"); 10852 pw.println(" prov[iders] [COMP_SPEC ...]: content provider state"); 10853 pw.println(" provider [COMP_SPEC]: provider client-side state"); 10854 pw.println(" s[ervices] [COMP_SPEC ...]: service state"); 10855 pw.println(" service [COMP_SPEC]: service client-side state"); 10856 pw.println(" package [PACKAGE_NAME]: all state related to given package"); 10857 pw.println(" all: dump all activities"); 10858 pw.println(" top: dump the top activity"); 10859 pw.println(" cmd may also be a COMP_SPEC to dump activities."); 10860 pw.println(" COMP_SPEC may be a component name (com.foo/.myApp),"); 10861 pw.println(" a partial substring in a component name, a"); 10862 pw.println(" hex object identifier."); 10863 pw.println(" -a: include all available server state."); 10864 pw.println(" -c: include client state."); 10865 return; 10866 } else { 10867 pw.println("Unknown argument: " + opt + "; use -h for help"); 10868 } 10869 } 10870 10871 long origId = Binder.clearCallingIdentity(); 10872 boolean more = false; 10873 // Is the caller requesting to dump a particular piece of data? 10874 if (opti < args.length) { 10875 String cmd = args[opti]; 10876 opti++; 10877 if ("activities".equals(cmd) || "a".equals(cmd)) { 10878 synchronized (this) { 10879 dumpActivitiesLocked(fd, pw, args, opti, true, dumpClient, null); 10880 } 10881 } else if ("broadcasts".equals(cmd) || "b".equals(cmd)) { 10882 String[] newArgs; 10883 String name; 10884 if (opti >= args.length) { 10885 name = null; 10886 newArgs = EMPTY_STRING_ARRAY; 10887 } else { 10888 name = args[opti]; 10889 opti++; 10890 newArgs = new String[args.length - opti]; 10891 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 10892 args.length - opti); 10893 } 10894 synchronized (this) { 10895 dumpBroadcastsLocked(fd, pw, args, opti, true, name); 10896 } 10897 } else if ("intents".equals(cmd) || "i".equals(cmd)) { 10898 String[] newArgs; 10899 String name; 10900 if (opti >= args.length) { 10901 name = null; 10902 newArgs = EMPTY_STRING_ARRAY; 10903 } else { 10904 name = args[opti]; 10905 opti++; 10906 newArgs = new String[args.length - opti]; 10907 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 10908 args.length - opti); 10909 } 10910 synchronized (this) { 10911 dumpPendingIntentsLocked(fd, pw, args, opti, true, name); 10912 } 10913 } else if ("processes".equals(cmd) || "p".equals(cmd)) { 10914 String[] newArgs; 10915 String name; 10916 if (opti >= args.length) { 10917 name = null; 10918 newArgs = EMPTY_STRING_ARRAY; 10919 } else { 10920 name = args[opti]; 10921 opti++; 10922 newArgs = new String[args.length - opti]; 10923 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 10924 args.length - opti); 10925 } 10926 synchronized (this) { 10927 dumpProcessesLocked(fd, pw, args, opti, true, name); 10928 } 10929 } else if ("oom".equals(cmd) || "o".equals(cmd)) { 10930 synchronized (this) { 10931 dumpOomLocked(fd, pw, args, opti, true); 10932 } 10933 } else if ("provider".equals(cmd)) { 10934 String[] newArgs; 10935 String name; 10936 if (opti >= args.length) { 10937 name = null; 10938 newArgs = EMPTY_STRING_ARRAY; 10939 } else { 10940 name = args[opti]; 10941 opti++; 10942 newArgs = new String[args.length - opti]; 10943 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, args.length - opti); 10944 } 10945 if (!dumpProvider(fd, pw, name, newArgs, 0, dumpAll)) { 10946 pw.println("No providers match: " + name); 10947 pw.println("Use -h for help."); 10948 } 10949 } else if ("providers".equals(cmd) || "prov".equals(cmd)) { 10950 synchronized (this) { 10951 dumpProvidersLocked(fd, pw, args, opti, true, null); 10952 } 10953 } else if ("service".equals(cmd)) { 10954 String[] newArgs; 10955 String name; 10956 if (opti >= args.length) { 10957 name = null; 10958 newArgs = EMPTY_STRING_ARRAY; 10959 } else { 10960 name = args[opti]; 10961 opti++; 10962 newArgs = new String[args.length - opti]; 10963 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 10964 args.length - opti); 10965 } 10966 if (!mServices.dumpService(fd, pw, name, newArgs, 0, dumpAll)) { 10967 pw.println("No services match: " + name); 10968 pw.println("Use -h for help."); 10969 } 10970 } else if ("package".equals(cmd)) { 10971 String[] newArgs; 10972 if (opti >= args.length) { 10973 pw.println("package: no package name specified"); 10974 pw.println("Use -h for help."); 10975 } else { 10976 dumpPackage = args[opti]; 10977 opti++; 10978 newArgs = new String[args.length - opti]; 10979 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 10980 args.length - opti); 10981 args = newArgs; 10982 opti = 0; 10983 more = true; 10984 } 10985 } else if ("services".equals(cmd) || "s".equals(cmd)) { 10986 synchronized (this) { 10987 mServices.dumpServicesLocked(fd, pw, args, opti, true, dumpClient, null); 10988 } 10989 } else { 10990 // Dumping a single activity? 10991 if (!dumpActivity(fd, pw, cmd, args, opti, dumpAll)) { 10992 pw.println("Bad activity command, or no activities match: " + cmd); 10993 pw.println("Use -h for help."); 10994 } 10995 } 10996 if (!more) { 10997 Binder.restoreCallingIdentity(origId); 10998 return; 10999 } 11000 } 11001 11002 // No piece of data specified, dump everything. 11003 synchronized (this) { 11004 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11005 pw.println(); 11006 if (dumpAll) { 11007 pw.println("-------------------------------------------------------------------------------"); 11008 } 11009 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11010 pw.println(); 11011 if (dumpAll) { 11012 pw.println("-------------------------------------------------------------------------------"); 11013 } 11014 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11015 pw.println(); 11016 if (dumpAll) { 11017 pw.println("-------------------------------------------------------------------------------"); 11018 } 11019 mServices.dumpServicesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 11020 pw.println(); 11021 if (dumpAll) { 11022 pw.println("-------------------------------------------------------------------------------"); 11023 } 11024 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 11025 pw.println(); 11026 if (dumpAll) { 11027 pw.println("-------------------------------------------------------------------------------"); 11028 } 11029 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11030 } 11031 Binder.restoreCallingIdentity(origId); 11032 } 11033 11034 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11035 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) { 11036 pw.println("ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)"); 11037 11038 boolean printedAnything = mStackSupervisor.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient, 11039 dumpPackage); 11040 boolean needSep = printedAnything; 11041 11042 boolean printed = ActivityStackSupervisor.printThisActivity(pw, mFocusedActivity, 11043 dumpPackage, needSep, " mFocusedActivity: "); 11044 if (printed) { 11045 printedAnything = true; 11046 needSep = false; 11047 } 11048 11049 if (dumpPackage == null) { 11050 if (needSep) { 11051 pw.println(); 11052 } 11053 needSep = true; 11054 printedAnything = true; 11055 mStackSupervisor.dump(pw, " "); 11056 } 11057 11058 if (mRecentTasks.size() > 0) { 11059 boolean printedHeader = false; 11060 11061 final int N = mRecentTasks.size(); 11062 for (int i=0; i<N; i++) { 11063 TaskRecord tr = mRecentTasks.get(i); 11064 if (dumpPackage != null) { 11065 if (tr.realActivity == null || 11066 !dumpPackage.equals(tr.realActivity)) { 11067 continue; 11068 } 11069 } 11070 if (!printedHeader) { 11071 if (needSep) { 11072 pw.println(); 11073 } 11074 pw.println(" Recent tasks:"); 11075 printedHeader = true; 11076 printedAnything = true; 11077 } 11078 pw.print(" * Recent #"); pw.print(i); pw.print(": "); 11079 pw.println(tr); 11080 if (dumpAll) { 11081 mRecentTasks.get(i).dump(pw, " "); 11082 } 11083 } 11084 } 11085 11086 if (!printedAnything) { 11087 pw.println(" (nothing)"); 11088 } 11089 } 11090 11091 void dumpProcessesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11092 int opti, boolean dumpAll, String dumpPackage) { 11093 boolean needSep = false; 11094 boolean printedAnything = false; 11095 int numPers = 0; 11096 11097 pw.println("ACTIVITY MANAGER RUNNING PROCESSES (dumpsys activity processes)"); 11098 11099 if (dumpAll) { 11100 final int NP = mProcessNames.getMap().size(); 11101 for (int ip=0; ip<NP; ip++) { 11102 SparseArray<ProcessRecord> procs = mProcessNames.getMap().valueAt(ip); 11103 final int NA = procs.size(); 11104 for (int ia=0; ia<NA; ia++) { 11105 ProcessRecord r = procs.valueAt(ia); 11106 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11107 continue; 11108 } 11109 if (!needSep) { 11110 pw.println(" All known processes:"); 11111 needSep = true; 11112 printedAnything = true; 11113 } 11114 pw.print(r.persistent ? " *PERS*" : " *APP*"); 11115 pw.print(" UID "); pw.print(procs.keyAt(ia)); 11116 pw.print(" "); pw.println(r); 11117 r.dump(pw, " "); 11118 if (r.persistent) { 11119 numPers++; 11120 } 11121 } 11122 } 11123 } 11124 11125 if (mIsolatedProcesses.size() > 0) { 11126 boolean printed = false; 11127 for (int i=0; i<mIsolatedProcesses.size(); i++) { 11128 ProcessRecord r = mIsolatedProcesses.valueAt(i); 11129 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11130 continue; 11131 } 11132 if (!printed) { 11133 if (needSep) { 11134 pw.println(); 11135 } 11136 pw.println(" Isolated process list (sorted by uid):"); 11137 printedAnything = true; 11138 printed = true; 11139 needSep = true; 11140 } 11141 pw.println(String.format("%sIsolated #%2d: %s", 11142 " ", i, r.toString())); 11143 } 11144 } 11145 11146 if (mLruProcesses.size() > 0) { 11147 if (needSep) { 11148 pw.println(); 11149 } 11150 pw.print(" Process LRU list (sorted by oom_adj, "); pw.print(mLruProcesses.size()); 11151 pw.print(" total, non-act at "); 11152 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 11153 pw.print(", non-svc at "); 11154 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 11155 pw.println("):"); 11156 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", false, dumpPackage); 11157 needSep = true; 11158 printedAnything = true; 11159 } 11160 11161 if (dumpAll || dumpPackage != null) { 11162 synchronized (mPidsSelfLocked) { 11163 boolean printed = false; 11164 for (int i=0; i<mPidsSelfLocked.size(); i++) { 11165 ProcessRecord r = mPidsSelfLocked.valueAt(i); 11166 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11167 continue; 11168 } 11169 if (!printed) { 11170 if (needSep) pw.println(); 11171 needSep = true; 11172 pw.println(" PID mappings:"); 11173 printed = true; 11174 printedAnything = true; 11175 } 11176 pw.print(" PID #"); pw.print(mPidsSelfLocked.keyAt(i)); 11177 pw.print(": "); pw.println(mPidsSelfLocked.valueAt(i)); 11178 } 11179 } 11180 } 11181 11182 if (mForegroundProcesses.size() > 0) { 11183 synchronized (mPidsSelfLocked) { 11184 boolean printed = false; 11185 for (int i=0; i<mForegroundProcesses.size(); i++) { 11186 ProcessRecord r = mPidsSelfLocked.get( 11187 mForegroundProcesses.valueAt(i).pid); 11188 if (dumpPackage != null && (r == null 11189 || !r.pkgList.containsKey(dumpPackage))) { 11190 continue; 11191 } 11192 if (!printed) { 11193 if (needSep) pw.println(); 11194 needSep = true; 11195 pw.println(" Foreground Processes:"); 11196 printed = true; 11197 printedAnything = true; 11198 } 11199 pw.print(" PID #"); pw.print(mForegroundProcesses.keyAt(i)); 11200 pw.print(": "); pw.println(mForegroundProcesses.valueAt(i)); 11201 } 11202 } 11203 } 11204 11205 if (mPersistentStartingProcesses.size() > 0) { 11206 if (needSep) pw.println(); 11207 needSep = true; 11208 printedAnything = true; 11209 pw.println(" Persisent processes that are starting:"); 11210 dumpProcessList(pw, this, mPersistentStartingProcesses, " ", 11211 "Starting Norm", "Restarting PERS", dumpPackage); 11212 } 11213 11214 if (mRemovedProcesses.size() > 0) { 11215 if (needSep) pw.println(); 11216 needSep = true; 11217 printedAnything = true; 11218 pw.println(" Processes that are being removed:"); 11219 dumpProcessList(pw, this, mRemovedProcesses, " ", 11220 "Removed Norm", "Removed PERS", dumpPackage); 11221 } 11222 11223 if (mProcessesOnHold.size() > 0) { 11224 if (needSep) pw.println(); 11225 needSep = true; 11226 printedAnything = true; 11227 pw.println(" Processes that are on old until the system is ready:"); 11228 dumpProcessList(pw, this, mProcessesOnHold, " ", 11229 "OnHold Norm", "OnHold PERS", dumpPackage); 11230 } 11231 11232 needSep = dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, dumpPackage); 11233 11234 if (mProcessCrashTimes.getMap().size() > 0) { 11235 boolean printed = false; 11236 long now = SystemClock.uptimeMillis(); 11237 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 11238 final int NP = pmap.size(); 11239 for (int ip=0; ip<NP; ip++) { 11240 String pname = pmap.keyAt(ip); 11241 SparseArray<Long> uids = pmap.valueAt(ip); 11242 final int N = uids.size(); 11243 for (int i=0; i<N; i++) { 11244 int puid = uids.keyAt(i); 11245 ProcessRecord r = mProcessNames.get(pname, puid); 11246 if (dumpPackage != null && (r == null 11247 || !r.pkgList.containsKey(dumpPackage))) { 11248 continue; 11249 } 11250 if (!printed) { 11251 if (needSep) pw.println(); 11252 needSep = true; 11253 pw.println(" Time since processes crashed:"); 11254 printed = true; 11255 printedAnything = true; 11256 } 11257 pw.print(" Process "); pw.print(pname); 11258 pw.print(" uid "); pw.print(puid); 11259 pw.print(": last crashed "); 11260 TimeUtils.formatDuration(now-uids.valueAt(i), pw); 11261 pw.println(" ago"); 11262 } 11263 } 11264 } 11265 11266 if (mBadProcesses.getMap().size() > 0) { 11267 boolean printed = false; 11268 final ArrayMap<String, SparseArray<BadProcessInfo>> pmap = mBadProcesses.getMap(); 11269 final int NP = pmap.size(); 11270 for (int ip=0; ip<NP; ip++) { 11271 String pname = pmap.keyAt(ip); 11272 SparseArray<BadProcessInfo> uids = pmap.valueAt(ip); 11273 final int N = uids.size(); 11274 for (int i=0; i<N; i++) { 11275 int puid = uids.keyAt(i); 11276 ProcessRecord r = mProcessNames.get(pname, puid); 11277 if (dumpPackage != null && (r == null 11278 || !r.pkgList.containsKey(dumpPackage))) { 11279 continue; 11280 } 11281 if (!printed) { 11282 if (needSep) pw.println(); 11283 needSep = true; 11284 pw.println(" Bad processes:"); 11285 printedAnything = true; 11286 } 11287 BadProcessInfo info = uids.valueAt(i); 11288 pw.print(" Bad process "); pw.print(pname); 11289 pw.print(" uid "); pw.print(puid); 11290 pw.print(": crashed at time "); pw.println(info.time); 11291 if (info.shortMsg != null) { 11292 pw.print(" Short msg: "); pw.println(info.shortMsg); 11293 } 11294 if (info.longMsg != null) { 11295 pw.print(" Long msg: "); pw.println(info.longMsg); 11296 } 11297 if (info.stack != null) { 11298 pw.println(" Stack:"); 11299 int lastPos = 0; 11300 for (int pos=0; pos<info.stack.length(); pos++) { 11301 if (info.stack.charAt(pos) == '\n') { 11302 pw.print(" "); 11303 pw.write(info.stack, lastPos, pos-lastPos); 11304 pw.println(); 11305 lastPos = pos+1; 11306 } 11307 } 11308 if (lastPos < info.stack.length()) { 11309 pw.print(" "); 11310 pw.write(info.stack, lastPos, info.stack.length()-lastPos); 11311 pw.println(); 11312 } 11313 } 11314 } 11315 } 11316 } 11317 11318 if (dumpPackage == null) { 11319 pw.println(); 11320 needSep = false; 11321 pw.println(" mStartedUsers:"); 11322 for (int i=0; i<mStartedUsers.size(); i++) { 11323 UserStartedState uss = mStartedUsers.valueAt(i); 11324 pw.print(" User #"); pw.print(uss.mHandle.getIdentifier()); 11325 pw.print(": "); uss.dump("", pw); 11326 } 11327 pw.print(" mStartedUserArray: ["); 11328 for (int i=0; i<mStartedUserArray.length; i++) { 11329 if (i > 0) pw.print(", "); 11330 pw.print(mStartedUserArray[i]); 11331 } 11332 pw.println("]"); 11333 pw.print(" mUserLru: ["); 11334 for (int i=0; i<mUserLru.size(); i++) { 11335 if (i > 0) pw.print(", "); 11336 pw.print(mUserLru.get(i)); 11337 } 11338 pw.println("]"); 11339 if (dumpAll) { 11340 pw.print(" mStartedUserArray: "); pw.println(Arrays.toString(mStartedUserArray)); 11341 } 11342 } 11343 if (mHomeProcess != null && (dumpPackage == null 11344 || mHomeProcess.pkgList.containsKey(dumpPackage))) { 11345 if (needSep) { 11346 pw.println(); 11347 needSep = false; 11348 } 11349 pw.println(" mHomeProcess: " + mHomeProcess); 11350 } 11351 if (mPreviousProcess != null && (dumpPackage == null 11352 || mPreviousProcess.pkgList.containsKey(dumpPackage))) { 11353 if (needSep) { 11354 pw.println(); 11355 needSep = false; 11356 } 11357 pw.println(" mPreviousProcess: " + mPreviousProcess); 11358 } 11359 if (dumpAll) { 11360 StringBuilder sb = new StringBuilder(128); 11361 sb.append(" mPreviousProcessVisibleTime: "); 11362 TimeUtils.formatDuration(mPreviousProcessVisibleTime, sb); 11363 pw.println(sb); 11364 } 11365 if (mHeavyWeightProcess != null && (dumpPackage == null 11366 || mHeavyWeightProcess.pkgList.containsKey(dumpPackage))) { 11367 if (needSep) { 11368 pw.println(); 11369 needSep = false; 11370 } 11371 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 11372 } 11373 if (dumpPackage == null) { 11374 pw.println(" mConfiguration: " + mConfiguration); 11375 } 11376 if (dumpAll) { 11377 pw.println(" mConfigWillChange: " + getFocusedStack().mConfigWillChange); 11378 if (mCompatModePackages.getPackages().size() > 0) { 11379 boolean printed = false; 11380 for (Map.Entry<String, Integer> entry 11381 : mCompatModePackages.getPackages().entrySet()) { 11382 String pkg = entry.getKey(); 11383 int mode = entry.getValue(); 11384 if (dumpPackage != null && !dumpPackage.equals(pkg)) { 11385 continue; 11386 } 11387 if (!printed) { 11388 pw.println(" mScreenCompatPackages:"); 11389 printed = true; 11390 } 11391 pw.print(" "); pw.print(pkg); pw.print(": "); 11392 pw.print(mode); pw.println(); 11393 } 11394 } 11395 } 11396 if (dumpPackage == null) { 11397 if (mSleeping || mWentToSleep || mLockScreenShown) { 11398 pw.println(" mSleeping=" + mSleeping + " mWentToSleep=" + mWentToSleep 11399 + " mLockScreenShown " + mLockScreenShown); 11400 } 11401 if (mShuttingDown || mRunningVoice) { 11402 pw.print(" mShuttingDown=" + mShuttingDown + " mRunningVoice=" + mRunningVoice); 11403 } 11404 } 11405 if (mDebugApp != null || mOrigDebugApp != null || mDebugTransient 11406 || mOrigWaitForDebugger) { 11407 if (dumpPackage == null || dumpPackage.equals(mDebugApp) 11408 || dumpPackage.equals(mOrigDebugApp)) { 11409 if (needSep) { 11410 pw.println(); 11411 needSep = false; 11412 } 11413 pw.println(" mDebugApp=" + mDebugApp + "/orig=" + mOrigDebugApp 11414 + " mDebugTransient=" + mDebugTransient 11415 + " mOrigWaitForDebugger=" + mOrigWaitForDebugger); 11416 } 11417 } 11418 if (mOpenGlTraceApp != null) { 11419 if (dumpPackage == null || dumpPackage.equals(mOpenGlTraceApp)) { 11420 if (needSep) { 11421 pw.println(); 11422 needSep = false; 11423 } 11424 pw.println(" mOpenGlTraceApp=" + mOpenGlTraceApp); 11425 } 11426 } 11427 if (mProfileApp != null || mProfileProc != null || mProfileFile != null 11428 || mProfileFd != null) { 11429 if (dumpPackage == null || dumpPackage.equals(mProfileApp)) { 11430 if (needSep) { 11431 pw.println(); 11432 needSep = false; 11433 } 11434 pw.println(" mProfileApp=" + mProfileApp + " mProfileProc=" + mProfileProc); 11435 pw.println(" mProfileFile=" + mProfileFile + " mProfileFd=" + mProfileFd); 11436 pw.println(" mProfileType=" + mProfileType + " mAutoStopProfiler=" 11437 + mAutoStopProfiler); 11438 } 11439 } 11440 if (dumpPackage == null) { 11441 if (mAlwaysFinishActivities || mController != null) { 11442 pw.println(" mAlwaysFinishActivities=" + mAlwaysFinishActivities 11443 + " mController=" + mController); 11444 } 11445 if (dumpAll) { 11446 pw.println(" Total persistent processes: " + numPers); 11447 pw.println(" mProcessesReady=" + mProcessesReady 11448 + " mSystemReady=" + mSystemReady); 11449 pw.println(" mBooting=" + mBooting 11450 + " mBooted=" + mBooted 11451 + " mFactoryTest=" + mFactoryTest); 11452 pw.print(" mLastPowerCheckRealtime="); 11453 TimeUtils.formatDuration(mLastPowerCheckRealtime, pw); 11454 pw.println(""); 11455 pw.print(" mLastPowerCheckUptime="); 11456 TimeUtils.formatDuration(mLastPowerCheckUptime, pw); 11457 pw.println(""); 11458 pw.println(" mGoingToSleep=" + mStackSupervisor.mGoingToSleep); 11459 pw.println(" mLaunchingActivity=" + mStackSupervisor.mLaunchingActivity); 11460 pw.println(" mAdjSeq=" + mAdjSeq + " mLruSeq=" + mLruSeq); 11461 pw.println(" mNumNonCachedProcs=" + mNumNonCachedProcs 11462 + " (" + mLruProcesses.size() + " total)" 11463 + " mNumCachedHiddenProcs=" + mNumCachedHiddenProcs 11464 + " mNumServiceProcs=" + mNumServiceProcs 11465 + " mNewNumServiceProcs=" + mNewNumServiceProcs); 11466 pw.println(" mAllowLowerMemLevel=" + mAllowLowerMemLevel 11467 + " mLastMemoryLevel" + mLastMemoryLevel 11468 + " mLastNumProcesses" + mLastNumProcesses); 11469 long now = SystemClock.uptimeMillis(); 11470 pw.print(" mLastIdleTime="); 11471 TimeUtils.formatDuration(now, mLastIdleTime, pw); 11472 pw.print(" mLowRamSinceLastIdle="); 11473 TimeUtils.formatDuration(getLowRamTimeSinceIdle(now), pw); 11474 pw.println(); 11475 } 11476 } 11477 11478 if (!printedAnything) { 11479 pw.println(" (nothing)"); 11480 } 11481 } 11482 11483 boolean dumpProcessesToGc(FileDescriptor fd, PrintWriter pw, String[] args, 11484 int opti, boolean needSep, boolean dumpAll, String dumpPackage) { 11485 if (mProcessesToGc.size() > 0) { 11486 boolean printed = false; 11487 long now = SystemClock.uptimeMillis(); 11488 for (int i=0; i<mProcessesToGc.size(); i++) { 11489 ProcessRecord proc = mProcessesToGc.get(i); 11490 if (dumpPackage != null && !dumpPackage.equals(proc.info.packageName)) { 11491 continue; 11492 } 11493 if (!printed) { 11494 if (needSep) pw.println(); 11495 needSep = true; 11496 pw.println(" Processes that are waiting to GC:"); 11497 printed = true; 11498 } 11499 pw.print(" Process "); pw.println(proc); 11500 pw.print(" lowMem="); pw.print(proc.reportLowMemory); 11501 pw.print(", last gced="); 11502 pw.print(now-proc.lastRequestedGc); 11503 pw.print(" ms ago, last lowMem="); 11504 pw.print(now-proc.lastLowMemory); 11505 pw.println(" ms ago"); 11506 11507 } 11508 } 11509 return needSep; 11510 } 11511 11512 void printOomLevel(PrintWriter pw, String name, int adj) { 11513 pw.print(" "); 11514 if (adj >= 0) { 11515 pw.print(' '); 11516 if (adj < 10) pw.print(' '); 11517 } else { 11518 if (adj > -10) pw.print(' '); 11519 } 11520 pw.print(adj); 11521 pw.print(": "); 11522 pw.print(name); 11523 pw.print(" ("); 11524 pw.print(mProcessList.getMemLevel(adj)/1024); 11525 pw.println(" kB)"); 11526 } 11527 11528 boolean dumpOomLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11529 int opti, boolean dumpAll) { 11530 boolean needSep = false; 11531 11532 if (mLruProcesses.size() > 0) { 11533 if (needSep) pw.println(); 11534 needSep = true; 11535 pw.println(" OOM levels:"); 11536 printOomLevel(pw, "SYSTEM_ADJ", ProcessList.SYSTEM_ADJ); 11537 printOomLevel(pw, "PERSISTENT_PROC_ADJ", ProcessList.PERSISTENT_PROC_ADJ); 11538 printOomLevel(pw, "FOREGROUND_APP_ADJ", ProcessList.FOREGROUND_APP_ADJ); 11539 printOomLevel(pw, "VISIBLE_APP_ADJ", ProcessList.VISIBLE_APP_ADJ); 11540 printOomLevel(pw, "PERCEPTIBLE_APP_ADJ", ProcessList.PERCEPTIBLE_APP_ADJ); 11541 printOomLevel(pw, "BACKUP_APP_ADJ", ProcessList.BACKUP_APP_ADJ); 11542 printOomLevel(pw, "HEAVY_WEIGHT_APP_ADJ", ProcessList.HEAVY_WEIGHT_APP_ADJ); 11543 printOomLevel(pw, "SERVICE_ADJ", ProcessList.SERVICE_ADJ); 11544 printOomLevel(pw, "HOME_APP_ADJ", ProcessList.HOME_APP_ADJ); 11545 printOomLevel(pw, "PREVIOUS_APP_ADJ", ProcessList.PREVIOUS_APP_ADJ); 11546 printOomLevel(pw, "SERVICE_B_ADJ", ProcessList.SERVICE_B_ADJ); 11547 printOomLevel(pw, "CACHED_APP_MIN_ADJ", ProcessList.CACHED_APP_MIN_ADJ); 11548 printOomLevel(pw, "CACHED_APP_MAX_ADJ", ProcessList.CACHED_APP_MAX_ADJ); 11549 11550 if (needSep) pw.println(); 11551 pw.print(" Process OOM control ("); pw.print(mLruProcesses.size()); 11552 pw.print(" total, non-act at "); 11553 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 11554 pw.print(", non-svc at "); 11555 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 11556 pw.println("):"); 11557 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", true, null); 11558 needSep = true; 11559 } 11560 11561 dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, null); 11562 11563 pw.println(); 11564 pw.println(" mHomeProcess: " + mHomeProcess); 11565 pw.println(" mPreviousProcess: " + mPreviousProcess); 11566 if (mHeavyWeightProcess != null) { 11567 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 11568 } 11569 11570 return true; 11571 } 11572 11573 /** 11574 * There are three ways to call this: 11575 * - no provider specified: dump all the providers 11576 * - a flattened component name that matched an existing provider was specified as the 11577 * first arg: dump that one provider 11578 * - the first arg isn't the flattened component name of an existing provider: 11579 * dump all providers whose component contains the first arg as a substring 11580 */ 11581 protected boolean dumpProvider(FileDescriptor fd, PrintWriter pw, String name, String[] args, 11582 int opti, boolean dumpAll) { 11583 return mProviderMap.dumpProvider(fd, pw, name, args, opti, dumpAll); 11584 } 11585 11586 static class ItemMatcher { 11587 ArrayList<ComponentName> components; 11588 ArrayList<String> strings; 11589 ArrayList<Integer> objects; 11590 boolean all; 11591 11592 ItemMatcher() { 11593 all = true; 11594 } 11595 11596 void build(String name) { 11597 ComponentName componentName = ComponentName.unflattenFromString(name); 11598 if (componentName != null) { 11599 if (components == null) { 11600 components = new ArrayList<ComponentName>(); 11601 } 11602 components.add(componentName); 11603 all = false; 11604 } else { 11605 int objectId = 0; 11606 // Not a '/' separated full component name; maybe an object ID? 11607 try { 11608 objectId = Integer.parseInt(name, 16); 11609 if (objects == null) { 11610 objects = new ArrayList<Integer>(); 11611 } 11612 objects.add(objectId); 11613 all = false; 11614 } catch (RuntimeException e) { 11615 // Not an integer; just do string match. 11616 if (strings == null) { 11617 strings = new ArrayList<String>(); 11618 } 11619 strings.add(name); 11620 all = false; 11621 } 11622 } 11623 } 11624 11625 int build(String[] args, int opti) { 11626 for (; opti<args.length; opti++) { 11627 String name = args[opti]; 11628 if ("--".equals(name)) { 11629 return opti+1; 11630 } 11631 build(name); 11632 } 11633 return opti; 11634 } 11635 11636 boolean match(Object object, ComponentName comp) { 11637 if (all) { 11638 return true; 11639 } 11640 if (components != null) { 11641 for (int i=0; i<components.size(); i++) { 11642 if (components.get(i).equals(comp)) { 11643 return true; 11644 } 11645 } 11646 } 11647 if (objects != null) { 11648 for (int i=0; i<objects.size(); i++) { 11649 if (System.identityHashCode(object) == objects.get(i)) { 11650 return true; 11651 } 11652 } 11653 } 11654 if (strings != null) { 11655 String flat = comp.flattenToString(); 11656 for (int i=0; i<strings.size(); i++) { 11657 if (flat.contains(strings.get(i))) { 11658 return true; 11659 } 11660 } 11661 } 11662 return false; 11663 } 11664 } 11665 11666 /** 11667 * There are three things that cmd can be: 11668 * - a flattened component name that matches an existing activity 11669 * - the cmd arg isn't the flattened component name of an existing activity: 11670 * dump all activity whose component contains the cmd as a substring 11671 * - A hex number of the ActivityRecord object instance. 11672 */ 11673 protected boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name, String[] args, 11674 int opti, boolean dumpAll) { 11675 ArrayList<ActivityRecord> activities; 11676 11677 synchronized (this) { 11678 activities = mStackSupervisor.getDumpActivitiesLocked(name); 11679 } 11680 11681 if (activities.size() <= 0) { 11682 return false; 11683 } 11684 11685 String[] newArgs = new String[args.length - opti]; 11686 System.arraycopy(args, opti, newArgs, 0, args.length - opti); 11687 11688 TaskRecord lastTask = null; 11689 boolean needSep = false; 11690 for (int i=activities.size()-1; i>=0; i--) { 11691 ActivityRecord r = activities.get(i); 11692 if (needSep) { 11693 pw.println(); 11694 } 11695 needSep = true; 11696 synchronized (this) { 11697 if (lastTask != r.task) { 11698 lastTask = r.task; 11699 pw.print("TASK "); pw.print(lastTask.affinity); 11700 pw.print(" id="); pw.println(lastTask.taskId); 11701 if (dumpAll) { 11702 lastTask.dump(pw, " "); 11703 } 11704 } 11705 } 11706 dumpActivity(" ", fd, pw, activities.get(i), newArgs, dumpAll); 11707 } 11708 return true; 11709 } 11710 11711 /** 11712 * Invokes IApplicationThread.dumpActivity() on the thread of the specified activity if 11713 * there is a thread associated with the activity. 11714 */ 11715 private void dumpActivity(String prefix, FileDescriptor fd, PrintWriter pw, 11716 final ActivityRecord r, String[] args, boolean dumpAll) { 11717 String innerPrefix = prefix + " "; 11718 synchronized (this) { 11719 pw.print(prefix); pw.print("ACTIVITY "); pw.print(r.shortComponentName); 11720 pw.print(" "); pw.print(Integer.toHexString(System.identityHashCode(r))); 11721 pw.print(" pid="); 11722 if (r.app != null) pw.println(r.app.pid); 11723 else pw.println("(not running)"); 11724 if (dumpAll) { 11725 r.dump(pw, innerPrefix); 11726 } 11727 } 11728 if (r.app != null && r.app.thread != null) { 11729 // flush anything that is already in the PrintWriter since the thread is going 11730 // to write to the file descriptor directly 11731 pw.flush(); 11732 try { 11733 TransferPipe tp = new TransferPipe(); 11734 try { 11735 r.app.thread.dumpActivity(tp.getWriteFd().getFileDescriptor(), 11736 r.appToken, innerPrefix, args); 11737 tp.go(fd); 11738 } finally { 11739 tp.kill(); 11740 } 11741 } catch (IOException e) { 11742 pw.println(innerPrefix + "Failure while dumping the activity: " + e); 11743 } catch (RemoteException e) { 11744 pw.println(innerPrefix + "Got a RemoteException while dumping the activity"); 11745 } 11746 } 11747 } 11748 11749 void dumpBroadcastsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11750 int opti, boolean dumpAll, String dumpPackage) { 11751 boolean needSep = false; 11752 boolean onlyHistory = false; 11753 boolean printedAnything = false; 11754 11755 if ("history".equals(dumpPackage)) { 11756 if (opti < args.length && "-s".equals(args[opti])) { 11757 dumpAll = false; 11758 } 11759 onlyHistory = true; 11760 dumpPackage = null; 11761 } 11762 11763 pw.println("ACTIVITY MANAGER BROADCAST STATE (dumpsys activity broadcasts)"); 11764 if (!onlyHistory && dumpAll) { 11765 if (mRegisteredReceivers.size() > 0) { 11766 boolean printed = false; 11767 Iterator it = mRegisteredReceivers.values().iterator(); 11768 while (it.hasNext()) { 11769 ReceiverList r = (ReceiverList)it.next(); 11770 if (dumpPackage != null && (r.app == null || 11771 !dumpPackage.equals(r.app.info.packageName))) { 11772 continue; 11773 } 11774 if (!printed) { 11775 pw.println(" Registered Receivers:"); 11776 needSep = true; 11777 printed = true; 11778 printedAnything = true; 11779 } 11780 pw.print(" * "); pw.println(r); 11781 r.dump(pw, " "); 11782 } 11783 } 11784 11785 if (mReceiverResolver.dump(pw, needSep ? 11786 "\n Receiver Resolver Table:" : " Receiver Resolver Table:", 11787 " ", dumpPackage, false)) { 11788 needSep = true; 11789 printedAnything = true; 11790 } 11791 } 11792 11793 for (BroadcastQueue q : mBroadcastQueues) { 11794 needSep = q.dumpLocked(fd, pw, args, opti, dumpAll, dumpPackage, needSep); 11795 printedAnything |= needSep; 11796 } 11797 11798 needSep = true; 11799 11800 if (!onlyHistory && mStickyBroadcasts != null && dumpPackage == null) { 11801 for (int user=0; user<mStickyBroadcasts.size(); user++) { 11802 if (needSep) { 11803 pw.println(); 11804 } 11805 needSep = true; 11806 printedAnything = true; 11807 pw.print(" Sticky broadcasts for user "); 11808 pw.print(mStickyBroadcasts.keyAt(user)); pw.println(":"); 11809 StringBuilder sb = new StringBuilder(128); 11810 for (Map.Entry<String, ArrayList<Intent>> ent 11811 : mStickyBroadcasts.valueAt(user).entrySet()) { 11812 pw.print(" * Sticky action "); pw.print(ent.getKey()); 11813 if (dumpAll) { 11814 pw.println(":"); 11815 ArrayList<Intent> intents = ent.getValue(); 11816 final int N = intents.size(); 11817 for (int i=0; i<N; i++) { 11818 sb.setLength(0); 11819 sb.append(" Intent: "); 11820 intents.get(i).toShortString(sb, false, true, false, false); 11821 pw.println(sb.toString()); 11822 Bundle bundle = intents.get(i).getExtras(); 11823 if (bundle != null) { 11824 pw.print(" "); 11825 pw.println(bundle.toString()); 11826 } 11827 } 11828 } else { 11829 pw.println(""); 11830 } 11831 } 11832 } 11833 } 11834 11835 if (!onlyHistory && dumpAll) { 11836 pw.println(); 11837 for (BroadcastQueue queue : mBroadcastQueues) { 11838 pw.println(" mBroadcastsScheduled [" + queue.mQueueName + "]=" 11839 + queue.mBroadcastsScheduled); 11840 } 11841 pw.println(" mHandler:"); 11842 mHandler.dump(new PrintWriterPrinter(pw), " "); 11843 needSep = true; 11844 printedAnything = true; 11845 } 11846 11847 if (!printedAnything) { 11848 pw.println(" (nothing)"); 11849 } 11850 } 11851 11852 void dumpProvidersLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11853 int opti, boolean dumpAll, String dumpPackage) { 11854 boolean needSep; 11855 boolean printedAnything = false; 11856 11857 ItemMatcher matcher = new ItemMatcher(); 11858 matcher.build(args, opti); 11859 11860 pw.println("ACTIVITY MANAGER CONTENT PROVIDERS (dumpsys activity providers)"); 11861 11862 needSep = mProviderMap.dumpProvidersLocked(pw, dumpAll, dumpPackage); 11863 printedAnything |= needSep; 11864 11865 if (mLaunchingProviders.size() > 0) { 11866 boolean printed = false; 11867 for (int i=mLaunchingProviders.size()-1; i>=0; i--) { 11868 ContentProviderRecord r = mLaunchingProviders.get(i); 11869 if (dumpPackage != null && !dumpPackage.equals(r.name.getPackageName())) { 11870 continue; 11871 } 11872 if (!printed) { 11873 if (needSep) pw.println(); 11874 needSep = true; 11875 pw.println(" Launching content providers:"); 11876 printed = true; 11877 printedAnything = true; 11878 } 11879 pw.print(" Launching #"); pw.print(i); pw.print(": "); 11880 pw.println(r); 11881 } 11882 } 11883 11884 if (mGrantedUriPermissions.size() > 0) { 11885 boolean printed = false; 11886 int dumpUid = -2; 11887 if (dumpPackage != null) { 11888 try { 11889 dumpUid = mContext.getPackageManager().getPackageUid(dumpPackage, 0); 11890 } catch (NameNotFoundException e) { 11891 dumpUid = -1; 11892 } 11893 } 11894 for (int i=0; i<mGrantedUriPermissions.size(); i++) { 11895 int uid = mGrantedUriPermissions.keyAt(i); 11896 if (dumpUid >= -1 && UserHandle.getAppId(uid) != dumpUid) { 11897 continue; 11898 } 11899 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 11900 if (!printed) { 11901 if (needSep) pw.println(); 11902 needSep = true; 11903 pw.println(" Granted Uri Permissions:"); 11904 printed = true; 11905 printedAnything = true; 11906 } 11907 pw.print(" * UID "); pw.print(uid); pw.println(" holds:"); 11908 for (UriPermission perm : perms.values()) { 11909 pw.print(" "); pw.println(perm); 11910 if (dumpAll) { 11911 perm.dump(pw, " "); 11912 } 11913 } 11914 } 11915 } 11916 11917 if (!printedAnything) { 11918 pw.println(" (nothing)"); 11919 } 11920 } 11921 11922 void dumpPendingIntentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11923 int opti, boolean dumpAll, String dumpPackage) { 11924 boolean printed = false; 11925 11926 pw.println("ACTIVITY MANAGER PENDING INTENTS (dumpsys activity intents)"); 11927 11928 if (mIntentSenderRecords.size() > 0) { 11929 Iterator<WeakReference<PendingIntentRecord>> it 11930 = mIntentSenderRecords.values().iterator(); 11931 while (it.hasNext()) { 11932 WeakReference<PendingIntentRecord> ref = it.next(); 11933 PendingIntentRecord rec = ref != null ? ref.get(): null; 11934 if (dumpPackage != null && (rec == null 11935 || !dumpPackage.equals(rec.key.packageName))) { 11936 continue; 11937 } 11938 printed = true; 11939 if (rec != null) { 11940 pw.print(" * "); pw.println(rec); 11941 if (dumpAll) { 11942 rec.dump(pw, " "); 11943 } 11944 } else { 11945 pw.print(" * "); pw.println(ref); 11946 } 11947 } 11948 } 11949 11950 if (!printed) { 11951 pw.println(" (nothing)"); 11952 } 11953 } 11954 11955 private static final int dumpProcessList(PrintWriter pw, 11956 ActivityManagerService service, List list, 11957 String prefix, String normalLabel, String persistentLabel, 11958 String dumpPackage) { 11959 int numPers = 0; 11960 final int N = list.size()-1; 11961 for (int i=N; i>=0; i--) { 11962 ProcessRecord r = (ProcessRecord)list.get(i); 11963 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 11964 continue; 11965 } 11966 pw.println(String.format("%s%s #%2d: %s", 11967 prefix, (r.persistent ? persistentLabel : normalLabel), 11968 i, r.toString())); 11969 if (r.persistent) { 11970 numPers++; 11971 } 11972 } 11973 return numPers; 11974 } 11975 11976 private static final boolean dumpProcessOomList(PrintWriter pw, 11977 ActivityManagerService service, List<ProcessRecord> origList, 11978 String prefix, String normalLabel, String persistentLabel, 11979 boolean inclDetails, String dumpPackage) { 11980 11981 ArrayList<Pair<ProcessRecord, Integer>> list 11982 = new ArrayList<Pair<ProcessRecord, Integer>>(origList.size()); 11983 for (int i=0; i<origList.size(); i++) { 11984 ProcessRecord r = origList.get(i); 11985 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11986 continue; 11987 } 11988 list.add(new Pair<ProcessRecord, Integer>(origList.get(i), i)); 11989 } 11990 11991 if (list.size() <= 0) { 11992 return false; 11993 } 11994 11995 Comparator<Pair<ProcessRecord, Integer>> comparator 11996 = new Comparator<Pair<ProcessRecord, Integer>>() { 11997 @Override 11998 public int compare(Pair<ProcessRecord, Integer> object1, 11999 Pair<ProcessRecord, Integer> object2) { 12000 if (object1.first.setAdj != object2.first.setAdj) { 12001 return object1.first.setAdj > object2.first.setAdj ? -1 : 1; 12002 } 12003 if (object1.second.intValue() != object2.second.intValue()) { 12004 return object1.second.intValue() > object2.second.intValue() ? -1 : 1; 12005 } 12006 return 0; 12007 } 12008 }; 12009 12010 Collections.sort(list, comparator); 12011 12012 final long curRealtime = SystemClock.elapsedRealtime(); 12013 final long realtimeSince = curRealtime - service.mLastPowerCheckRealtime; 12014 final long curUptime = SystemClock.uptimeMillis(); 12015 final long uptimeSince = curUptime - service.mLastPowerCheckUptime; 12016 12017 for (int i=list.size()-1; i>=0; i--) { 12018 ProcessRecord r = list.get(i).first; 12019 String oomAdj = ProcessList.makeOomAdjString(r.setAdj); 12020 char schedGroup; 12021 switch (r.setSchedGroup) { 12022 case Process.THREAD_GROUP_BG_NONINTERACTIVE: 12023 schedGroup = 'B'; 12024 break; 12025 case Process.THREAD_GROUP_DEFAULT: 12026 schedGroup = 'F'; 12027 break; 12028 default: 12029 schedGroup = '?'; 12030 break; 12031 } 12032 char foreground; 12033 if (r.foregroundActivities) { 12034 foreground = 'A'; 12035 } else if (r.foregroundServices) { 12036 foreground = 'S'; 12037 } else { 12038 foreground = ' '; 12039 } 12040 String procState = ProcessList.makeProcStateString(r.curProcState); 12041 pw.print(prefix); 12042 pw.print(r.persistent ? persistentLabel : normalLabel); 12043 pw.print(" #"); 12044 int num = (origList.size()-1)-list.get(i).second; 12045 if (num < 10) pw.print(' '); 12046 pw.print(num); 12047 pw.print(": "); 12048 pw.print(oomAdj); 12049 pw.print(' '); 12050 pw.print(schedGroup); 12051 pw.print('/'); 12052 pw.print(foreground); 12053 pw.print('/'); 12054 pw.print(procState); 12055 pw.print(" trm:"); 12056 if (r.trimMemoryLevel < 10) pw.print(' '); 12057 pw.print(r.trimMemoryLevel); 12058 pw.print(' '); 12059 pw.print(r.toShortString()); 12060 pw.print(" ("); 12061 pw.print(r.adjType); 12062 pw.println(')'); 12063 if (r.adjSource != null || r.adjTarget != null) { 12064 pw.print(prefix); 12065 pw.print(" "); 12066 if (r.adjTarget instanceof ComponentName) { 12067 pw.print(((ComponentName)r.adjTarget).flattenToShortString()); 12068 } else if (r.adjTarget != null) { 12069 pw.print(r.adjTarget.toString()); 12070 } else { 12071 pw.print("{null}"); 12072 } 12073 pw.print("<="); 12074 if (r.adjSource instanceof ProcessRecord) { 12075 pw.print("Proc{"); 12076 pw.print(((ProcessRecord)r.adjSource).toShortString()); 12077 pw.println("}"); 12078 } else if (r.adjSource != null) { 12079 pw.println(r.adjSource.toString()); 12080 } else { 12081 pw.println("{null}"); 12082 } 12083 } 12084 if (inclDetails) { 12085 pw.print(prefix); 12086 pw.print(" "); 12087 pw.print("oom: max="); pw.print(r.maxAdj); 12088 pw.print(" curRaw="); pw.print(r.curRawAdj); 12089 pw.print(" setRaw="); pw.print(r.setRawAdj); 12090 pw.print(" cur="); pw.print(r.curAdj); 12091 pw.print(" set="); pw.println(r.setAdj); 12092 pw.print(prefix); 12093 pw.print(" "); 12094 pw.print("state: cur="); pw.print(ProcessList.makeProcStateString(r.curProcState)); 12095 pw.print(" set="); pw.print(ProcessList.makeProcStateString(r.setProcState)); 12096 pw.print(" lastPss="); pw.print(r.lastPss); 12097 pw.print(" lastCachedPss="); pw.println(r.lastCachedPss); 12098 pw.print(prefix); 12099 pw.print(" "); 12100 pw.print("keeping="); pw.print(r.keeping); 12101 pw.print(" cached="); pw.print(r.cached); 12102 pw.print(" empty="); pw.print(r.empty); 12103 pw.print(" hasAboveClient="); pw.println(r.hasAboveClient); 12104 12105 if (!r.keeping) { 12106 if (r.lastWakeTime != 0) { 12107 long wtime; 12108 BatteryStatsImpl stats = service.mBatteryStatsService.getActiveStatistics(); 12109 synchronized (stats) { 12110 wtime = stats.getProcessWakeTime(r.info.uid, 12111 r.pid, curRealtime); 12112 } 12113 long timeUsed = wtime - r.lastWakeTime; 12114 pw.print(prefix); 12115 pw.print(" "); 12116 pw.print("keep awake over "); 12117 TimeUtils.formatDuration(realtimeSince, pw); 12118 pw.print(" used "); 12119 TimeUtils.formatDuration(timeUsed, pw); 12120 pw.print(" ("); 12121 pw.print((timeUsed*100)/realtimeSince); 12122 pw.println("%)"); 12123 } 12124 if (r.lastCpuTime != 0) { 12125 long timeUsed = r.curCpuTime - r.lastCpuTime; 12126 pw.print(prefix); 12127 pw.print(" "); 12128 pw.print("run cpu over "); 12129 TimeUtils.formatDuration(uptimeSince, pw); 12130 pw.print(" used "); 12131 TimeUtils.formatDuration(timeUsed, pw); 12132 pw.print(" ("); 12133 pw.print((timeUsed*100)/uptimeSince); 12134 pw.println("%)"); 12135 } 12136 } 12137 } 12138 } 12139 return true; 12140 } 12141 12142 ArrayList<ProcessRecord> collectProcesses(PrintWriter pw, int start, String[] args) { 12143 ArrayList<ProcessRecord> procs; 12144 synchronized (this) { 12145 if (args != null && args.length > start 12146 && args[start].charAt(0) != '-') { 12147 procs = new ArrayList<ProcessRecord>(); 12148 int pid = -1; 12149 try { 12150 pid = Integer.parseInt(args[start]); 12151 } catch (NumberFormatException e) { 12152 } 12153 for (int i=mLruProcesses.size()-1; i>=0; i--) { 12154 ProcessRecord proc = mLruProcesses.get(i); 12155 if (proc.pid == pid) { 12156 procs.add(proc); 12157 } else if (proc.processName.equals(args[start])) { 12158 procs.add(proc); 12159 } 12160 } 12161 if (procs.size() <= 0) { 12162 return null; 12163 } 12164 } else { 12165 procs = new ArrayList<ProcessRecord>(mLruProcesses); 12166 } 12167 } 12168 return procs; 12169 } 12170 12171 final void dumpGraphicsHardwareUsage(FileDescriptor fd, 12172 PrintWriter pw, String[] args) { 12173 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 12174 if (procs == null) { 12175 pw.println("No process found for: " + args[0]); 12176 return; 12177 } 12178 12179 long uptime = SystemClock.uptimeMillis(); 12180 long realtime = SystemClock.elapsedRealtime(); 12181 pw.println("Applications Graphics Acceleration Info:"); 12182 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 12183 12184 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12185 ProcessRecord r = procs.get(i); 12186 if (r.thread != null) { 12187 pw.println("\n** Graphics info for pid " + r.pid + " [" + r.processName + "] **"); 12188 pw.flush(); 12189 try { 12190 TransferPipe tp = new TransferPipe(); 12191 try { 12192 r.thread.dumpGfxInfo(tp.getWriteFd().getFileDescriptor(), args); 12193 tp.go(fd); 12194 } finally { 12195 tp.kill(); 12196 } 12197 } catch (IOException e) { 12198 pw.println("Failure while dumping the app: " + r); 12199 pw.flush(); 12200 } catch (RemoteException e) { 12201 pw.println("Got a RemoteException while dumping the app " + r); 12202 pw.flush(); 12203 } 12204 } 12205 } 12206 } 12207 12208 final void dumpDbInfo(FileDescriptor fd, PrintWriter pw, String[] args) { 12209 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 12210 if (procs == null) { 12211 pw.println("No process found for: " + args[0]); 12212 return; 12213 } 12214 12215 pw.println("Applications Database Info:"); 12216 12217 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12218 ProcessRecord r = procs.get(i); 12219 if (r.thread != null) { 12220 pw.println("\n** Database info for pid " + r.pid + " [" + r.processName + "] **"); 12221 pw.flush(); 12222 try { 12223 TransferPipe tp = new TransferPipe(); 12224 try { 12225 r.thread.dumpDbInfo(tp.getWriteFd().getFileDescriptor(), args); 12226 tp.go(fd); 12227 } finally { 12228 tp.kill(); 12229 } 12230 } catch (IOException e) { 12231 pw.println("Failure while dumping the app: " + r); 12232 pw.flush(); 12233 } catch (RemoteException e) { 12234 pw.println("Got a RemoteException while dumping the app " + r); 12235 pw.flush(); 12236 } 12237 } 12238 } 12239 } 12240 12241 final static class MemItem { 12242 final boolean isProc; 12243 final String label; 12244 final String shortLabel; 12245 final long pss; 12246 final int id; 12247 final boolean hasActivities; 12248 ArrayList<MemItem> subitems; 12249 12250 public MemItem(String _label, String _shortLabel, long _pss, int _id, 12251 boolean _hasActivities) { 12252 isProc = true; 12253 label = _label; 12254 shortLabel = _shortLabel; 12255 pss = _pss; 12256 id = _id; 12257 hasActivities = _hasActivities; 12258 } 12259 12260 public MemItem(String _label, String _shortLabel, long _pss, int _id) { 12261 isProc = false; 12262 label = _label; 12263 shortLabel = _shortLabel; 12264 pss = _pss; 12265 id = _id; 12266 hasActivities = false; 12267 } 12268 } 12269 12270 static final void dumpMemItems(PrintWriter pw, String prefix, String tag, 12271 ArrayList<MemItem> items, boolean sort, boolean isCompact) { 12272 if (sort && !isCompact) { 12273 Collections.sort(items, new Comparator<MemItem>() { 12274 @Override 12275 public int compare(MemItem lhs, MemItem rhs) { 12276 if (lhs.pss < rhs.pss) { 12277 return 1; 12278 } else if (lhs.pss > rhs.pss) { 12279 return -1; 12280 } 12281 return 0; 12282 } 12283 }); 12284 } 12285 12286 for (int i=0; i<items.size(); i++) { 12287 MemItem mi = items.get(i); 12288 if (!isCompact) { 12289 pw.print(prefix); pw.printf("%7d kB: ", mi.pss); pw.println(mi.label); 12290 } else if (mi.isProc) { 12291 pw.print("proc,"); pw.print(tag); pw.print(","); pw.print(mi.shortLabel); 12292 pw.print(","); pw.print(mi.id); pw.print(","); pw.print(mi.pss); 12293 pw.println(mi.hasActivities ? ",a" : ",e"); 12294 } else { 12295 pw.print(tag); pw.print(","); pw.print(mi.shortLabel); pw.print(","); 12296 pw.println(mi.pss); 12297 } 12298 if (mi.subitems != null) { 12299 dumpMemItems(pw, prefix + " ", mi.shortLabel, mi.subitems, 12300 true, isCompact); 12301 } 12302 } 12303 } 12304 12305 // These are in KB. 12306 static final long[] DUMP_MEM_BUCKETS = new long[] { 12307 5*1024, 7*1024, 10*1024, 15*1024, 20*1024, 30*1024, 40*1024, 80*1024, 12308 120*1024, 160*1024, 200*1024, 12309 250*1024, 300*1024, 350*1024, 400*1024, 500*1024, 600*1024, 800*1024, 12310 1*1024*1024, 2*1024*1024, 5*1024*1024, 10*1024*1024, 20*1024*1024 12311 }; 12312 12313 static final void appendMemBucket(StringBuilder out, long memKB, String label, 12314 boolean stackLike) { 12315 int start = label.lastIndexOf('.'); 12316 if (start >= 0) start++; 12317 else start = 0; 12318 int end = label.length(); 12319 for (int i=0; i<DUMP_MEM_BUCKETS.length; i++) { 12320 if (DUMP_MEM_BUCKETS[i] >= memKB) { 12321 long bucket = DUMP_MEM_BUCKETS[i]/1024; 12322 out.append(bucket); 12323 out.append(stackLike ? "MB." : "MB "); 12324 out.append(label, start, end); 12325 return; 12326 } 12327 } 12328 out.append(memKB/1024); 12329 out.append(stackLike ? "MB." : "MB "); 12330 out.append(label, start, end); 12331 } 12332 12333 static final int[] DUMP_MEM_OOM_ADJ = new int[] { 12334 ProcessList.NATIVE_ADJ, 12335 ProcessList.SYSTEM_ADJ, ProcessList.PERSISTENT_PROC_ADJ, ProcessList.FOREGROUND_APP_ADJ, 12336 ProcessList.VISIBLE_APP_ADJ, ProcessList.PERCEPTIBLE_APP_ADJ, 12337 ProcessList.BACKUP_APP_ADJ, ProcessList.HEAVY_WEIGHT_APP_ADJ, 12338 ProcessList.SERVICE_ADJ, ProcessList.HOME_APP_ADJ, 12339 ProcessList.PREVIOUS_APP_ADJ, ProcessList.SERVICE_B_ADJ, ProcessList.CACHED_APP_MAX_ADJ 12340 }; 12341 static final String[] DUMP_MEM_OOM_LABEL = new String[] { 12342 "Native", 12343 "System", "Persistent", "Foreground", 12344 "Visible", "Perceptible", 12345 "Heavy Weight", "Backup", 12346 "A Services", "Home", 12347 "Previous", "B Services", "Cached" 12348 }; 12349 static final String[] DUMP_MEM_OOM_COMPACT_LABEL = new String[] { 12350 "native", 12351 "sys", "pers", "fore", 12352 "vis", "percept", 12353 "heavy", "backup", 12354 "servicea", "home", 12355 "prev", "serviceb", "cached" 12356 }; 12357 12358 private final void dumpApplicationMemoryUsageHeader(PrintWriter pw, long uptime, 12359 long realtime, boolean isCheckinRequest, boolean isCompact) { 12360 if (isCheckinRequest || isCompact) { 12361 // short checkin version 12362 pw.print("time,"); pw.print(uptime); pw.print(","); pw.println(realtime); 12363 } else { 12364 pw.println("Applications Memory Usage (kB):"); 12365 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 12366 } 12367 } 12368 12369 final void dumpApplicationMemoryUsage(FileDescriptor fd, 12370 PrintWriter pw, String prefix, String[] args, boolean brief, PrintWriter categoryPw) { 12371 boolean dumpDetails = false; 12372 boolean dumpFullDetails = false; 12373 boolean dumpDalvik = false; 12374 boolean oomOnly = false; 12375 boolean isCompact = false; 12376 boolean localOnly = false; 12377 12378 int opti = 0; 12379 while (opti < args.length) { 12380 String opt = args[opti]; 12381 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 12382 break; 12383 } 12384 opti++; 12385 if ("-a".equals(opt)) { 12386 dumpDetails = true; 12387 dumpFullDetails = true; 12388 dumpDalvik = true; 12389 } else if ("-d".equals(opt)) { 12390 dumpDalvik = true; 12391 } else if ("-c".equals(opt)) { 12392 isCompact = true; 12393 } else if ("--oom".equals(opt)) { 12394 oomOnly = true; 12395 } else if ("--local".equals(opt)) { 12396 localOnly = true; 12397 } else if ("-h".equals(opt)) { 12398 pw.println("meminfo dump options: [-a] [-d] [-c] [--oom] [process]"); 12399 pw.println(" -a: include all available information for each process."); 12400 pw.println(" -d: include dalvik details when dumping process details."); 12401 pw.println(" -c: dump in a compact machine-parseable representation."); 12402 pw.println(" --oom: only show processes organized by oom adj."); 12403 pw.println(" --local: only collect details locally, don't call process."); 12404 pw.println("If [process] is specified it can be the name or "); 12405 pw.println("pid of a specific process to dump."); 12406 return; 12407 } else { 12408 pw.println("Unknown argument: " + opt + "; use -h for help"); 12409 } 12410 } 12411 12412 final boolean isCheckinRequest = scanArgs(args, "--checkin"); 12413 long uptime = SystemClock.uptimeMillis(); 12414 long realtime = SystemClock.elapsedRealtime(); 12415 final long[] tmpLong = new long[1]; 12416 12417 ArrayList<ProcessRecord> procs = collectProcesses(pw, opti, args); 12418 if (procs == null) { 12419 // No Java processes. Maybe they want to print a native process. 12420 if (args != null && args.length > opti 12421 && args[opti].charAt(0) != '-') { 12422 ArrayList<ProcessCpuTracker.Stats> nativeProcs 12423 = new ArrayList<ProcessCpuTracker.Stats>(); 12424 updateCpuStatsNow(); 12425 int findPid = -1; 12426 try { 12427 findPid = Integer.parseInt(args[opti]); 12428 } catch (NumberFormatException e) { 12429 } 12430 synchronized (mProcessCpuThread) { 12431 final int N = mProcessCpuTracker.countStats(); 12432 for (int i=0; i<N; i++) { 12433 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 12434 if (st.pid == findPid || (st.baseName != null 12435 && st.baseName.equals(args[opti]))) { 12436 nativeProcs.add(st); 12437 } 12438 } 12439 } 12440 if (nativeProcs.size() > 0) { 12441 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, 12442 isCompact); 12443 Debug.MemoryInfo mi = null; 12444 for (int i = nativeProcs.size() - 1 ; i >= 0 ; i--) { 12445 final ProcessCpuTracker.Stats r = nativeProcs.get(i); 12446 final int pid = r.pid; 12447 if (!isCheckinRequest && dumpDetails) { 12448 pw.println("\n** MEMINFO in pid " + pid + " [" + r.baseName + "] **"); 12449 } 12450 if (mi == null) { 12451 mi = new Debug.MemoryInfo(); 12452 } 12453 if (dumpDetails || (!brief && !oomOnly)) { 12454 Debug.getMemoryInfo(pid, mi); 12455 } else { 12456 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 12457 mi.dalvikPrivateDirty = (int)tmpLong[0]; 12458 } 12459 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 12460 dumpDalvik, pid, r.baseName, 0, 0, 0, 0, 0, 0); 12461 if (isCheckinRequest) { 12462 pw.println(); 12463 } 12464 } 12465 return; 12466 } 12467 } 12468 pw.println("No process found for: " + args[opti]); 12469 return; 12470 } 12471 12472 if (!brief && !oomOnly && (procs.size() == 1 || isCheckinRequest)) { 12473 dumpDetails = true; 12474 } 12475 12476 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, isCompact); 12477 12478 String[] innerArgs = new String[args.length-opti]; 12479 System.arraycopy(args, opti, innerArgs, 0, args.length-opti); 12480 12481 ArrayList<MemItem> procMems = new ArrayList<MemItem>(); 12482 final SparseArray<MemItem> procMemsMap = new SparseArray<MemItem>(); 12483 long nativePss=0, dalvikPss=0, otherPss=0; 12484 long[] miscPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 12485 12486 long oomPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 12487 ArrayList<MemItem>[] oomProcs = (ArrayList<MemItem>[]) 12488 new ArrayList[DUMP_MEM_OOM_LABEL.length]; 12489 12490 long totalPss = 0; 12491 long cachedPss = 0; 12492 12493 Debug.MemoryInfo mi = null; 12494 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12495 final ProcessRecord r = procs.get(i); 12496 final IApplicationThread thread; 12497 final int pid; 12498 final int oomAdj; 12499 final boolean hasActivities; 12500 synchronized (this) { 12501 thread = r.thread; 12502 pid = r.pid; 12503 oomAdj = r.getSetAdjWithServices(); 12504 hasActivities = r.activities.size() > 0; 12505 } 12506 if (thread != null) { 12507 if (!isCheckinRequest && dumpDetails) { 12508 pw.println("\n** MEMINFO in pid " + pid + " [" + r.processName + "] **"); 12509 } 12510 if (mi == null) { 12511 mi = new Debug.MemoryInfo(); 12512 } 12513 if (dumpDetails || (!brief && !oomOnly)) { 12514 Debug.getMemoryInfo(pid, mi); 12515 } else { 12516 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 12517 mi.dalvikPrivateDirty = (int)tmpLong[0]; 12518 } 12519 if (dumpDetails) { 12520 if (localOnly) { 12521 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 12522 dumpDalvik, pid, r.processName, 0, 0, 0, 0, 0, 0); 12523 if (isCheckinRequest) { 12524 pw.println(); 12525 } 12526 } else { 12527 try { 12528 pw.flush(); 12529 thread.dumpMemInfo(fd, mi, isCheckinRequest, dumpFullDetails, 12530 dumpDalvik, innerArgs); 12531 } catch (RemoteException e) { 12532 if (!isCheckinRequest) { 12533 pw.println("Got RemoteException!"); 12534 pw.flush(); 12535 } 12536 } 12537 } 12538 } 12539 12540 final long myTotalPss = mi.getTotalPss(); 12541 final long myTotalUss = mi.getTotalUss(); 12542 12543 synchronized (this) { 12544 if (r.thread != null && oomAdj == r.getSetAdjWithServices()) { 12545 // Record this for posterity if the process has been stable. 12546 r.baseProcessTracker.addPss(myTotalPss, myTotalUss, true, r.pkgList); 12547 } 12548 } 12549 12550 if (!isCheckinRequest && mi != null) { 12551 totalPss += myTotalPss; 12552 MemItem pssItem = new MemItem(r.processName + " (pid " + pid + 12553 (hasActivities ? " / activities)" : ")"), 12554 r.processName, myTotalPss, pid, hasActivities); 12555 procMems.add(pssItem); 12556 procMemsMap.put(pid, pssItem); 12557 12558 nativePss += mi.nativePss; 12559 dalvikPss += mi.dalvikPss; 12560 otherPss += mi.otherPss; 12561 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 12562 long mem = mi.getOtherPss(j); 12563 miscPss[j] += mem; 12564 otherPss -= mem; 12565 } 12566 12567 if (oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 12568 cachedPss += myTotalPss; 12569 } 12570 12571 for (int oomIndex=0; oomIndex<oomPss.length; oomIndex++) { 12572 if (oomAdj <= DUMP_MEM_OOM_ADJ[oomIndex] 12573 || oomIndex == (oomPss.length-1)) { 12574 oomPss[oomIndex] += myTotalPss; 12575 if (oomProcs[oomIndex] == null) { 12576 oomProcs[oomIndex] = new ArrayList<MemItem>(); 12577 } 12578 oomProcs[oomIndex].add(pssItem); 12579 break; 12580 } 12581 } 12582 } 12583 } 12584 } 12585 12586 if (!isCheckinRequest && procs.size() > 1) { 12587 // If we are showing aggregations, also look for native processes to 12588 // include so that our aggregations are more accurate. 12589 updateCpuStatsNow(); 12590 synchronized (mProcessCpuThread) { 12591 final int N = mProcessCpuTracker.countStats(); 12592 for (int i=0; i<N; i++) { 12593 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 12594 if (st.vsize > 0 && procMemsMap.indexOfKey(st.pid) < 0) { 12595 if (mi == null) { 12596 mi = new Debug.MemoryInfo(); 12597 } 12598 if (!brief && !oomOnly) { 12599 Debug.getMemoryInfo(st.pid, mi); 12600 } else { 12601 mi.nativePss = (int)Debug.getPss(st.pid, tmpLong); 12602 mi.nativePrivateDirty = (int)tmpLong[0]; 12603 } 12604 12605 final long myTotalPss = mi.getTotalPss(); 12606 totalPss += myTotalPss; 12607 12608 MemItem pssItem = new MemItem(st.name + " (pid " + st.pid + ")", 12609 st.name, myTotalPss, st.pid, false); 12610 procMems.add(pssItem); 12611 12612 nativePss += mi.nativePss; 12613 dalvikPss += mi.dalvikPss; 12614 otherPss += mi.otherPss; 12615 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 12616 long mem = mi.getOtherPss(j); 12617 miscPss[j] += mem; 12618 otherPss -= mem; 12619 } 12620 oomPss[0] += myTotalPss; 12621 if (oomProcs[0] == null) { 12622 oomProcs[0] = new ArrayList<MemItem>(); 12623 } 12624 oomProcs[0].add(pssItem); 12625 } 12626 } 12627 } 12628 12629 ArrayList<MemItem> catMems = new ArrayList<MemItem>(); 12630 12631 catMems.add(new MemItem("Native", "Native", nativePss, -1)); 12632 catMems.add(new MemItem("Dalvik", "Dalvik", dalvikPss, -2)); 12633 catMems.add(new MemItem("Unknown", "Unknown", otherPss, -3)); 12634 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 12635 String label = Debug.MemoryInfo.getOtherLabel(j); 12636 catMems.add(new MemItem(label, label, miscPss[j], j)); 12637 } 12638 12639 ArrayList<MemItem> oomMems = new ArrayList<MemItem>(); 12640 for (int j=0; j<oomPss.length; j++) { 12641 if (oomPss[j] != 0) { 12642 String label = isCompact ? DUMP_MEM_OOM_COMPACT_LABEL[j] 12643 : DUMP_MEM_OOM_LABEL[j]; 12644 MemItem item = new MemItem(label, label, oomPss[j], 12645 DUMP_MEM_OOM_ADJ[j]); 12646 item.subitems = oomProcs[j]; 12647 oomMems.add(item); 12648 } 12649 } 12650 12651 if (!brief && !oomOnly && !isCompact) { 12652 pw.println(); 12653 pw.println("Total PSS by process:"); 12654 dumpMemItems(pw, " ", "proc", procMems, true, isCompact); 12655 pw.println(); 12656 } 12657 if (!isCompact) { 12658 pw.println("Total PSS by OOM adjustment:"); 12659 } 12660 dumpMemItems(pw, " ", "oom", oomMems, false, isCompact); 12661 if (!brief && !oomOnly) { 12662 PrintWriter out = categoryPw != null ? categoryPw : pw; 12663 if (!isCompact) { 12664 out.println(); 12665 out.println("Total PSS by category:"); 12666 } 12667 dumpMemItems(out, " ", "cat", catMems, true, isCompact); 12668 } 12669 if (!isCompact) { 12670 pw.println(); 12671 } 12672 MemInfoReader memInfo = new MemInfoReader(); 12673 memInfo.readMemInfo(); 12674 if (!brief) { 12675 if (!isCompact) { 12676 pw.print("Total RAM: "); pw.print(memInfo.getTotalSizeKb()); 12677 pw.print(" kB (status "); 12678 switch (mLastMemoryLevel) { 12679 case ProcessStats.ADJ_MEM_FACTOR_NORMAL: 12680 pw.println("normal)"); 12681 break; 12682 case ProcessStats.ADJ_MEM_FACTOR_MODERATE: 12683 pw.println("moderate)"); 12684 break; 12685 case ProcessStats.ADJ_MEM_FACTOR_LOW: 12686 pw.println("low)"); 12687 break; 12688 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 12689 pw.println("critical)"); 12690 break; 12691 default: 12692 pw.print(mLastMemoryLevel); 12693 pw.println(")"); 12694 break; 12695 } 12696 pw.print(" Free RAM: "); pw.print(cachedPss + memInfo.getCachedSizeKb() 12697 + memInfo.getFreeSizeKb()); pw.print(" kB ("); 12698 pw.print(cachedPss); pw.print(" cached pss + "); 12699 pw.print(memInfo.getCachedSizeKb()); pw.print(" cached + "); 12700 pw.print(memInfo.getFreeSizeKb()); pw.println(" free)"); 12701 } else { 12702 pw.print("ram,"); pw.print(memInfo.getTotalSizeKb()); pw.print(","); 12703 pw.print(cachedPss + memInfo.getCachedSizeKb() 12704 + memInfo.getFreeSizeKb()); pw.print(","); 12705 pw.println(totalPss - cachedPss); 12706 } 12707 } 12708 if (!isCompact) { 12709 pw.print(" Used RAM: "); pw.print(totalPss - cachedPss 12710 + memInfo.getBuffersSizeKb() + memInfo.getShmemSizeKb() 12711 + memInfo.getSlabSizeKb()); pw.print(" kB ("); 12712 pw.print(totalPss - cachedPss); pw.print(" used pss + "); 12713 pw.print(memInfo.getBuffersSizeKb()); pw.print(" buffers + "); 12714 pw.print(memInfo.getShmemSizeKb()); pw.print(" shmem + "); 12715 pw.print(memInfo.getSlabSizeKb()); pw.println(" slab)"); 12716 pw.print(" Lost RAM: "); pw.print(memInfo.getTotalSizeKb() 12717 - totalPss - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 12718 - memInfo.getBuffersSizeKb() - memInfo.getShmemSizeKb() 12719 - memInfo.getSlabSizeKb()); pw.println(" kB"); 12720 } 12721 if (!brief) { 12722 if (memInfo.getZramTotalSizeKb() != 0) { 12723 if (!isCompact) { 12724 pw.print(" ZRAM: "); pw.print(memInfo.getZramTotalSizeKb()); 12725 pw.print(" kB physical used for "); 12726 pw.print(memInfo.getSwapTotalSizeKb() 12727 - memInfo.getSwapFreeSizeKb()); 12728 pw.print(" kB in swap ("); 12729 pw.print(memInfo.getSwapTotalSizeKb()); 12730 pw.println(" kB total swap)"); 12731 } else { 12732 pw.print("zram,"); pw.print(memInfo.getZramTotalSizeKb()); pw.print(","); 12733 pw.print(memInfo.getSwapTotalSizeKb()); pw.print(","); 12734 pw.println(memInfo.getSwapFreeSizeKb()); 12735 } 12736 } 12737 final int[] SINGLE_LONG_FORMAT = new int[] { 12738 Process.PROC_SPACE_TERM|Process.PROC_OUT_LONG 12739 }; 12740 long[] longOut = new long[1]; 12741 Process.readProcFile("/sys/kernel/mm/ksm/pages_shared", 12742 SINGLE_LONG_FORMAT, null, longOut, null); 12743 long shared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 12744 longOut[0] = 0; 12745 Process.readProcFile("/sys/kernel/mm/ksm/pages_sharing", 12746 SINGLE_LONG_FORMAT, null, longOut, null); 12747 long sharing = longOut[0] * ProcessList.PAGE_SIZE / 1024; 12748 longOut[0] = 0; 12749 Process.readProcFile("/sys/kernel/mm/ksm/pages_unshared", 12750 SINGLE_LONG_FORMAT, null, longOut, null); 12751 long unshared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 12752 longOut[0] = 0; 12753 Process.readProcFile("/sys/kernel/mm/ksm/pages_volatile", 12754 SINGLE_LONG_FORMAT, null, longOut, null); 12755 long voltile = longOut[0] * ProcessList.PAGE_SIZE / 1024; 12756 if (!isCompact) { 12757 if (sharing != 0 || shared != 0 || unshared != 0 || voltile != 0) { 12758 pw.print(" KSM: "); pw.print(sharing); 12759 pw.print(" kB saved from shared "); 12760 pw.print(shared); pw.println(" kB"); 12761 pw.print(" "); pw.print(unshared); pw.print(" kB unshared; "); 12762 pw.print(voltile); pw.println(" kB volatile"); 12763 } 12764 pw.print(" Tuning: "); 12765 pw.print(ActivityManager.staticGetMemoryClass()); 12766 pw.print(" (large "); 12767 pw.print(ActivityManager.staticGetLargeMemoryClass()); 12768 pw.print("), oom "); 12769 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 12770 pw.print(" kB"); 12771 pw.print(", restore limit "); 12772 pw.print(mProcessList.getCachedRestoreThresholdKb()); 12773 pw.print(" kB"); 12774 if (ActivityManager.isLowRamDeviceStatic()) { 12775 pw.print(" (low-ram)"); 12776 } 12777 if (ActivityManager.isHighEndGfx()) { 12778 pw.print(" (high-end-gfx)"); 12779 } 12780 pw.println(); 12781 } else { 12782 pw.print("ksm,"); pw.print(sharing); pw.print(","); 12783 pw.print(shared); pw.print(","); pw.print(unshared); pw.print(","); 12784 pw.println(voltile); 12785 pw.print("tuning,"); 12786 pw.print(ActivityManager.staticGetMemoryClass()); 12787 pw.print(','); 12788 pw.print(ActivityManager.staticGetLargeMemoryClass()); 12789 pw.print(','); 12790 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 12791 if (ActivityManager.isLowRamDeviceStatic()) { 12792 pw.print(",low-ram"); 12793 } 12794 if (ActivityManager.isHighEndGfx()) { 12795 pw.print(",high-end-gfx"); 12796 } 12797 pw.println(); 12798 } 12799 } 12800 } 12801 } 12802 12803 /** 12804 * Searches array of arguments for the specified string 12805 * @param args array of argument strings 12806 * @param value value to search for 12807 * @return true if the value is contained in the array 12808 */ 12809 private static boolean scanArgs(String[] args, String value) { 12810 if (args != null) { 12811 for (String arg : args) { 12812 if (value.equals(arg)) { 12813 return true; 12814 } 12815 } 12816 } 12817 return false; 12818 } 12819 12820 private final boolean removeDyingProviderLocked(ProcessRecord proc, 12821 ContentProviderRecord cpr, boolean always) { 12822 final boolean inLaunching = mLaunchingProviders.contains(cpr); 12823 12824 if (!inLaunching || always) { 12825 synchronized (cpr) { 12826 cpr.launchingApp = null; 12827 cpr.notifyAll(); 12828 } 12829 mProviderMap.removeProviderByClass(cpr.name, UserHandle.getUserId(cpr.uid)); 12830 String names[] = cpr.info.authority.split(";"); 12831 for (int j = 0; j < names.length; j++) { 12832 mProviderMap.removeProviderByName(names[j], UserHandle.getUserId(cpr.uid)); 12833 } 12834 } 12835 12836 for (int i=0; i<cpr.connections.size(); i++) { 12837 ContentProviderConnection conn = cpr.connections.get(i); 12838 if (conn.waiting) { 12839 // If this connection is waiting for the provider, then we don't 12840 // need to mess with its process unless we are always removing 12841 // or for some reason the provider is not currently launching. 12842 if (inLaunching && !always) { 12843 continue; 12844 } 12845 } 12846 ProcessRecord capp = conn.client; 12847 conn.dead = true; 12848 if (conn.stableCount > 0) { 12849 if (!capp.persistent && capp.thread != null 12850 && capp.pid != 0 12851 && capp.pid != MY_PID) { 12852 killUnneededProcessLocked(capp, "depends on provider " 12853 + cpr.name.flattenToShortString() 12854 + " in dying proc " + (proc != null ? proc.processName : "??")); 12855 } 12856 } else if (capp.thread != null && conn.provider.provider != null) { 12857 try { 12858 capp.thread.unstableProviderDied(conn.provider.provider.asBinder()); 12859 } catch (RemoteException e) { 12860 } 12861 // In the protocol here, we don't expect the client to correctly 12862 // clean up this connection, we'll just remove it. 12863 cpr.connections.remove(i); 12864 conn.client.conProviders.remove(conn); 12865 } 12866 } 12867 12868 if (inLaunching && always) { 12869 mLaunchingProviders.remove(cpr); 12870 } 12871 return inLaunching; 12872 } 12873 12874 /** 12875 * Main code for cleaning up a process when it has gone away. This is 12876 * called both as a result of the process dying, or directly when stopping 12877 * a process when running in single process mode. 12878 */ 12879 private final void cleanUpApplicationRecordLocked(ProcessRecord app, 12880 boolean restarting, boolean allowRestart, int index) { 12881 if (index >= 0) { 12882 removeLruProcessLocked(app); 12883 ProcessList.remove(app.pid); 12884 } 12885 12886 mProcessesToGc.remove(app); 12887 mPendingPssProcesses.remove(app); 12888 12889 // Dismiss any open dialogs. 12890 if (app.crashDialog != null && !app.forceCrashReport) { 12891 app.crashDialog.dismiss(); 12892 app.crashDialog = null; 12893 } 12894 if (app.anrDialog != null) { 12895 app.anrDialog.dismiss(); 12896 app.anrDialog = null; 12897 } 12898 if (app.waitDialog != null) { 12899 app.waitDialog.dismiss(); 12900 app.waitDialog = null; 12901 } 12902 12903 app.crashing = false; 12904 app.notResponding = false; 12905 12906 app.resetPackageList(mProcessStats); 12907 app.unlinkDeathRecipient(); 12908 app.makeInactive(mProcessStats); 12909 app.forcingToForeground = null; 12910 updateProcessForegroundLocked(app, false, false); 12911 app.foregroundActivities = false; 12912 app.hasShownUi = false; 12913 app.treatLikeActivity = false; 12914 app.hasAboveClient = false; 12915 app.hasClientActivities = false; 12916 12917 mServices.killServicesLocked(app, allowRestart); 12918 12919 boolean restart = false; 12920 12921 // Remove published content providers. 12922 for (int i=app.pubProviders.size()-1; i>=0; i--) { 12923 ContentProviderRecord cpr = app.pubProviders.valueAt(i); 12924 final boolean always = app.bad || !allowRestart; 12925 if (removeDyingProviderLocked(app, cpr, always) || always) { 12926 // We left the provider in the launching list, need to 12927 // restart it. 12928 restart = true; 12929 } 12930 12931 cpr.provider = null; 12932 cpr.proc = null; 12933 } 12934 app.pubProviders.clear(); 12935 12936 // Take care of any launching providers waiting for this process. 12937 if (checkAppInLaunchingProvidersLocked(app, false)) { 12938 restart = true; 12939 } 12940 12941 // Unregister from connected content providers. 12942 if (!app.conProviders.isEmpty()) { 12943 for (int i=0; i<app.conProviders.size(); i++) { 12944 ContentProviderConnection conn = app.conProviders.get(i); 12945 conn.provider.connections.remove(conn); 12946 } 12947 app.conProviders.clear(); 12948 } 12949 12950 // At this point there may be remaining entries in mLaunchingProviders 12951 // where we were the only one waiting, so they are no longer of use. 12952 // Look for these and clean up if found. 12953 // XXX Commented out for now. Trying to figure out a way to reproduce 12954 // the actual situation to identify what is actually going on. 12955 if (false) { 12956 for (int i=0; i<mLaunchingProviders.size(); i++) { 12957 ContentProviderRecord cpr = (ContentProviderRecord) 12958 mLaunchingProviders.get(i); 12959 if (cpr.connections.size() <= 0 && !cpr.hasExternalProcessHandles()) { 12960 synchronized (cpr) { 12961 cpr.launchingApp = null; 12962 cpr.notifyAll(); 12963 } 12964 } 12965 } 12966 } 12967 12968 skipCurrentReceiverLocked(app); 12969 12970 // Unregister any receivers. 12971 for (int i=app.receivers.size()-1; i>=0; i--) { 12972 removeReceiverLocked(app.receivers.valueAt(i)); 12973 } 12974 app.receivers.clear(); 12975 12976 // If the app is undergoing backup, tell the backup manager about it 12977 if (mBackupTarget != null && app.pid == mBackupTarget.app.pid) { 12978 if (DEBUG_BACKUP || DEBUG_CLEANUP) Slog.d(TAG, "App " 12979 + mBackupTarget.appInfo + " died during backup"); 12980 try { 12981 IBackupManager bm = IBackupManager.Stub.asInterface( 12982 ServiceManager.getService(Context.BACKUP_SERVICE)); 12983 bm.agentDisconnected(app.info.packageName); 12984 } catch (RemoteException e) { 12985 // can't happen; backup manager is local 12986 } 12987 } 12988 12989 for (int i = mPendingProcessChanges.size()-1; i>=0; i--) { 12990 ProcessChangeItem item = mPendingProcessChanges.get(i); 12991 if (item.pid == app.pid) { 12992 mPendingProcessChanges.remove(i); 12993 mAvailProcessChanges.add(item); 12994 } 12995 } 12996 mHandler.obtainMessage(DISPATCH_PROCESS_DIED, app.pid, app.info.uid, null).sendToTarget(); 12997 12998 // If the caller is restarting this app, then leave it in its 12999 // current lists and let the caller take care of it. 13000 if (restarting) { 13001 return; 13002 } 13003 13004 if (!app.persistent || app.isolated) { 13005 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, 13006 "Removing non-persistent process during cleanup: " + app); 13007 mProcessNames.remove(app.processName, app.uid); 13008 mIsolatedProcesses.remove(app.uid); 13009 if (mHeavyWeightProcess == app) { 13010 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 13011 mHeavyWeightProcess.userId, 0)); 13012 mHeavyWeightProcess = null; 13013 } 13014 } else if (!app.removed) { 13015 // This app is persistent, so we need to keep its record around. 13016 // If it is not already on the pending app list, add it there 13017 // and start a new process for it. 13018 if (mPersistentStartingProcesses.indexOf(app) < 0) { 13019 mPersistentStartingProcesses.add(app); 13020 restart = true; 13021 } 13022 } 13023 if ((DEBUG_PROCESSES || DEBUG_CLEANUP) && mProcessesOnHold.contains(app)) Slog.v(TAG, 13024 "Clean-up removing on hold: " + app); 13025 mProcessesOnHold.remove(app); 13026 13027 if (app == mHomeProcess) { 13028 mHomeProcess = null; 13029 } 13030 if (app == mPreviousProcess) { 13031 mPreviousProcess = null; 13032 } 13033 13034 if (restart && !app.isolated) { 13035 // We have components that still need to be running in the 13036 // process, so re-launch it. 13037 mProcessNames.put(app.processName, app.uid, app); 13038 startProcessLocked(app, "restart", app.processName, null /* ABI override */); 13039 } else if (app.pid > 0 && app.pid != MY_PID) { 13040 // Goodbye! 13041 boolean removed; 13042 synchronized (mPidsSelfLocked) { 13043 mPidsSelfLocked.remove(app.pid); 13044 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 13045 } 13046 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_PROC_FINISH, 13047 app.processName, app.info.uid); 13048 if (app.isolated) { 13049 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 13050 } 13051 app.setPid(0); 13052 } 13053 } 13054 13055 boolean checkAppInLaunchingProvidersLocked(ProcessRecord app, boolean alwaysBad) { 13056 // Look through the content providers we are waiting to have launched, 13057 // and if any run in this process then either schedule a restart of 13058 // the process or kill the client waiting for it if this process has 13059 // gone bad. 13060 int NL = mLaunchingProviders.size(); 13061 boolean restart = false; 13062 for (int i=0; i<NL; i++) { 13063 ContentProviderRecord cpr = mLaunchingProviders.get(i); 13064 if (cpr.launchingApp == app) { 13065 if (!alwaysBad && !app.bad) { 13066 restart = true; 13067 } else { 13068 removeDyingProviderLocked(app, cpr, true); 13069 // cpr should have been removed from mLaunchingProviders 13070 NL = mLaunchingProviders.size(); 13071 i--; 13072 } 13073 } 13074 } 13075 return restart; 13076 } 13077 13078 // ========================================================= 13079 // SERVICES 13080 // ========================================================= 13081 13082 public List<ActivityManager.RunningServiceInfo> getServices(int maxNum, 13083 int flags) { 13084 enforceNotIsolatedCaller("getServices"); 13085 synchronized (this) { 13086 return mServices.getRunningServiceInfoLocked(maxNum, flags); 13087 } 13088 } 13089 13090 public PendingIntent getRunningServiceControlPanel(ComponentName name) { 13091 enforceNotIsolatedCaller("getRunningServiceControlPanel"); 13092 synchronized (this) { 13093 return mServices.getRunningServiceControlPanelLocked(name); 13094 } 13095 } 13096 13097 public ComponentName startService(IApplicationThread caller, Intent service, 13098 String resolvedType, int userId) { 13099 enforceNotIsolatedCaller("startService"); 13100 // Refuse possible leaked file descriptors 13101 if (service != null && service.hasFileDescriptors() == true) { 13102 throw new IllegalArgumentException("File descriptors passed in Intent"); 13103 } 13104 13105 if (DEBUG_SERVICE) 13106 Slog.v(TAG, "startService: " + service + " type=" + resolvedType); 13107 synchronized(this) { 13108 final int callingPid = Binder.getCallingPid(); 13109 final int callingUid = Binder.getCallingUid(); 13110 final long origId = Binder.clearCallingIdentity(); 13111 ComponentName res = mServices.startServiceLocked(caller, service, 13112 resolvedType, callingPid, callingUid, userId); 13113 Binder.restoreCallingIdentity(origId); 13114 return res; 13115 } 13116 } 13117 13118 ComponentName startServiceInPackage(int uid, 13119 Intent service, String resolvedType, int userId) { 13120 synchronized(this) { 13121 if (DEBUG_SERVICE) 13122 Slog.v(TAG, "startServiceInPackage: " + service + " type=" + resolvedType); 13123 final long origId = Binder.clearCallingIdentity(); 13124 ComponentName res = mServices.startServiceLocked(null, service, 13125 resolvedType, -1, uid, userId); 13126 Binder.restoreCallingIdentity(origId); 13127 return res; 13128 } 13129 } 13130 13131 public int stopService(IApplicationThread caller, Intent service, 13132 String resolvedType, int userId) { 13133 enforceNotIsolatedCaller("stopService"); 13134 // Refuse possible leaked file descriptors 13135 if (service != null && service.hasFileDescriptors() == true) { 13136 throw new IllegalArgumentException("File descriptors passed in Intent"); 13137 } 13138 13139 synchronized(this) { 13140 return mServices.stopServiceLocked(caller, service, resolvedType, userId); 13141 } 13142 } 13143 13144 public IBinder peekService(Intent service, String resolvedType) { 13145 enforceNotIsolatedCaller("peekService"); 13146 // Refuse possible leaked file descriptors 13147 if (service != null && service.hasFileDescriptors() == true) { 13148 throw new IllegalArgumentException("File descriptors passed in Intent"); 13149 } 13150 synchronized(this) { 13151 return mServices.peekServiceLocked(service, resolvedType); 13152 } 13153 } 13154 13155 public boolean stopServiceToken(ComponentName className, IBinder token, 13156 int startId) { 13157 synchronized(this) { 13158 return mServices.stopServiceTokenLocked(className, token, startId); 13159 } 13160 } 13161 13162 public void setServiceForeground(ComponentName className, IBinder token, 13163 int id, Notification notification, boolean removeNotification) { 13164 synchronized(this) { 13165 mServices.setServiceForegroundLocked(className, token, id, notification, 13166 removeNotification); 13167 } 13168 } 13169 13170 public int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 13171 boolean requireFull, String name, String callerPackage) { 13172 final int callingUserId = UserHandle.getUserId(callingUid); 13173 if (callingUserId != userId) { 13174 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 13175 if ((requireFull || checkComponentPermission( 13176 android.Manifest.permission.INTERACT_ACROSS_USERS, 13177 callingPid, callingUid, -1, true) != PackageManager.PERMISSION_GRANTED) 13178 && checkComponentPermission(INTERACT_ACROSS_USERS_FULL, 13179 callingPid, callingUid, -1, true) 13180 != PackageManager.PERMISSION_GRANTED) { 13181 if (userId == UserHandle.USER_CURRENT_OR_SELF) { 13182 // In this case, they would like to just execute as their 13183 // owner user instead of failing. 13184 userId = callingUserId; 13185 } else { 13186 StringBuilder builder = new StringBuilder(128); 13187 builder.append("Permission Denial: "); 13188 builder.append(name); 13189 if (callerPackage != null) { 13190 builder.append(" from "); 13191 builder.append(callerPackage); 13192 } 13193 builder.append(" asks to run as user "); 13194 builder.append(userId); 13195 builder.append(" but is calling from user "); 13196 builder.append(UserHandle.getUserId(callingUid)); 13197 builder.append("; this requires "); 13198 builder.append(INTERACT_ACROSS_USERS_FULL); 13199 if (!requireFull) { 13200 builder.append(" or "); 13201 builder.append(android.Manifest.permission.INTERACT_ACROSS_USERS); 13202 } 13203 String msg = builder.toString(); 13204 Slog.w(TAG, msg); 13205 throw new SecurityException(msg); 13206 } 13207 } 13208 } 13209 if (userId == UserHandle.USER_CURRENT 13210 || userId == UserHandle.USER_CURRENT_OR_SELF) { 13211 // Note that we may be accessing this outside of a lock... 13212 // shouldn't be a big deal, if this is being called outside 13213 // of a locked context there is intrinsically a race with 13214 // the value the caller will receive and someone else changing it. 13215 userId = mCurrentUserId; 13216 } 13217 if (!allowAll && userId < 0) { 13218 throw new IllegalArgumentException( 13219 "Call does not support special user #" + userId); 13220 } 13221 } 13222 return userId; 13223 } 13224 13225 boolean isSingleton(String componentProcessName, ApplicationInfo aInfo, 13226 String className, int flags) { 13227 boolean result = false; 13228 // For apps that don't have pre-defined UIDs, check for permission 13229 if (UserHandle.getAppId(aInfo.uid) >= Process.FIRST_APPLICATION_UID) { 13230 if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 13231 if (ActivityManager.checkUidPermission( 13232 android.Manifest.permission.INTERACT_ACROSS_USERS, 13233 aInfo.uid) != PackageManager.PERMISSION_GRANTED) { 13234 ComponentName comp = new ComponentName(aInfo.packageName, className); 13235 String msg = "Permission Denial: Component " + comp.flattenToShortString() 13236 + " requests FLAG_SINGLE_USER, but app does not hold " 13237 + android.Manifest.permission.INTERACT_ACROSS_USERS; 13238 Slog.w(TAG, msg); 13239 throw new SecurityException(msg); 13240 } 13241 // Permission passed 13242 result = true; 13243 } 13244 } else if ("system".equals(componentProcessName)) { 13245 result = true; 13246 } else { 13247 // App with pre-defined UID, check if it's a persistent app 13248 result = (aInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0; 13249 } 13250 if (DEBUG_MU) { 13251 Slog.v(TAG, "isSingleton(" + componentProcessName + ", " + aInfo 13252 + ", " + className + ", 0x" + Integer.toHexString(flags) + ") = " + result); 13253 } 13254 return result; 13255 } 13256 13257 /** 13258 * Checks to see if the caller is in the same app as the singleton 13259 * component, or the component is in a special app. It allows special apps 13260 * to export singleton components but prevents exporting singleton 13261 * components for regular apps. 13262 */ 13263 boolean isValidSingletonCall(int callingUid, int componentUid) { 13264 int componentAppId = UserHandle.getAppId(componentUid); 13265 return UserHandle.isSameApp(callingUid, componentUid) 13266 || componentAppId == Process.SYSTEM_UID 13267 || componentAppId == Process.PHONE_UID 13268 || ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, componentUid) 13269 == PackageManager.PERMISSION_GRANTED; 13270 } 13271 13272 public int bindService(IApplicationThread caller, IBinder token, 13273 Intent service, String resolvedType, 13274 IServiceConnection connection, int flags, int userId) { 13275 enforceNotIsolatedCaller("bindService"); 13276 // Refuse possible leaked file descriptors 13277 if (service != null && service.hasFileDescriptors() == true) { 13278 throw new IllegalArgumentException("File descriptors passed in Intent"); 13279 } 13280 13281 synchronized(this) { 13282 return mServices.bindServiceLocked(caller, token, service, resolvedType, 13283 connection, flags, userId); 13284 } 13285 } 13286 13287 public boolean unbindService(IServiceConnection connection) { 13288 synchronized (this) { 13289 return mServices.unbindServiceLocked(connection); 13290 } 13291 } 13292 13293 public void publishService(IBinder token, Intent intent, IBinder service) { 13294 // Refuse possible leaked file descriptors 13295 if (intent != null && intent.hasFileDescriptors() == true) { 13296 throw new IllegalArgumentException("File descriptors passed in Intent"); 13297 } 13298 13299 synchronized(this) { 13300 if (!(token instanceof ServiceRecord)) { 13301 throw new IllegalArgumentException("Invalid service token"); 13302 } 13303 mServices.publishServiceLocked((ServiceRecord)token, intent, service); 13304 } 13305 } 13306 13307 public void unbindFinished(IBinder token, Intent intent, boolean doRebind) { 13308 // Refuse possible leaked file descriptors 13309 if (intent != null && intent.hasFileDescriptors() == true) { 13310 throw new IllegalArgumentException("File descriptors passed in Intent"); 13311 } 13312 13313 synchronized(this) { 13314 mServices.unbindFinishedLocked((ServiceRecord)token, intent, doRebind); 13315 } 13316 } 13317 13318 public void serviceDoneExecuting(IBinder token, int type, int startId, int res) { 13319 synchronized(this) { 13320 if (!(token instanceof ServiceRecord)) { 13321 throw new IllegalArgumentException("Invalid service token"); 13322 } 13323 mServices.serviceDoneExecutingLocked((ServiceRecord)token, type, startId, res); 13324 } 13325 } 13326 13327 // ========================================================= 13328 // BACKUP AND RESTORE 13329 // ========================================================= 13330 13331 // Cause the target app to be launched if necessary and its backup agent 13332 // instantiated. The backup agent will invoke backupAgentCreated() on the 13333 // activity manager to announce its creation. 13334 public boolean bindBackupAgent(ApplicationInfo app, int backupMode) { 13335 if (DEBUG_BACKUP) Slog.v(TAG, "bindBackupAgent: app=" + app + " mode=" + backupMode); 13336 enforceCallingPermission("android.permission.BACKUP", "bindBackupAgent"); 13337 13338 synchronized(this) { 13339 // !!! TODO: currently no check here that we're already bound 13340 BatteryStatsImpl.Uid.Pkg.Serv ss = null; 13341 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 13342 synchronized (stats) { 13343 ss = stats.getServiceStatsLocked(app.uid, app.packageName, app.name); 13344 } 13345 13346 // Backup agent is now in use, its package can't be stopped. 13347 try { 13348 AppGlobals.getPackageManager().setPackageStoppedState( 13349 app.packageName, false, UserHandle.getUserId(app.uid)); 13350 } catch (RemoteException e) { 13351 } catch (IllegalArgumentException e) { 13352 Slog.w(TAG, "Failed trying to unstop package " 13353 + app.packageName + ": " + e); 13354 } 13355 13356 BackupRecord r = new BackupRecord(ss, app, backupMode); 13357 ComponentName hostingName = (backupMode == IApplicationThread.BACKUP_MODE_INCREMENTAL) 13358 ? new ComponentName(app.packageName, app.backupAgentName) 13359 : new ComponentName("android", "FullBackupAgent"); 13360 // startProcessLocked() returns existing proc's record if it's already running 13361 ProcessRecord proc = startProcessLocked(app.processName, app, 13362 false, 0, "backup", hostingName, false, false, false); 13363 if (proc == null) { 13364 Slog.e(TAG, "Unable to start backup agent process " + r); 13365 return false; 13366 } 13367 13368 r.app = proc; 13369 mBackupTarget = r; 13370 mBackupAppName = app.packageName; 13371 13372 // Try not to kill the process during backup 13373 updateOomAdjLocked(proc); 13374 13375 // If the process is already attached, schedule the creation of the backup agent now. 13376 // If it is not yet live, this will be done when it attaches to the framework. 13377 if (proc.thread != null) { 13378 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc already running: " + proc); 13379 try { 13380 proc.thread.scheduleCreateBackupAgent(app, 13381 compatibilityInfoForPackageLocked(app), backupMode); 13382 } catch (RemoteException e) { 13383 // Will time out on the backup manager side 13384 } 13385 } else { 13386 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc not running, waiting for attach"); 13387 } 13388 // Invariants: at this point, the target app process exists and the application 13389 // is either already running or in the process of coming up. mBackupTarget and 13390 // mBackupAppName describe the app, so that when it binds back to the AM we 13391 // know that it's scheduled for a backup-agent operation. 13392 } 13393 13394 return true; 13395 } 13396 13397 @Override 13398 public void clearPendingBackup() { 13399 if (DEBUG_BACKUP) Slog.v(TAG, "clearPendingBackup"); 13400 enforceCallingPermission("android.permission.BACKUP", "clearPendingBackup"); 13401 13402 synchronized (this) { 13403 mBackupTarget = null; 13404 mBackupAppName = null; 13405 } 13406 } 13407 13408 // A backup agent has just come up 13409 public void backupAgentCreated(String agentPackageName, IBinder agent) { 13410 if (DEBUG_BACKUP) Slog.v(TAG, "backupAgentCreated: " + agentPackageName 13411 + " = " + agent); 13412 13413 synchronized(this) { 13414 if (!agentPackageName.equals(mBackupAppName)) { 13415 Slog.e(TAG, "Backup agent created for " + agentPackageName + " but not requested!"); 13416 return; 13417 } 13418 } 13419 13420 long oldIdent = Binder.clearCallingIdentity(); 13421 try { 13422 IBackupManager bm = IBackupManager.Stub.asInterface( 13423 ServiceManager.getService(Context.BACKUP_SERVICE)); 13424 bm.agentConnected(agentPackageName, agent); 13425 } catch (RemoteException e) { 13426 // can't happen; the backup manager service is local 13427 } catch (Exception e) { 13428 Slog.w(TAG, "Exception trying to deliver BackupAgent binding: "); 13429 e.printStackTrace(); 13430 } finally { 13431 Binder.restoreCallingIdentity(oldIdent); 13432 } 13433 } 13434 13435 // done with this agent 13436 public void unbindBackupAgent(ApplicationInfo appInfo) { 13437 if (DEBUG_BACKUP) Slog.v(TAG, "unbindBackupAgent: " + appInfo); 13438 if (appInfo == null) { 13439 Slog.w(TAG, "unbind backup agent for null app"); 13440 return; 13441 } 13442 13443 synchronized(this) { 13444 try { 13445 if (mBackupAppName == null) { 13446 Slog.w(TAG, "Unbinding backup agent with no active backup"); 13447 return; 13448 } 13449 13450 if (!mBackupAppName.equals(appInfo.packageName)) { 13451 Slog.e(TAG, "Unbind of " + appInfo + " but is not the current backup target"); 13452 return; 13453 } 13454 13455 // Not backing this app up any more; reset its OOM adjustment 13456 final ProcessRecord proc = mBackupTarget.app; 13457 updateOomAdjLocked(proc); 13458 13459 // If the app crashed during backup, 'thread' will be null here 13460 if (proc.thread != null) { 13461 try { 13462 proc.thread.scheduleDestroyBackupAgent(appInfo, 13463 compatibilityInfoForPackageLocked(appInfo)); 13464 } catch (Exception e) { 13465 Slog.e(TAG, "Exception when unbinding backup agent:"); 13466 e.printStackTrace(); 13467 } 13468 } 13469 } finally { 13470 mBackupTarget = null; 13471 mBackupAppName = null; 13472 } 13473 } 13474 } 13475 // ========================================================= 13476 // BROADCASTS 13477 // ========================================================= 13478 13479 private final List getStickiesLocked(String action, IntentFilter filter, 13480 List cur, int userId) { 13481 final ContentResolver resolver = mContext.getContentResolver(); 13482 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 13483 if (stickies == null) { 13484 return cur; 13485 } 13486 final ArrayList<Intent> list = stickies.get(action); 13487 if (list == null) { 13488 return cur; 13489 } 13490 int N = list.size(); 13491 for (int i=0; i<N; i++) { 13492 Intent intent = list.get(i); 13493 if (filter.match(resolver, intent, true, TAG) >= 0) { 13494 if (cur == null) { 13495 cur = new ArrayList<Intent>(); 13496 } 13497 cur.add(intent); 13498 } 13499 } 13500 return cur; 13501 } 13502 13503 boolean isPendingBroadcastProcessLocked(int pid) { 13504 return mFgBroadcastQueue.isPendingBroadcastProcessLocked(pid) 13505 || mBgBroadcastQueue.isPendingBroadcastProcessLocked(pid); 13506 } 13507 13508 void skipPendingBroadcastLocked(int pid) { 13509 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 13510 for (BroadcastQueue queue : mBroadcastQueues) { 13511 queue.skipPendingBroadcastLocked(pid); 13512 } 13513 } 13514 13515 // The app just attached; send any pending broadcasts that it should receive 13516 boolean sendPendingBroadcastsLocked(ProcessRecord app) { 13517 boolean didSomething = false; 13518 for (BroadcastQueue queue : mBroadcastQueues) { 13519 didSomething |= queue.sendPendingBroadcastsLocked(app); 13520 } 13521 return didSomething; 13522 } 13523 13524 public Intent registerReceiver(IApplicationThread caller, String callerPackage, 13525 IIntentReceiver receiver, IntentFilter filter, String permission, int userId) { 13526 enforceNotIsolatedCaller("registerReceiver"); 13527 int callingUid; 13528 int callingPid; 13529 synchronized(this) { 13530 ProcessRecord callerApp = null; 13531 if (caller != null) { 13532 callerApp = getRecordForAppLocked(caller); 13533 if (callerApp == null) { 13534 throw new SecurityException( 13535 "Unable to find app for caller " + caller 13536 + " (pid=" + Binder.getCallingPid() 13537 + ") when registering receiver " + receiver); 13538 } 13539 if (callerApp.info.uid != Process.SYSTEM_UID && 13540 !callerApp.pkgList.containsKey(callerPackage) && 13541 !"android".equals(callerPackage)) { 13542 throw new SecurityException("Given caller package " + callerPackage 13543 + " is not running in process " + callerApp); 13544 } 13545 callingUid = callerApp.info.uid; 13546 callingPid = callerApp.pid; 13547 } else { 13548 callerPackage = null; 13549 callingUid = Binder.getCallingUid(); 13550 callingPid = Binder.getCallingPid(); 13551 } 13552 13553 userId = this.handleIncomingUser(callingPid, callingUid, userId, 13554 true, true, "registerReceiver", callerPackage); 13555 13556 List allSticky = null; 13557 13558 // Look for any matching sticky broadcasts... 13559 Iterator actions = filter.actionsIterator(); 13560 if (actions != null) { 13561 while (actions.hasNext()) { 13562 String action = (String)actions.next(); 13563 allSticky = getStickiesLocked(action, filter, allSticky, 13564 UserHandle.USER_ALL); 13565 allSticky = getStickiesLocked(action, filter, allSticky, 13566 UserHandle.getUserId(callingUid)); 13567 } 13568 } else { 13569 allSticky = getStickiesLocked(null, filter, allSticky, 13570 UserHandle.USER_ALL); 13571 allSticky = getStickiesLocked(null, filter, allSticky, 13572 UserHandle.getUserId(callingUid)); 13573 } 13574 13575 // The first sticky in the list is returned directly back to 13576 // the client. 13577 Intent sticky = allSticky != null ? (Intent)allSticky.get(0) : null; 13578 13579 if (DEBUG_BROADCAST) Slog.v(TAG, "Register receiver " + filter 13580 + ": " + sticky); 13581 13582 if (receiver == null) { 13583 return sticky; 13584 } 13585 13586 ReceiverList rl 13587 = (ReceiverList)mRegisteredReceivers.get(receiver.asBinder()); 13588 if (rl == null) { 13589 rl = new ReceiverList(this, callerApp, callingPid, callingUid, 13590 userId, receiver); 13591 if (rl.app != null) { 13592 rl.app.receivers.add(rl); 13593 } else { 13594 try { 13595 receiver.asBinder().linkToDeath(rl, 0); 13596 } catch (RemoteException e) { 13597 return sticky; 13598 } 13599 rl.linkedToDeath = true; 13600 } 13601 mRegisteredReceivers.put(receiver.asBinder(), rl); 13602 } else if (rl.uid != callingUid) { 13603 throw new IllegalArgumentException( 13604 "Receiver requested to register for uid " + callingUid 13605 + " was previously registered for uid " + rl.uid); 13606 } else if (rl.pid != callingPid) { 13607 throw new IllegalArgumentException( 13608 "Receiver requested to register for pid " + callingPid 13609 + " was previously registered for pid " + rl.pid); 13610 } else if (rl.userId != userId) { 13611 throw new IllegalArgumentException( 13612 "Receiver requested to register for user " + userId 13613 + " was previously registered for user " + rl.userId); 13614 } 13615 BroadcastFilter bf = new BroadcastFilter(filter, rl, callerPackage, 13616 permission, callingUid, userId); 13617 rl.add(bf); 13618 if (!bf.debugCheck()) { 13619 Slog.w(TAG, "==> For Dynamic broadast"); 13620 } 13621 mReceiverResolver.addFilter(bf); 13622 13623 // Enqueue broadcasts for all existing stickies that match 13624 // this filter. 13625 if (allSticky != null) { 13626 ArrayList receivers = new ArrayList(); 13627 receivers.add(bf); 13628 13629 int N = allSticky.size(); 13630 for (int i=0; i<N; i++) { 13631 Intent intent = (Intent)allSticky.get(i); 13632 BroadcastQueue queue = broadcastQueueForIntent(intent); 13633 BroadcastRecord r = new BroadcastRecord(queue, intent, null, 13634 null, -1, -1, null, null, AppOpsManager.OP_NONE, receivers, null, 0, 13635 null, null, false, true, true, -1); 13636 queue.enqueueParallelBroadcastLocked(r); 13637 queue.scheduleBroadcastsLocked(); 13638 } 13639 } 13640 13641 return sticky; 13642 } 13643 } 13644 13645 public void unregisterReceiver(IIntentReceiver receiver) { 13646 if (DEBUG_BROADCAST) Slog.v(TAG, "Unregister receiver: " + receiver); 13647 13648 final long origId = Binder.clearCallingIdentity(); 13649 try { 13650 boolean doTrim = false; 13651 13652 synchronized(this) { 13653 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder()); 13654 if (rl != null) { 13655 if (rl.curBroadcast != null) { 13656 BroadcastRecord r = rl.curBroadcast; 13657 final boolean doNext = finishReceiverLocked( 13658 receiver.asBinder(), r.resultCode, r.resultData, 13659 r.resultExtras, r.resultAbort); 13660 if (doNext) { 13661 doTrim = true; 13662 r.queue.processNextBroadcast(false); 13663 } 13664 } 13665 13666 if (rl.app != null) { 13667 rl.app.receivers.remove(rl); 13668 } 13669 removeReceiverLocked(rl); 13670 if (rl.linkedToDeath) { 13671 rl.linkedToDeath = false; 13672 rl.receiver.asBinder().unlinkToDeath(rl, 0); 13673 } 13674 } 13675 } 13676 13677 // If we actually concluded any broadcasts, we might now be able 13678 // to trim the recipients' apps from our working set 13679 if (doTrim) { 13680 trimApplications(); 13681 return; 13682 } 13683 13684 } finally { 13685 Binder.restoreCallingIdentity(origId); 13686 } 13687 } 13688 13689 void removeReceiverLocked(ReceiverList rl) { 13690 mRegisteredReceivers.remove(rl.receiver.asBinder()); 13691 int N = rl.size(); 13692 for (int i=0; i<N; i++) { 13693 mReceiverResolver.removeFilter(rl.get(i)); 13694 } 13695 } 13696 13697 private final void sendPackageBroadcastLocked(int cmd, String[] packages, int userId) { 13698 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 13699 ProcessRecord r = mLruProcesses.get(i); 13700 if (r.thread != null && (userId == UserHandle.USER_ALL || r.userId == userId)) { 13701 try { 13702 r.thread.dispatchPackageBroadcast(cmd, packages); 13703 } catch (RemoteException ex) { 13704 } 13705 } 13706 } 13707 } 13708 13709 private List<ResolveInfo> collectReceiverComponents(Intent intent, String resolvedType, 13710 int[] users) { 13711 List<ResolveInfo> receivers = null; 13712 try { 13713 HashSet<ComponentName> singleUserReceivers = null; 13714 boolean scannedFirstReceivers = false; 13715 for (int user : users) { 13716 List<ResolveInfo> newReceivers = AppGlobals.getPackageManager() 13717 .queryIntentReceivers(intent, resolvedType, STOCK_PM_FLAGS, user); 13718 if (user != 0 && newReceivers != null) { 13719 // If this is not the primary user, we need to check for 13720 // any receivers that should be filtered out. 13721 for (int i=0; i<newReceivers.size(); i++) { 13722 ResolveInfo ri = newReceivers.get(i); 13723 if ((ri.activityInfo.flags&ActivityInfo.FLAG_PRIMARY_USER_ONLY) != 0) { 13724 newReceivers.remove(i); 13725 i--; 13726 } 13727 } 13728 } 13729 if (newReceivers != null && newReceivers.size() == 0) { 13730 newReceivers = null; 13731 } 13732 if (receivers == null) { 13733 receivers = newReceivers; 13734 } else if (newReceivers != null) { 13735 // We need to concatenate the additional receivers 13736 // found with what we have do far. This would be easy, 13737 // but we also need to de-dup any receivers that are 13738 // singleUser. 13739 if (!scannedFirstReceivers) { 13740 // Collect any single user receivers we had already retrieved. 13741 scannedFirstReceivers = true; 13742 for (int i=0; i<receivers.size(); i++) { 13743 ResolveInfo ri = receivers.get(i); 13744 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 13745 ComponentName cn = new ComponentName( 13746 ri.activityInfo.packageName, ri.activityInfo.name); 13747 if (singleUserReceivers == null) { 13748 singleUserReceivers = new HashSet<ComponentName>(); 13749 } 13750 singleUserReceivers.add(cn); 13751 } 13752 } 13753 } 13754 // Add the new results to the existing results, tracking 13755 // and de-dupping single user receivers. 13756 for (int i=0; i<newReceivers.size(); i++) { 13757 ResolveInfo ri = newReceivers.get(i); 13758 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 13759 ComponentName cn = new ComponentName( 13760 ri.activityInfo.packageName, ri.activityInfo.name); 13761 if (singleUserReceivers == null) { 13762 singleUserReceivers = new HashSet<ComponentName>(); 13763 } 13764 if (!singleUserReceivers.contains(cn)) { 13765 singleUserReceivers.add(cn); 13766 receivers.add(ri); 13767 } 13768 } else { 13769 receivers.add(ri); 13770 } 13771 } 13772 } 13773 } 13774 } catch (RemoteException ex) { 13775 // pm is in same process, this will never happen. 13776 } 13777 return receivers; 13778 } 13779 13780 private final int broadcastIntentLocked(ProcessRecord callerApp, 13781 String callerPackage, Intent intent, String resolvedType, 13782 IIntentReceiver resultTo, int resultCode, String resultData, 13783 Bundle map, String requiredPermission, int appOp, 13784 boolean ordered, boolean sticky, int callingPid, int callingUid, 13785 int userId) { 13786 intent = new Intent(intent); 13787 13788 // By default broadcasts do not go to stopped apps. 13789 intent.addFlags(Intent.FLAG_EXCLUDE_STOPPED_PACKAGES); 13790 13791 if (DEBUG_BROADCAST_LIGHT) Slog.v( 13792 TAG, (sticky ? "Broadcast sticky: ": "Broadcast: ") + intent 13793 + " ordered=" + ordered + " userid=" + userId); 13794 if ((resultTo != null) && !ordered) { 13795 Slog.w(TAG, "Broadcast " + intent + " not ordered but result callback requested!"); 13796 } 13797 13798 userId = handleIncomingUser(callingPid, callingUid, userId, 13799 true, false, "broadcast", callerPackage); 13800 13801 // Make sure that the user who is receiving this broadcast is started. 13802 // If not, we will just skip it. 13803 if (userId != UserHandle.USER_ALL && mStartedUsers.get(userId) == null) { 13804 if (callingUid != Process.SYSTEM_UID || (intent.getFlags() 13805 & Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) { 13806 Slog.w(TAG, "Skipping broadcast of " + intent 13807 + ": user " + userId + " is stopped"); 13808 return ActivityManager.BROADCAST_SUCCESS; 13809 } 13810 } 13811 13812 /* 13813 * Prevent non-system code (defined here to be non-persistent 13814 * processes) from sending protected broadcasts. 13815 */ 13816 int callingAppId = UserHandle.getAppId(callingUid); 13817 if (callingAppId == Process.SYSTEM_UID || callingAppId == Process.PHONE_UID 13818 || callingAppId == Process.SHELL_UID || callingAppId == Process.BLUETOOTH_UID 13819 || callingUid == 0) { 13820 // Always okay. 13821 } else if (callerApp == null || !callerApp.persistent) { 13822 try { 13823 if (AppGlobals.getPackageManager().isProtectedBroadcast( 13824 intent.getAction())) { 13825 String msg = "Permission Denial: not allowed to send broadcast " 13826 + intent.getAction() + " from pid=" 13827 + callingPid + ", uid=" + callingUid; 13828 Slog.w(TAG, msg); 13829 throw new SecurityException(msg); 13830 } else if (AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(intent.getAction())) { 13831 // Special case for compatibility: we don't want apps to send this, 13832 // but historically it has not been protected and apps may be using it 13833 // to poke their own app widget. So, instead of making it protected, 13834 // just limit it to the caller. 13835 if (callerApp == null) { 13836 String msg = "Permission Denial: not allowed to send broadcast " 13837 + intent.getAction() + " from unknown caller."; 13838 Slog.w(TAG, msg); 13839 throw new SecurityException(msg); 13840 } else if (intent.getComponent() != null) { 13841 // They are good enough to send to an explicit component... verify 13842 // it is being sent to the calling app. 13843 if (!intent.getComponent().getPackageName().equals( 13844 callerApp.info.packageName)) { 13845 String msg = "Permission Denial: not allowed to send broadcast " 13846 + intent.getAction() + " to " 13847 + intent.getComponent().getPackageName() + " from " 13848 + callerApp.info.packageName; 13849 Slog.w(TAG, msg); 13850 throw new SecurityException(msg); 13851 } 13852 } else { 13853 // Limit broadcast to their own package. 13854 intent.setPackage(callerApp.info.packageName); 13855 } 13856 } 13857 } catch (RemoteException e) { 13858 Slog.w(TAG, "Remote exception", e); 13859 return ActivityManager.BROADCAST_SUCCESS; 13860 } 13861 } 13862 13863 // Handle special intents: if this broadcast is from the package 13864 // manager about a package being removed, we need to remove all of 13865 // its activities from the history stack. 13866 final boolean uidRemoved = Intent.ACTION_UID_REMOVED.equals( 13867 intent.getAction()); 13868 if (Intent.ACTION_PACKAGE_REMOVED.equals(intent.getAction()) 13869 || Intent.ACTION_PACKAGE_CHANGED.equals(intent.getAction()) 13870 || Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction()) 13871 || uidRemoved) { 13872 if (checkComponentPermission( 13873 android.Manifest.permission.BROADCAST_PACKAGE_REMOVED, 13874 callingPid, callingUid, -1, true) 13875 == PackageManager.PERMISSION_GRANTED) { 13876 if (uidRemoved) { 13877 final Bundle intentExtras = intent.getExtras(); 13878 final int uid = intentExtras != null 13879 ? intentExtras.getInt(Intent.EXTRA_UID) : -1; 13880 if (uid >= 0) { 13881 BatteryStatsImpl bs = mBatteryStatsService.getActiveStatistics(); 13882 synchronized (bs) { 13883 bs.removeUidStatsLocked(uid); 13884 } 13885 mAppOpsService.uidRemoved(uid); 13886 } 13887 } else { 13888 // If resources are unavailable just force stop all 13889 // those packages and flush the attribute cache as well. 13890 if (Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction())) { 13891 String list[] = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 13892 if (list != null && (list.length > 0)) { 13893 for (String pkg : list) { 13894 forceStopPackageLocked(pkg, -1, false, true, true, false, false, userId, 13895 "storage unmount"); 13896 } 13897 sendPackageBroadcastLocked( 13898 IApplicationThread.EXTERNAL_STORAGE_UNAVAILABLE, list, userId); 13899 } 13900 } else { 13901 Uri data = intent.getData(); 13902 String ssp; 13903 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 13904 boolean removed = Intent.ACTION_PACKAGE_REMOVED.equals( 13905 intent.getAction()); 13906 boolean fullUninstall = removed && 13907 !intent.getBooleanExtra(Intent.EXTRA_REPLACING, false); 13908 if (!intent.getBooleanExtra(Intent.EXTRA_DONT_KILL_APP, false)) { 13909 forceStopPackageLocked(ssp, UserHandle.getAppId( 13910 intent.getIntExtra(Intent.EXTRA_UID, -1)), false, true, true, 13911 false, fullUninstall, userId, 13912 removed ? "pkg removed" : "pkg changed"); 13913 } 13914 if (removed) { 13915 sendPackageBroadcastLocked(IApplicationThread.PACKAGE_REMOVED, 13916 new String[] {ssp}, userId); 13917 if (!intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)) { 13918 mAppOpsService.packageRemoved( 13919 intent.getIntExtra(Intent.EXTRA_UID, -1), ssp); 13920 13921 // Remove all permissions granted from/to this package 13922 removeUriPermissionsForPackageLocked(ssp, userId, true); 13923 } 13924 } 13925 } 13926 } 13927 } 13928 } else { 13929 String msg = "Permission Denial: " + intent.getAction() 13930 + " broadcast from " + callerPackage + " (pid=" + callingPid 13931 + ", uid=" + callingUid + ")" 13932 + " requires " 13933 + android.Manifest.permission.BROADCAST_PACKAGE_REMOVED; 13934 Slog.w(TAG, msg); 13935 throw new SecurityException(msg); 13936 } 13937 13938 // Special case for adding a package: by default turn on compatibility 13939 // mode. 13940 } else if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction())) { 13941 Uri data = intent.getData(); 13942 String ssp; 13943 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 13944 mCompatModePackages.handlePackageAddedLocked(ssp, 13945 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)); 13946 } 13947 } 13948 13949 /* 13950 * If this is the time zone changed action, queue up a message that will reset the timezone 13951 * of all currently running processes. This message will get queued up before the broadcast 13952 * happens. 13953 */ 13954 if (Intent.ACTION_TIMEZONE_CHANGED.equals(intent.getAction())) { 13955 mHandler.sendEmptyMessage(UPDATE_TIME_ZONE); 13956 } 13957 13958 /* 13959 * If the user set the time, let all running processes know. 13960 */ 13961 if (Intent.ACTION_TIME_CHANGED.equals(intent.getAction())) { 13962 final int is24Hour = intent.getBooleanExtra( 13963 Intent.EXTRA_TIME_PREF_24_HOUR_FORMAT, false) ? 1 : 0; 13964 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_TIME, is24Hour, 0)); 13965 } 13966 13967 if (Intent.ACTION_CLEAR_DNS_CACHE.equals(intent.getAction())) { 13968 mHandler.sendEmptyMessage(CLEAR_DNS_CACHE_MSG); 13969 } 13970 13971 if (Proxy.PROXY_CHANGE_ACTION.equals(intent.getAction())) { 13972 ProxyInfo proxy = intent.getParcelableExtra(Proxy.EXTRA_PROXY_INFO); 13973 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_HTTP_PROXY_MSG, proxy)); 13974 } 13975 13976 // Add to the sticky list if requested. 13977 if (sticky) { 13978 if (checkPermission(android.Manifest.permission.BROADCAST_STICKY, 13979 callingPid, callingUid) 13980 != PackageManager.PERMISSION_GRANTED) { 13981 String msg = "Permission Denial: broadcastIntent() requesting a sticky broadcast from pid=" 13982 + callingPid + ", uid=" + callingUid 13983 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 13984 Slog.w(TAG, msg); 13985 throw new SecurityException(msg); 13986 } 13987 if (requiredPermission != null) { 13988 Slog.w(TAG, "Can't broadcast sticky intent " + intent 13989 + " and enforce permission " + requiredPermission); 13990 return ActivityManager.BROADCAST_STICKY_CANT_HAVE_PERMISSION; 13991 } 13992 if (intent.getComponent() != null) { 13993 throw new SecurityException( 13994 "Sticky broadcasts can't target a specific component"); 13995 } 13996 // We use userId directly here, since the "all" target is maintained 13997 // as a separate set of sticky broadcasts. 13998 if (userId != UserHandle.USER_ALL) { 13999 // But first, if this is not a broadcast to all users, then 14000 // make sure it doesn't conflict with an existing broadcast to 14001 // all users. 14002 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get( 14003 UserHandle.USER_ALL); 14004 if (stickies != null) { 14005 ArrayList<Intent> list = stickies.get(intent.getAction()); 14006 if (list != null) { 14007 int N = list.size(); 14008 int i; 14009 for (i=0; i<N; i++) { 14010 if (intent.filterEquals(list.get(i))) { 14011 throw new IllegalArgumentException( 14012 "Sticky broadcast " + intent + " for user " 14013 + userId + " conflicts with existing global broadcast"); 14014 } 14015 } 14016 } 14017 } 14018 } 14019 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 14020 if (stickies == null) { 14021 stickies = new ArrayMap<String, ArrayList<Intent>>(); 14022 mStickyBroadcasts.put(userId, stickies); 14023 } 14024 ArrayList<Intent> list = stickies.get(intent.getAction()); 14025 if (list == null) { 14026 list = new ArrayList<Intent>(); 14027 stickies.put(intent.getAction(), list); 14028 } 14029 int N = list.size(); 14030 int i; 14031 for (i=0; i<N; i++) { 14032 if (intent.filterEquals(list.get(i))) { 14033 // This sticky already exists, replace it. 14034 list.set(i, new Intent(intent)); 14035 break; 14036 } 14037 } 14038 if (i >= N) { 14039 list.add(new Intent(intent)); 14040 } 14041 } 14042 14043 int[] users; 14044 if (userId == UserHandle.USER_ALL) { 14045 // Caller wants broadcast to go to all started users. 14046 users = mStartedUserArray; 14047 } else { 14048 // Caller wants broadcast to go to one specific user. 14049 users = new int[] {userId}; 14050 } 14051 14052 // Figure out who all will receive this broadcast. 14053 List receivers = null; 14054 List<BroadcastFilter> registeredReceivers = null; 14055 // Need to resolve the intent to interested receivers... 14056 if ((intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) 14057 == 0) { 14058 receivers = collectReceiverComponents(intent, resolvedType, users); 14059 } 14060 if (intent.getComponent() == null) { 14061 registeredReceivers = mReceiverResolver.queryIntent(intent, 14062 resolvedType, false, userId); 14063 } 14064 14065 final boolean replacePending = 14066 (intent.getFlags()&Intent.FLAG_RECEIVER_REPLACE_PENDING) != 0; 14067 14068 if (DEBUG_BROADCAST) Slog.v(TAG, "Enqueing broadcast: " + intent.getAction() 14069 + " replacePending=" + replacePending); 14070 14071 int NR = registeredReceivers != null ? registeredReceivers.size() : 0; 14072 if (!ordered && NR > 0) { 14073 // If we are not serializing this broadcast, then send the 14074 // registered receivers separately so they don't wait for the 14075 // components to be launched. 14076 final BroadcastQueue queue = broadcastQueueForIntent(intent); 14077 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 14078 callerPackage, callingPid, callingUid, resolvedType, requiredPermission, 14079 appOp, registeredReceivers, resultTo, resultCode, resultData, map, 14080 ordered, sticky, false, userId); 14081 if (DEBUG_BROADCAST) Slog.v( 14082 TAG, "Enqueueing parallel broadcast " + r); 14083 final boolean replaced = replacePending && queue.replaceParallelBroadcastLocked(r); 14084 if (!replaced) { 14085 queue.enqueueParallelBroadcastLocked(r); 14086 queue.scheduleBroadcastsLocked(); 14087 } 14088 registeredReceivers = null; 14089 NR = 0; 14090 } 14091 14092 // Merge into one list. 14093 int ir = 0; 14094 if (receivers != null) { 14095 // A special case for PACKAGE_ADDED: do not allow the package 14096 // being added to see this broadcast. This prevents them from 14097 // using this as a back door to get run as soon as they are 14098 // installed. Maybe in the future we want to have a special install 14099 // broadcast or such for apps, but we'd like to deliberately make 14100 // this decision. 14101 String skipPackages[] = null; 14102 if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction()) 14103 || Intent.ACTION_PACKAGE_RESTARTED.equals(intent.getAction()) 14104 || Intent.ACTION_PACKAGE_DATA_CLEARED.equals(intent.getAction())) { 14105 Uri data = intent.getData(); 14106 if (data != null) { 14107 String pkgName = data.getSchemeSpecificPart(); 14108 if (pkgName != null) { 14109 skipPackages = new String[] { pkgName }; 14110 } 14111 } 14112 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction())) { 14113 skipPackages = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 14114 } 14115 if (skipPackages != null && (skipPackages.length > 0)) { 14116 for (String skipPackage : skipPackages) { 14117 if (skipPackage != null) { 14118 int NT = receivers.size(); 14119 for (int it=0; it<NT; it++) { 14120 ResolveInfo curt = (ResolveInfo)receivers.get(it); 14121 if (curt.activityInfo.packageName.equals(skipPackage)) { 14122 receivers.remove(it); 14123 it--; 14124 NT--; 14125 } 14126 } 14127 } 14128 } 14129 } 14130 14131 int NT = receivers != null ? receivers.size() : 0; 14132 int it = 0; 14133 ResolveInfo curt = null; 14134 BroadcastFilter curr = null; 14135 while (it < NT && ir < NR) { 14136 if (curt == null) { 14137 curt = (ResolveInfo)receivers.get(it); 14138 } 14139 if (curr == null) { 14140 curr = registeredReceivers.get(ir); 14141 } 14142 if (curr.getPriority() >= curt.priority) { 14143 // Insert this broadcast record into the final list. 14144 receivers.add(it, curr); 14145 ir++; 14146 curr = null; 14147 it++; 14148 NT++; 14149 } else { 14150 // Skip to the next ResolveInfo in the final list. 14151 it++; 14152 curt = null; 14153 } 14154 } 14155 } 14156 while (ir < NR) { 14157 if (receivers == null) { 14158 receivers = new ArrayList(); 14159 } 14160 receivers.add(registeredReceivers.get(ir)); 14161 ir++; 14162 } 14163 14164 if ((receivers != null && receivers.size() > 0) 14165 || resultTo != null) { 14166 BroadcastQueue queue = broadcastQueueForIntent(intent); 14167 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 14168 callerPackage, callingPid, callingUid, resolvedType, 14169 requiredPermission, appOp, receivers, resultTo, resultCode, 14170 resultData, map, ordered, sticky, false, userId); 14171 if (DEBUG_BROADCAST) Slog.v( 14172 TAG, "Enqueueing ordered broadcast " + r 14173 + ": prev had " + queue.mOrderedBroadcasts.size()); 14174 if (DEBUG_BROADCAST) { 14175 int seq = r.intent.getIntExtra("seq", -1); 14176 Slog.i(TAG, "Enqueueing broadcast " + r.intent.getAction() + " seq=" + seq); 14177 } 14178 boolean replaced = replacePending && queue.replaceOrderedBroadcastLocked(r); 14179 if (!replaced) { 14180 queue.enqueueOrderedBroadcastLocked(r); 14181 queue.scheduleBroadcastsLocked(); 14182 } 14183 } 14184 14185 return ActivityManager.BROADCAST_SUCCESS; 14186 } 14187 14188 final Intent verifyBroadcastLocked(Intent intent) { 14189 // Refuse possible leaked file descriptors 14190 if (intent != null && intent.hasFileDescriptors() == true) { 14191 throw new IllegalArgumentException("File descriptors passed in Intent"); 14192 } 14193 14194 int flags = intent.getFlags(); 14195 14196 if (!mProcessesReady) { 14197 // if the caller really truly claims to know what they're doing, go 14198 // ahead and allow the broadcast without launching any receivers 14199 if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT) != 0) { 14200 intent = new Intent(intent); 14201 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 14202 } else if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) { 14203 Slog.e(TAG, "Attempt to launch receivers of broadcast intent " + intent 14204 + " before boot completion"); 14205 throw new IllegalStateException("Cannot broadcast before boot completed"); 14206 } 14207 } 14208 14209 if ((flags&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 14210 throw new IllegalArgumentException( 14211 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 14212 } 14213 14214 return intent; 14215 } 14216 14217 public final int broadcastIntent(IApplicationThread caller, 14218 Intent intent, String resolvedType, IIntentReceiver resultTo, 14219 int resultCode, String resultData, Bundle map, 14220 String requiredPermission, int appOp, boolean serialized, boolean sticky, int userId) { 14221 enforceNotIsolatedCaller("broadcastIntent"); 14222 synchronized(this) { 14223 intent = verifyBroadcastLocked(intent); 14224 14225 final ProcessRecord callerApp = getRecordForAppLocked(caller); 14226 final int callingPid = Binder.getCallingPid(); 14227 final int callingUid = Binder.getCallingUid(); 14228 final long origId = Binder.clearCallingIdentity(); 14229 int res = broadcastIntentLocked(callerApp, 14230 callerApp != null ? callerApp.info.packageName : null, 14231 intent, resolvedType, resultTo, 14232 resultCode, resultData, map, requiredPermission, appOp, serialized, sticky, 14233 callingPid, callingUid, userId); 14234 Binder.restoreCallingIdentity(origId); 14235 return res; 14236 } 14237 } 14238 14239 int broadcastIntentInPackage(String packageName, int uid, 14240 Intent intent, String resolvedType, IIntentReceiver resultTo, 14241 int resultCode, String resultData, Bundle map, 14242 String requiredPermission, boolean serialized, boolean sticky, int userId) { 14243 synchronized(this) { 14244 intent = verifyBroadcastLocked(intent); 14245 14246 final long origId = Binder.clearCallingIdentity(); 14247 int res = broadcastIntentLocked(null, packageName, intent, resolvedType, 14248 resultTo, resultCode, resultData, map, requiredPermission, 14249 AppOpsManager.OP_NONE, serialized, sticky, -1, uid, userId); 14250 Binder.restoreCallingIdentity(origId); 14251 return res; 14252 } 14253 } 14254 14255 public final void unbroadcastIntent(IApplicationThread caller, Intent intent, int userId) { 14256 // Refuse possible leaked file descriptors 14257 if (intent != null && intent.hasFileDescriptors() == true) { 14258 throw new IllegalArgumentException("File descriptors passed in Intent"); 14259 } 14260 14261 userId = handleIncomingUser(Binder.getCallingPid(), 14262 Binder.getCallingUid(), userId, true, false, "removeStickyBroadcast", null); 14263 14264 synchronized(this) { 14265 if (checkCallingPermission(android.Manifest.permission.BROADCAST_STICKY) 14266 != PackageManager.PERMISSION_GRANTED) { 14267 String msg = "Permission Denial: unbroadcastIntent() from pid=" 14268 + Binder.getCallingPid() 14269 + ", uid=" + Binder.getCallingUid() 14270 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 14271 Slog.w(TAG, msg); 14272 throw new SecurityException(msg); 14273 } 14274 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 14275 if (stickies != null) { 14276 ArrayList<Intent> list = stickies.get(intent.getAction()); 14277 if (list != null) { 14278 int N = list.size(); 14279 int i; 14280 for (i=0; i<N; i++) { 14281 if (intent.filterEquals(list.get(i))) { 14282 list.remove(i); 14283 break; 14284 } 14285 } 14286 if (list.size() <= 0) { 14287 stickies.remove(intent.getAction()); 14288 } 14289 } 14290 if (stickies.size() <= 0) { 14291 mStickyBroadcasts.remove(userId); 14292 } 14293 } 14294 } 14295 } 14296 14297 private final boolean finishReceiverLocked(IBinder receiver, int resultCode, 14298 String resultData, Bundle resultExtras, boolean resultAbort) { 14299 final BroadcastRecord r = broadcastRecordForReceiverLocked(receiver); 14300 if (r == null) { 14301 Slog.w(TAG, "finishReceiver called but not found on queue"); 14302 return false; 14303 } 14304 14305 return r.queue.finishReceiverLocked(r, resultCode, resultData, resultExtras, resultAbort, false); 14306 } 14307 14308 void backgroundServicesFinishedLocked(int userId) { 14309 for (BroadcastQueue queue : mBroadcastQueues) { 14310 queue.backgroundServicesFinishedLocked(userId); 14311 } 14312 } 14313 14314 public void finishReceiver(IBinder who, int resultCode, String resultData, 14315 Bundle resultExtras, boolean resultAbort) { 14316 if (DEBUG_BROADCAST) Slog.v(TAG, "Finish receiver: " + who); 14317 14318 // Refuse possible leaked file descriptors 14319 if (resultExtras != null && resultExtras.hasFileDescriptors()) { 14320 throw new IllegalArgumentException("File descriptors passed in Bundle"); 14321 } 14322 14323 final long origId = Binder.clearCallingIdentity(); 14324 try { 14325 boolean doNext = false; 14326 BroadcastRecord r; 14327 14328 synchronized(this) { 14329 r = broadcastRecordForReceiverLocked(who); 14330 if (r != null) { 14331 doNext = r.queue.finishReceiverLocked(r, resultCode, 14332 resultData, resultExtras, resultAbort, true); 14333 } 14334 } 14335 14336 if (doNext) { 14337 r.queue.processNextBroadcast(false); 14338 } 14339 trimApplications(); 14340 } finally { 14341 Binder.restoreCallingIdentity(origId); 14342 } 14343 } 14344 14345 // ========================================================= 14346 // INSTRUMENTATION 14347 // ========================================================= 14348 14349 public boolean startInstrumentation(ComponentName className, 14350 String profileFile, int flags, Bundle arguments, 14351 IInstrumentationWatcher watcher, IUiAutomationConnection uiAutomationConnection, 14352 int userId, String abiOverride) { 14353 enforceNotIsolatedCaller("startInstrumentation"); 14354 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 14355 userId, false, true, "startInstrumentation", null); 14356 // Refuse possible leaked file descriptors 14357 if (arguments != null && arguments.hasFileDescriptors()) { 14358 throw new IllegalArgumentException("File descriptors passed in Bundle"); 14359 } 14360 14361 synchronized(this) { 14362 InstrumentationInfo ii = null; 14363 ApplicationInfo ai = null; 14364 try { 14365 ii = mContext.getPackageManager().getInstrumentationInfo( 14366 className, STOCK_PM_FLAGS); 14367 ai = AppGlobals.getPackageManager().getApplicationInfo( 14368 ii.targetPackage, STOCK_PM_FLAGS, userId); 14369 } catch (PackageManager.NameNotFoundException e) { 14370 } catch (RemoteException e) { 14371 } 14372 if (ii == null) { 14373 reportStartInstrumentationFailure(watcher, className, 14374 "Unable to find instrumentation info for: " + className); 14375 return false; 14376 } 14377 if (ai == null) { 14378 reportStartInstrumentationFailure(watcher, className, 14379 "Unable to find instrumentation target package: " + ii.targetPackage); 14380 return false; 14381 } 14382 14383 int match = mContext.getPackageManager().checkSignatures( 14384 ii.targetPackage, ii.packageName); 14385 if (match < 0 && match != PackageManager.SIGNATURE_FIRST_NOT_SIGNED) { 14386 String msg = "Permission Denial: starting instrumentation " 14387 + className + " from pid=" 14388 + Binder.getCallingPid() 14389 + ", uid=" + Binder.getCallingPid() 14390 + " not allowed because package " + ii.packageName 14391 + " does not have a signature matching the target " 14392 + ii.targetPackage; 14393 reportStartInstrumentationFailure(watcher, className, msg); 14394 throw new SecurityException(msg); 14395 } 14396 14397 final long origId = Binder.clearCallingIdentity(); 14398 // Instrumentation can kill and relaunch even persistent processes 14399 forceStopPackageLocked(ii.targetPackage, -1, true, false, true, true, false, userId, 14400 "start instr"); 14401 ProcessRecord app = addAppLocked(ai, false, abiOverride); 14402 app.instrumentationClass = className; 14403 app.instrumentationInfo = ai; 14404 app.instrumentationProfileFile = profileFile; 14405 app.instrumentationArguments = arguments; 14406 app.instrumentationWatcher = watcher; 14407 app.instrumentationUiAutomationConnection = uiAutomationConnection; 14408 app.instrumentationResultClass = className; 14409 Binder.restoreCallingIdentity(origId); 14410 } 14411 14412 return true; 14413 } 14414 14415 /** 14416 * Report errors that occur while attempting to start Instrumentation. Always writes the 14417 * error to the logs, but if somebody is watching, send the report there too. This enables 14418 * the "am" command to report errors with more information. 14419 * 14420 * @param watcher The IInstrumentationWatcher. Null if there isn't one. 14421 * @param cn The component name of the instrumentation. 14422 * @param report The error report. 14423 */ 14424 private void reportStartInstrumentationFailure(IInstrumentationWatcher watcher, 14425 ComponentName cn, String report) { 14426 Slog.w(TAG, report); 14427 try { 14428 if (watcher != null) { 14429 Bundle results = new Bundle(); 14430 results.putString(Instrumentation.REPORT_KEY_IDENTIFIER, "ActivityManagerService"); 14431 results.putString("Error", report); 14432 watcher.instrumentationStatus(cn, -1, results); 14433 } 14434 } catch (RemoteException e) { 14435 Slog.w(TAG, e); 14436 } 14437 } 14438 14439 void finishInstrumentationLocked(ProcessRecord app, int resultCode, Bundle results) { 14440 if (app.instrumentationWatcher != null) { 14441 try { 14442 // NOTE: IInstrumentationWatcher *must* be oneway here 14443 app.instrumentationWatcher.instrumentationFinished( 14444 app.instrumentationClass, 14445 resultCode, 14446 results); 14447 } catch (RemoteException e) { 14448 } 14449 } 14450 if (app.instrumentationUiAutomationConnection != null) { 14451 try { 14452 app.instrumentationUiAutomationConnection.shutdown(); 14453 } catch (RemoteException re) { 14454 /* ignore */ 14455 } 14456 // Only a UiAutomation can set this flag and now that 14457 // it is finished we make sure it is reset to its default. 14458 mUserIsMonkey = false; 14459 } 14460 app.instrumentationWatcher = null; 14461 app.instrumentationUiAutomationConnection = null; 14462 app.instrumentationClass = null; 14463 app.instrumentationInfo = null; 14464 app.instrumentationProfileFile = null; 14465 app.instrumentationArguments = null; 14466 14467 forceStopPackageLocked(app.info.packageName, -1, false, false, true, true, false, app.userId, 14468 "finished inst"); 14469 } 14470 14471 public void finishInstrumentation(IApplicationThread target, 14472 int resultCode, Bundle results) { 14473 int userId = UserHandle.getCallingUserId(); 14474 // Refuse possible leaked file descriptors 14475 if (results != null && results.hasFileDescriptors()) { 14476 throw new IllegalArgumentException("File descriptors passed in Intent"); 14477 } 14478 14479 synchronized(this) { 14480 ProcessRecord app = getRecordForAppLocked(target); 14481 if (app == null) { 14482 Slog.w(TAG, "finishInstrumentation: no app for " + target); 14483 return; 14484 } 14485 final long origId = Binder.clearCallingIdentity(); 14486 finishInstrumentationLocked(app, resultCode, results); 14487 Binder.restoreCallingIdentity(origId); 14488 } 14489 } 14490 14491 // ========================================================= 14492 // CONFIGURATION 14493 // ========================================================= 14494 14495 public ConfigurationInfo getDeviceConfigurationInfo() { 14496 ConfigurationInfo config = new ConfigurationInfo(); 14497 synchronized (this) { 14498 config.reqTouchScreen = mConfiguration.touchscreen; 14499 config.reqKeyboardType = mConfiguration.keyboard; 14500 config.reqNavigation = mConfiguration.navigation; 14501 if (mConfiguration.navigation == Configuration.NAVIGATION_DPAD 14502 || mConfiguration.navigation == Configuration.NAVIGATION_TRACKBALL) { 14503 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_FIVE_WAY_NAV; 14504 } 14505 if (mConfiguration.keyboard != Configuration.KEYBOARD_UNDEFINED 14506 && mConfiguration.keyboard != Configuration.KEYBOARD_NOKEYS) { 14507 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_HARD_KEYBOARD; 14508 } 14509 config.reqGlEsVersion = GL_ES_VERSION; 14510 } 14511 return config; 14512 } 14513 14514 ActivityStack getFocusedStack() { 14515 return mStackSupervisor.getFocusedStack(); 14516 } 14517 14518 public Configuration getConfiguration() { 14519 Configuration ci; 14520 synchronized(this) { 14521 ci = new Configuration(mConfiguration); 14522 } 14523 return ci; 14524 } 14525 14526 public void updatePersistentConfiguration(Configuration values) { 14527 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 14528 "updateConfiguration()"); 14529 enforceCallingPermission(android.Manifest.permission.WRITE_SETTINGS, 14530 "updateConfiguration()"); 14531 if (values == null) { 14532 throw new NullPointerException("Configuration must not be null"); 14533 } 14534 14535 synchronized(this) { 14536 final long origId = Binder.clearCallingIdentity(); 14537 updateConfigurationLocked(values, null, true, false); 14538 Binder.restoreCallingIdentity(origId); 14539 } 14540 } 14541 14542 public void updateConfiguration(Configuration values) { 14543 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 14544 "updateConfiguration()"); 14545 14546 synchronized(this) { 14547 if (values == null && mWindowManager != null) { 14548 // sentinel: fetch the current configuration from the window manager 14549 values = mWindowManager.computeNewConfiguration(); 14550 } 14551 14552 if (mWindowManager != null) { 14553 mProcessList.applyDisplaySize(mWindowManager); 14554 } 14555 14556 final long origId = Binder.clearCallingIdentity(); 14557 if (values != null) { 14558 Settings.System.clearConfiguration(values); 14559 } 14560 updateConfigurationLocked(values, null, false, false); 14561 Binder.restoreCallingIdentity(origId); 14562 } 14563 } 14564 14565 /** 14566 * Do either or both things: (1) change the current configuration, and (2) 14567 * make sure the given activity is running with the (now) current 14568 * configuration. Returns true if the activity has been left running, or 14569 * false if <var>starting</var> is being destroyed to match the new 14570 * configuration. 14571 * @param persistent TODO 14572 */ 14573 boolean updateConfigurationLocked(Configuration values, 14574 ActivityRecord starting, boolean persistent, boolean initLocale) { 14575 int changes = 0; 14576 14577 if (values != null) { 14578 Configuration newConfig = new Configuration(mConfiguration); 14579 changes = newConfig.updateFrom(values); 14580 if (changes != 0) { 14581 if (DEBUG_SWITCH || DEBUG_CONFIGURATION) { 14582 Slog.i(TAG, "Updating configuration to: " + values); 14583 } 14584 14585 EventLog.writeEvent(EventLogTags.CONFIGURATION_CHANGED, changes); 14586 14587 if (values.locale != null && !initLocale) { 14588 saveLocaleLocked(values.locale, 14589 !values.locale.equals(mConfiguration.locale), 14590 values.userSetLocale); 14591 } 14592 14593 mConfigurationSeq++; 14594 if (mConfigurationSeq <= 0) { 14595 mConfigurationSeq = 1; 14596 } 14597 newConfig.seq = mConfigurationSeq; 14598 mConfiguration = newConfig; 14599 Slog.i(TAG, "Config changes=" + Integer.toHexString(changes) + " " + newConfig); 14600 mUsageStatsService.noteStartConfig(newConfig); 14601 14602 final Configuration configCopy = new Configuration(mConfiguration); 14603 14604 // TODO: If our config changes, should we auto dismiss any currently 14605 // showing dialogs? 14606 mShowDialogs = shouldShowDialogs(newConfig); 14607 14608 AttributeCache ac = AttributeCache.instance(); 14609 if (ac != null) { 14610 ac.updateConfiguration(configCopy); 14611 } 14612 14613 // Make sure all resources in our process are updated 14614 // right now, so that anyone who is going to retrieve 14615 // resource values after we return will be sure to get 14616 // the new ones. This is especially important during 14617 // boot, where the first config change needs to guarantee 14618 // all resources have that config before following boot 14619 // code is executed. 14620 mSystemThread.applyConfigurationToResources(configCopy); 14621 14622 if (persistent && Settings.System.hasInterestingConfigurationChanges(changes)) { 14623 Message msg = mHandler.obtainMessage(UPDATE_CONFIGURATION_MSG); 14624 msg.obj = new Configuration(configCopy); 14625 mHandler.sendMessage(msg); 14626 } 14627 14628 for (int i=mLruProcesses.size()-1; i>=0; i--) { 14629 ProcessRecord app = mLruProcesses.get(i); 14630 try { 14631 if (app.thread != null) { 14632 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Sending to proc " 14633 + app.processName + " new config " + mConfiguration); 14634 app.thread.scheduleConfigurationChanged(configCopy); 14635 } 14636 } catch (Exception e) { 14637 } 14638 } 14639 Intent intent = new Intent(Intent.ACTION_CONFIGURATION_CHANGED); 14640 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 14641 | Intent.FLAG_RECEIVER_REPLACE_PENDING 14642 | Intent.FLAG_RECEIVER_FOREGROUND); 14643 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, 14644 null, AppOpsManager.OP_NONE, false, false, MY_PID, 14645 Process.SYSTEM_UID, UserHandle.USER_ALL); 14646 if ((changes&ActivityInfo.CONFIG_LOCALE) != 0) { 14647 intent = new Intent(Intent.ACTION_LOCALE_CHANGED); 14648 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 14649 broadcastIntentLocked(null, null, intent, 14650 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 14651 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 14652 } 14653 } 14654 } 14655 14656 boolean kept = true; 14657 final ActivityStack mainStack = mStackSupervisor.getFocusedStack(); 14658 // mainStack is null during startup. 14659 if (mainStack != null) { 14660 if (changes != 0 && starting == null) { 14661 // If the configuration changed, and the caller is not already 14662 // in the process of starting an activity, then find the top 14663 // activity to check if its configuration needs to change. 14664 starting = mainStack.topRunningActivityLocked(null); 14665 } 14666 14667 if (starting != null) { 14668 kept = mainStack.ensureActivityConfigurationLocked(starting, changes); 14669 // And we need to make sure at this point that all other activities 14670 // are made visible with the correct configuration. 14671 mStackSupervisor.ensureActivitiesVisibleLocked(starting, changes); 14672 } 14673 } 14674 14675 if (values != null && mWindowManager != null) { 14676 mWindowManager.setNewConfiguration(mConfiguration); 14677 } 14678 14679 return kept; 14680 } 14681 14682 /** 14683 * Decide based on the configuration whether we should shouw the ANR, 14684 * crash, etc dialogs. The idea is that if there is no affordnace to 14685 * press the on-screen buttons, we shouldn't show the dialog. 14686 * 14687 * A thought: SystemUI might also want to get told about this, the Power 14688 * dialog / global actions also might want different behaviors. 14689 */ 14690 private static final boolean shouldShowDialogs(Configuration config) { 14691 return !(config.keyboard == Configuration.KEYBOARD_NOKEYS 14692 && config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH); 14693 } 14694 14695 /** 14696 * Save the locale. You must be inside a synchronized (this) block. 14697 */ 14698 private void saveLocaleLocked(Locale l, boolean isDiff, boolean isPersist) { 14699 if(isDiff) { 14700 SystemProperties.set("user.language", l.getLanguage()); 14701 SystemProperties.set("user.region", l.getCountry()); 14702 } 14703 14704 if(isPersist) { 14705 SystemProperties.set("persist.sys.language", l.getLanguage()); 14706 SystemProperties.set("persist.sys.country", l.getCountry()); 14707 SystemProperties.set("persist.sys.localevar", l.getVariant()); 14708 } 14709 } 14710 14711 @Override 14712 public boolean targetTaskAffinityMatchesActivity(IBinder token, String destAffinity) { 14713 ActivityRecord srec = ActivityRecord.forToken(token); 14714 return srec != null && srec.task.affinity != null && 14715 srec.task.affinity.equals(destAffinity); 14716 } 14717 14718 public boolean navigateUpTo(IBinder token, Intent destIntent, int resultCode, 14719 Intent resultData) { 14720 14721 synchronized (this) { 14722 final ActivityStack stack = ActivityRecord.getStackLocked(token); 14723 if (stack != null) { 14724 return stack.navigateUpToLocked(token, destIntent, resultCode, resultData); 14725 } 14726 return false; 14727 } 14728 } 14729 14730 public int getLaunchedFromUid(IBinder activityToken) { 14731 ActivityRecord srec = ActivityRecord.forToken(activityToken); 14732 if (srec == null) { 14733 return -1; 14734 } 14735 return srec.launchedFromUid; 14736 } 14737 14738 public String getLaunchedFromPackage(IBinder activityToken) { 14739 ActivityRecord srec = ActivityRecord.forToken(activityToken); 14740 if (srec == null) { 14741 return null; 14742 } 14743 return srec.launchedFromPackage; 14744 } 14745 14746 // ========================================================= 14747 // LIFETIME MANAGEMENT 14748 // ========================================================= 14749 14750 // Returns which broadcast queue the app is the current [or imminent] receiver 14751 // on, or 'null' if the app is not an active broadcast recipient. 14752 private BroadcastQueue isReceivingBroadcast(ProcessRecord app) { 14753 BroadcastRecord r = app.curReceiver; 14754 if (r != null) { 14755 return r.queue; 14756 } 14757 14758 // It's not the current receiver, but it might be starting up to become one 14759 synchronized (this) { 14760 for (BroadcastQueue queue : mBroadcastQueues) { 14761 r = queue.mPendingBroadcast; 14762 if (r != null && r.curApp == app) { 14763 // found it; report which queue it's in 14764 return queue; 14765 } 14766 } 14767 } 14768 14769 return null; 14770 } 14771 14772 private final int computeOomAdjLocked(ProcessRecord app, int cachedAdj, ProcessRecord TOP_APP, 14773 boolean doingAll, long now) { 14774 if (mAdjSeq == app.adjSeq) { 14775 // This adjustment has already been computed. 14776 return app.curRawAdj; 14777 } 14778 14779 if (app.thread == null) { 14780 app.adjSeq = mAdjSeq; 14781 app.curSchedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 14782 app.curProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 14783 return (app.curAdj=app.curRawAdj=ProcessList.CACHED_APP_MAX_ADJ); 14784 } 14785 14786 app.adjTypeCode = ActivityManager.RunningAppProcessInfo.REASON_UNKNOWN; 14787 app.adjSource = null; 14788 app.adjTarget = null; 14789 app.empty = false; 14790 app.cached = false; 14791 14792 final int activitiesSize = app.activities.size(); 14793 14794 if (app.maxAdj <= ProcessList.FOREGROUND_APP_ADJ) { 14795 // The max adjustment doesn't allow this app to be anything 14796 // below foreground, so it is not worth doing work for it. 14797 app.adjType = "fixed"; 14798 app.adjSeq = mAdjSeq; 14799 app.curRawAdj = app.maxAdj; 14800 app.foregroundActivities = false; 14801 app.keeping = true; 14802 app.curSchedGroup = Process.THREAD_GROUP_DEFAULT; 14803 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT; 14804 // System processes can do UI, and when they do we want to have 14805 // them trim their memory after the user leaves the UI. To 14806 // facilitate this, here we need to determine whether or not it 14807 // is currently showing UI. 14808 app.systemNoUi = true; 14809 if (app == TOP_APP) { 14810 app.systemNoUi = false; 14811 } else if (activitiesSize > 0) { 14812 for (int j = 0; j < activitiesSize; j++) { 14813 final ActivityRecord r = app.activities.get(j); 14814 if (r.visible) { 14815 app.systemNoUi = false; 14816 } 14817 } 14818 } 14819 if (!app.systemNoUi) { 14820 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT_UI; 14821 } 14822 return (app.curAdj=app.maxAdj); 14823 } 14824 14825 app.keeping = false; 14826 app.systemNoUi = false; 14827 14828 // Determine the importance of the process, starting with most 14829 // important to least, and assign an appropriate OOM adjustment. 14830 int adj; 14831 int schedGroup; 14832 int procState; 14833 boolean foregroundActivities = false; 14834 boolean interesting = false; 14835 BroadcastQueue queue; 14836 if (app == TOP_APP) { 14837 // The last app on the list is the foreground app. 14838 adj = ProcessList.FOREGROUND_APP_ADJ; 14839 schedGroup = Process.THREAD_GROUP_DEFAULT; 14840 app.adjType = "top-activity"; 14841 foregroundActivities = true; 14842 interesting = true; 14843 procState = ActivityManager.PROCESS_STATE_TOP; 14844 } else if (app.instrumentationClass != null) { 14845 // Don't want to kill running instrumentation. 14846 adj = ProcessList.FOREGROUND_APP_ADJ; 14847 schedGroup = Process.THREAD_GROUP_DEFAULT; 14848 app.adjType = "instrumentation"; 14849 interesting = true; 14850 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 14851 } else if ((queue = isReceivingBroadcast(app)) != null) { 14852 // An app that is currently receiving a broadcast also 14853 // counts as being in the foreground for OOM killer purposes. 14854 // It's placed in a sched group based on the nature of the 14855 // broadcast as reflected by which queue it's active in. 14856 adj = ProcessList.FOREGROUND_APP_ADJ; 14857 schedGroup = (queue == mFgBroadcastQueue) 14858 ? Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 14859 app.adjType = "broadcast"; 14860 procState = ActivityManager.PROCESS_STATE_RECEIVER; 14861 } else if (app.executingServices.size() > 0) { 14862 // An app that is currently executing a service callback also 14863 // counts as being in the foreground. 14864 adj = ProcessList.FOREGROUND_APP_ADJ; 14865 schedGroup = app.execServicesFg ? 14866 Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 14867 app.adjType = "exec-service"; 14868 procState = ActivityManager.PROCESS_STATE_SERVICE; 14869 //Slog.i(TAG, "EXEC " + (app.execServicesFg ? "FG" : "BG") + ": " + app); 14870 } else { 14871 // As far as we know the process is empty. We may change our mind later. 14872 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 14873 // At this point we don't actually know the adjustment. Use the cached adj 14874 // value that the caller wants us to. 14875 adj = cachedAdj; 14876 procState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 14877 app.cached = true; 14878 app.empty = true; 14879 app.adjType = "cch-empty"; 14880 } 14881 14882 // Examine all activities if not already foreground. 14883 if (!foregroundActivities && activitiesSize > 0) { 14884 for (int j = 0; j < activitiesSize; j++) { 14885 final ActivityRecord r = app.activities.get(j); 14886 if (r.app != app) { 14887 Slog.w(TAG, "Wtf, activity " + r + " in proc activity list not using proc " 14888 + app + "?!?"); 14889 continue; 14890 } 14891 if (r.visible) { 14892 // App has a visible activity; only upgrade adjustment. 14893 if (adj > ProcessList.VISIBLE_APP_ADJ) { 14894 adj = ProcessList.VISIBLE_APP_ADJ; 14895 app.adjType = "visible"; 14896 } 14897 if (procState > ActivityManager.PROCESS_STATE_TOP) { 14898 procState = ActivityManager.PROCESS_STATE_TOP; 14899 } 14900 schedGroup = Process.THREAD_GROUP_DEFAULT; 14901 app.cached = false; 14902 app.empty = false; 14903 foregroundActivities = true; 14904 break; 14905 } else if (r.state == ActivityState.PAUSING || r.state == ActivityState.PAUSED) { 14906 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 14907 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 14908 app.adjType = "pausing"; 14909 } 14910 if (procState > ActivityManager.PROCESS_STATE_TOP) { 14911 procState = ActivityManager.PROCESS_STATE_TOP; 14912 } 14913 schedGroup = Process.THREAD_GROUP_DEFAULT; 14914 app.cached = false; 14915 app.empty = false; 14916 foregroundActivities = true; 14917 } else if (r.state == ActivityState.STOPPING) { 14918 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 14919 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 14920 app.adjType = "stopping"; 14921 } 14922 // For the process state, we will at this point consider the 14923 // process to be cached. It will be cached either as an activity 14924 // or empty depending on whether the activity is finishing. We do 14925 // this so that we can treat the process as cached for purposes of 14926 // memory trimming (determing current memory level, trim command to 14927 // send to process) since there can be an arbitrary number of stopping 14928 // processes and they should soon all go into the cached state. 14929 if (!r.finishing) { 14930 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 14931 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 14932 } 14933 } 14934 app.cached = false; 14935 app.empty = false; 14936 foregroundActivities = true; 14937 } else { 14938 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 14939 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 14940 app.adjType = "cch-act"; 14941 } 14942 } 14943 } 14944 } 14945 14946 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 14947 if (app.foregroundServices) { 14948 // The user is aware of this app, so make it visible. 14949 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 14950 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 14951 app.cached = false; 14952 app.adjType = "fg-service"; 14953 schedGroup = Process.THREAD_GROUP_DEFAULT; 14954 } else if (app.forcingToForeground != null) { 14955 // The user is aware of this app, so make it visible. 14956 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 14957 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 14958 app.cached = false; 14959 app.adjType = "force-fg"; 14960 app.adjSource = app.forcingToForeground; 14961 schedGroup = Process.THREAD_GROUP_DEFAULT; 14962 } 14963 } 14964 14965 if (app.foregroundServices) { 14966 interesting = true; 14967 } 14968 14969 if (app == mHeavyWeightProcess) { 14970 if (adj > ProcessList.HEAVY_WEIGHT_APP_ADJ) { 14971 // We don't want to kill the current heavy-weight process. 14972 adj = ProcessList.HEAVY_WEIGHT_APP_ADJ; 14973 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 14974 app.cached = false; 14975 app.adjType = "heavy"; 14976 } 14977 if (procState > ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 14978 procState = ActivityManager.PROCESS_STATE_HEAVY_WEIGHT; 14979 } 14980 } 14981 14982 if (app == mHomeProcess) { 14983 if (adj > ProcessList.HOME_APP_ADJ) { 14984 // This process is hosting what we currently consider to be the 14985 // home app, so we don't want to let it go into the background. 14986 adj = ProcessList.HOME_APP_ADJ; 14987 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 14988 app.cached = false; 14989 app.adjType = "home"; 14990 } 14991 if (procState > ActivityManager.PROCESS_STATE_HOME) { 14992 procState = ActivityManager.PROCESS_STATE_HOME; 14993 } 14994 } 14995 14996 if (app == mPreviousProcess && app.activities.size() > 0) { 14997 if (adj > ProcessList.PREVIOUS_APP_ADJ) { 14998 // This was the previous process that showed UI to the user. 14999 // We want to try to keep it around more aggressively, to give 15000 // a good experience around switching between two apps. 15001 adj = ProcessList.PREVIOUS_APP_ADJ; 15002 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15003 app.cached = false; 15004 app.adjType = "previous"; 15005 } 15006 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 15007 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 15008 } 15009 } 15010 15011 if (false) Slog.i(TAG, "OOM " + app + ": initial adj=" + adj 15012 + " reason=" + app.adjType); 15013 15014 // By default, we use the computed adjustment. It may be changed if 15015 // there are applications dependent on our services or providers, but 15016 // this gives us a baseline and makes sure we don't get into an 15017 // infinite recursion. 15018 app.adjSeq = mAdjSeq; 15019 app.curRawAdj = adj; 15020 app.hasStartedServices = false; 15021 15022 if (mBackupTarget != null && app == mBackupTarget.app) { 15023 // If possible we want to avoid killing apps while they're being backed up 15024 if (adj > ProcessList.BACKUP_APP_ADJ) { 15025 if (DEBUG_BACKUP) Slog.v(TAG, "oom BACKUP_APP_ADJ for " + app); 15026 adj = ProcessList.BACKUP_APP_ADJ; 15027 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 15028 procState = ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 15029 } 15030 app.adjType = "backup"; 15031 app.cached = false; 15032 } 15033 if (procState > ActivityManager.PROCESS_STATE_BACKUP) { 15034 procState = ActivityManager.PROCESS_STATE_BACKUP; 15035 } 15036 } 15037 15038 boolean mayBeTop = false; 15039 15040 for (int is = app.services.size()-1; 15041 is >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15042 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15043 || procState > ActivityManager.PROCESS_STATE_TOP); 15044 is--) { 15045 ServiceRecord s = app.services.valueAt(is); 15046 if (s.startRequested) { 15047 app.hasStartedServices = true; 15048 if (procState > ActivityManager.PROCESS_STATE_SERVICE) { 15049 procState = ActivityManager.PROCESS_STATE_SERVICE; 15050 } 15051 if (app.hasShownUi && app != mHomeProcess) { 15052 // If this process has shown some UI, let it immediately 15053 // go to the LRU list because it may be pretty heavy with 15054 // UI stuff. We'll tag it with a label just to help 15055 // debug and understand what is going on. 15056 if (adj > ProcessList.SERVICE_ADJ) { 15057 app.adjType = "cch-started-ui-services"; 15058 } 15059 } else { 15060 if (now < (s.lastActivity + ActiveServices.MAX_SERVICE_INACTIVITY)) { 15061 // This service has seen some activity within 15062 // recent memory, so we will keep its process ahead 15063 // of the background processes. 15064 if (adj > ProcessList.SERVICE_ADJ) { 15065 adj = ProcessList.SERVICE_ADJ; 15066 app.adjType = "started-services"; 15067 app.cached = false; 15068 } 15069 } 15070 // If we have let the service slide into the background 15071 // state, still have some text describing what it is doing 15072 // even though the service no longer has an impact. 15073 if (adj > ProcessList.SERVICE_ADJ) { 15074 app.adjType = "cch-started-services"; 15075 } 15076 } 15077 // Don't kill this process because it is doing work; it 15078 // has said it is doing work. 15079 app.keeping = true; 15080 } 15081 for (int conni = s.connections.size()-1; 15082 conni >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15083 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15084 || procState > ActivityManager.PROCESS_STATE_TOP); 15085 conni--) { 15086 ArrayList<ConnectionRecord> clist = s.connections.valueAt(conni); 15087 for (int i = 0; 15088 i < clist.size() && (adj > ProcessList.FOREGROUND_APP_ADJ 15089 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15090 || procState > ActivityManager.PROCESS_STATE_TOP); 15091 i++) { 15092 // XXX should compute this based on the max of 15093 // all connected clients. 15094 ConnectionRecord cr = clist.get(i); 15095 if (cr.binding.client == app) { 15096 // Binding to ourself is not interesting. 15097 continue; 15098 } 15099 if ((cr.flags&Context.BIND_WAIVE_PRIORITY) == 0) { 15100 ProcessRecord client = cr.binding.client; 15101 int clientAdj = computeOomAdjLocked(client, cachedAdj, 15102 TOP_APP, doingAll, now); 15103 int clientProcState = client.curProcState; 15104 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15105 // If the other app is cached for any reason, for purposes here 15106 // we are going to consider it empty. The specific cached state 15107 // doesn't propagate except under certain conditions. 15108 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15109 } 15110 String adjType = null; 15111 if ((cr.flags&Context.BIND_ALLOW_OOM_MANAGEMENT) != 0) { 15112 // Not doing bind OOM management, so treat 15113 // this guy more like a started service. 15114 if (app.hasShownUi && app != mHomeProcess) { 15115 // If this process has shown some UI, let it immediately 15116 // go to the LRU list because it may be pretty heavy with 15117 // UI stuff. We'll tag it with a label just to help 15118 // debug and understand what is going on. 15119 if (adj > clientAdj) { 15120 adjType = "cch-bound-ui-services"; 15121 } 15122 app.cached = false; 15123 clientAdj = adj; 15124 clientProcState = procState; 15125 } else { 15126 if (now >= (s.lastActivity 15127 + ActiveServices.MAX_SERVICE_INACTIVITY)) { 15128 // This service has not seen activity within 15129 // recent memory, so allow it to drop to the 15130 // LRU list if there is no other reason to keep 15131 // it around. We'll also tag it with a label just 15132 // to help debug and undertand what is going on. 15133 if (adj > clientAdj) { 15134 adjType = "cch-bound-services"; 15135 } 15136 clientAdj = adj; 15137 } 15138 } 15139 } 15140 if (adj > clientAdj) { 15141 // If this process has recently shown UI, and 15142 // the process that is binding to it is less 15143 // important than being visible, then we don't 15144 // care about the binding as much as we care 15145 // about letting this process get into the LRU 15146 // list to be killed and restarted if needed for 15147 // memory. 15148 if (app.hasShownUi && app != mHomeProcess 15149 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15150 adjType = "cch-bound-ui-services"; 15151 } else { 15152 if ((cr.flags&(Context.BIND_ABOVE_CLIENT 15153 |Context.BIND_IMPORTANT)) != 0) { 15154 adj = clientAdj; 15155 } else if ((cr.flags&Context.BIND_NOT_VISIBLE) != 0 15156 && clientAdj < ProcessList.PERCEPTIBLE_APP_ADJ 15157 && adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15158 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15159 } else if (clientAdj > ProcessList.VISIBLE_APP_ADJ) { 15160 adj = clientAdj; 15161 } else { 15162 if (adj > ProcessList.VISIBLE_APP_ADJ) { 15163 adj = ProcessList.VISIBLE_APP_ADJ; 15164 } 15165 } 15166 if (!client.cached) { 15167 app.cached = false; 15168 } 15169 if (client.keeping) { 15170 app.keeping = true; 15171 } 15172 adjType = "service"; 15173 } 15174 } 15175 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 15176 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 15177 schedGroup = Process.THREAD_GROUP_DEFAULT; 15178 } 15179 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 15180 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 15181 // Special handling of clients who are in the top state. 15182 // We *may* want to consider this process to be in the 15183 // top state as well, but only if there is not another 15184 // reason for it to be running. Being on the top is a 15185 // special state, meaning you are specifically running 15186 // for the current top app. If the process is already 15187 // running in the background for some other reason, it 15188 // is more important to continue considering it to be 15189 // in the background state. 15190 mayBeTop = true; 15191 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15192 } else { 15193 // Special handling for above-top states (persistent 15194 // processes). These should not bring the current process 15195 // into the top state, since they are not on top. Instead 15196 // give them the best state after that. 15197 clientProcState = 15198 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15199 } 15200 } 15201 } else { 15202 if (clientProcState < 15203 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 15204 clientProcState = 15205 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 15206 } 15207 } 15208 if (procState > clientProcState) { 15209 procState = clientProcState; 15210 } 15211 if (procState < ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 15212 && (cr.flags&Context.BIND_SHOWING_UI) != 0) { 15213 app.pendingUiClean = true; 15214 } 15215 if (adjType != null) { 15216 app.adjType = adjType; 15217 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15218 .REASON_SERVICE_IN_USE; 15219 app.adjSource = cr.binding.client; 15220 app.adjSourceOom = clientAdj; 15221 app.adjTarget = s.name; 15222 } 15223 } 15224 if ((cr.flags&Context.BIND_TREAT_LIKE_ACTIVITY) != 0) { 15225 app.treatLikeActivity = true; 15226 } 15227 final ActivityRecord a = cr.activity; 15228 if ((cr.flags&Context.BIND_ADJUST_WITH_ACTIVITY) != 0) { 15229 if (a != null && adj > ProcessList.FOREGROUND_APP_ADJ && 15230 (a.visible || a.state == ActivityState.RESUMED 15231 || a.state == ActivityState.PAUSING)) { 15232 adj = ProcessList.FOREGROUND_APP_ADJ; 15233 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 15234 schedGroup = Process.THREAD_GROUP_DEFAULT; 15235 } 15236 app.cached = false; 15237 app.adjType = "service"; 15238 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15239 .REASON_SERVICE_IN_USE; 15240 app.adjSource = a; 15241 app.adjSourceOom = adj; 15242 app.adjTarget = s.name; 15243 } 15244 } 15245 } 15246 } 15247 } 15248 15249 for (int provi = app.pubProviders.size()-1; 15250 provi >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15251 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15252 || procState > ActivityManager.PROCESS_STATE_TOP); 15253 provi--) { 15254 ContentProviderRecord cpr = app.pubProviders.valueAt(provi); 15255 for (int i = cpr.connections.size()-1; 15256 i >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15257 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15258 || procState > ActivityManager.PROCESS_STATE_TOP); 15259 i--) { 15260 ContentProviderConnection conn = cpr.connections.get(i); 15261 ProcessRecord client = conn.client; 15262 if (client == app) { 15263 // Being our own client is not interesting. 15264 continue; 15265 } 15266 int clientAdj = computeOomAdjLocked(client, cachedAdj, TOP_APP, doingAll, now); 15267 int clientProcState = client.curProcState; 15268 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15269 // If the other app is cached for any reason, for purposes here 15270 // we are going to consider it empty. 15271 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15272 } 15273 if (adj > clientAdj) { 15274 if (app.hasShownUi && app != mHomeProcess 15275 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15276 app.adjType = "cch-ui-provider"; 15277 } else { 15278 adj = clientAdj > ProcessList.FOREGROUND_APP_ADJ 15279 ? clientAdj : ProcessList.FOREGROUND_APP_ADJ; 15280 app.adjType = "provider"; 15281 } 15282 app.cached &= client.cached; 15283 app.keeping |= client.keeping; 15284 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15285 .REASON_PROVIDER_IN_USE; 15286 app.adjSource = client; 15287 app.adjSourceOom = clientAdj; 15288 app.adjTarget = cpr.name; 15289 } 15290 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 15291 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 15292 // Special handling of clients who are in the top state. 15293 // We *may* want to consider this process to be in the 15294 // top state as well, but only if there is not another 15295 // reason for it to be running. Being on the top is a 15296 // special state, meaning you are specifically running 15297 // for the current top app. If the process is already 15298 // running in the background for some other reason, it 15299 // is more important to continue considering it to be 15300 // in the background state. 15301 mayBeTop = true; 15302 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15303 } else { 15304 // Special handling for above-top states (persistent 15305 // processes). These should not bring the current process 15306 // into the top state, since they are not on top. Instead 15307 // give them the best state after that. 15308 clientProcState = 15309 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15310 } 15311 } 15312 if (procState > clientProcState) { 15313 procState = clientProcState; 15314 } 15315 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 15316 schedGroup = Process.THREAD_GROUP_DEFAULT; 15317 } 15318 } 15319 // If the provider has external (non-framework) process 15320 // dependencies, ensure that its adjustment is at least 15321 // FOREGROUND_APP_ADJ. 15322 if (cpr.hasExternalProcessHandles()) { 15323 if (adj > ProcessList.FOREGROUND_APP_ADJ) { 15324 adj = ProcessList.FOREGROUND_APP_ADJ; 15325 schedGroup = Process.THREAD_GROUP_DEFAULT; 15326 app.cached = false; 15327 app.keeping = true; 15328 app.adjType = "provider"; 15329 app.adjTarget = cpr.name; 15330 } 15331 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) { 15332 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15333 } 15334 } 15335 } 15336 15337 if (mayBeTop && procState > ActivityManager.PROCESS_STATE_TOP) { 15338 // A client of one of our services or providers is in the top state. We 15339 // *may* want to be in the top state, but not if we are already running in 15340 // the background for some other reason. For the decision here, we are going 15341 // to pick out a few specific states that we want to remain in when a client 15342 // is top (states that tend to be longer-term) and otherwise allow it to go 15343 // to the top state. 15344 switch (procState) { 15345 case ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND: 15346 case ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND: 15347 case ActivityManager.PROCESS_STATE_SERVICE: 15348 // These all are longer-term states, so pull them up to the top 15349 // of the background states, but not all the way to the top state. 15350 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15351 break; 15352 default: 15353 // Otherwise, top is a better choice, so take it. 15354 procState = ActivityManager.PROCESS_STATE_TOP; 15355 break; 15356 } 15357 } 15358 15359 if (procState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 15360 if (app.hasClientActivities) { 15361 // This is a cached process, but with client activities. Mark it so. 15362 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT; 15363 app.adjType = "cch-client-act"; 15364 } else if (app.treatLikeActivity) { 15365 // This is a cached process, but somebody wants us to treat it like it has 15366 // an activity, okay! 15367 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 15368 app.adjType = "cch-as-act"; 15369 } 15370 } 15371 15372 if (adj == ProcessList.SERVICE_ADJ) { 15373 if (doingAll) { 15374 app.serviceb = mNewNumAServiceProcs > (mNumServiceProcs/3); 15375 mNewNumServiceProcs++; 15376 //Slog.i(TAG, "ADJ " + app + " serviceb=" + app.serviceb); 15377 if (!app.serviceb) { 15378 // This service isn't far enough down on the LRU list to 15379 // normally be a B service, but if we are low on RAM and it 15380 // is large we want to force it down since we would prefer to 15381 // keep launcher over it. 15382 if (mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 15383 && app.lastPss >= mProcessList.getCachedRestoreThresholdKb()) { 15384 app.serviceHighRam = true; 15385 app.serviceb = true; 15386 //Slog.i(TAG, "ADJ " + app + " high ram!"); 15387 } else { 15388 mNewNumAServiceProcs++; 15389 //Slog.i(TAG, "ADJ " + app + " not high ram!"); 15390 } 15391 } else { 15392 app.serviceHighRam = false; 15393 } 15394 } 15395 if (app.serviceb) { 15396 adj = ProcessList.SERVICE_B_ADJ; 15397 } 15398 } 15399 15400 app.curRawAdj = adj; 15401 15402 //Slog.i(TAG, "OOM ADJ " + app + ": pid=" + app.pid + 15403 // " adj=" + adj + " curAdj=" + app.curAdj + " maxAdj=" + app.maxAdj); 15404 if (adj > app.maxAdj) { 15405 adj = app.maxAdj; 15406 if (app.maxAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 15407 schedGroup = Process.THREAD_GROUP_DEFAULT; 15408 } 15409 } 15410 if (adj < ProcessList.CACHED_APP_MIN_ADJ) { 15411 app.keeping = true; 15412 } 15413 15414 // Do final modification to adj. Everything we do between here and applying 15415 // the final setAdj must be done in this function, because we will also use 15416 // it when computing the final cached adj later. Note that we don't need to 15417 // worry about this for max adj above, since max adj will always be used to 15418 // keep it out of the cached vaues. 15419 app.curAdj = app.modifyRawOomAdj(adj); 15420 app.curSchedGroup = schedGroup; 15421 app.curProcState = procState; 15422 app.foregroundActivities = foregroundActivities; 15423 15424 return app.curRawAdj; 15425 } 15426 15427 /** 15428 * Schedule PSS collection of a process. 15429 */ 15430 void requestPssLocked(ProcessRecord proc, int procState) { 15431 if (mPendingPssProcesses.contains(proc)) { 15432 return; 15433 } 15434 if (mPendingPssProcesses.size() == 0) { 15435 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 15436 } 15437 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of: " + proc); 15438 proc.pssProcState = procState; 15439 mPendingPssProcesses.add(proc); 15440 } 15441 15442 /** 15443 * Schedule PSS collection of all processes. 15444 */ 15445 void requestPssAllProcsLocked(long now, boolean always, boolean memLowered) { 15446 if (!always) { 15447 if (now < (mLastFullPssTime + 15448 (memLowered ? FULL_PSS_LOWERED_INTERVAL : FULL_PSS_MIN_INTERVAL))) { 15449 return; 15450 } 15451 } 15452 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of all procs! memLowered=" + memLowered); 15453 mLastFullPssTime = now; 15454 mPendingPssProcesses.ensureCapacity(mLruProcesses.size()); 15455 mPendingPssProcesses.clear(); 15456 for (int i=mLruProcesses.size()-1; i>=0; i--) { 15457 ProcessRecord app = mLruProcesses.get(i); 15458 if (memLowered || now > (app.lastStateTime+ProcessList.PSS_ALL_INTERVAL)) { 15459 app.pssProcState = app.setProcState; 15460 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 15461 isSleeping(), now); 15462 mPendingPssProcesses.add(app); 15463 } 15464 } 15465 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 15466 } 15467 15468 /** 15469 * Ask a given process to GC right now. 15470 */ 15471 final void performAppGcLocked(ProcessRecord app) { 15472 try { 15473 app.lastRequestedGc = SystemClock.uptimeMillis(); 15474 if (app.thread != null) { 15475 if (app.reportLowMemory) { 15476 app.reportLowMemory = false; 15477 app.thread.scheduleLowMemory(); 15478 } else { 15479 app.thread.processInBackground(); 15480 } 15481 } 15482 } catch (Exception e) { 15483 // whatever. 15484 } 15485 } 15486 15487 /** 15488 * Returns true if things are idle enough to perform GCs. 15489 */ 15490 private final boolean canGcNowLocked() { 15491 boolean processingBroadcasts = false; 15492 for (BroadcastQueue q : mBroadcastQueues) { 15493 if (q.mParallelBroadcasts.size() != 0 || q.mOrderedBroadcasts.size() != 0) { 15494 processingBroadcasts = true; 15495 } 15496 } 15497 return !processingBroadcasts 15498 && (isSleeping() || mStackSupervisor.allResumedActivitiesIdle()); 15499 } 15500 15501 /** 15502 * Perform GCs on all processes that are waiting for it, but only 15503 * if things are idle. 15504 */ 15505 final void performAppGcsLocked() { 15506 final int N = mProcessesToGc.size(); 15507 if (N <= 0) { 15508 return; 15509 } 15510 if (canGcNowLocked()) { 15511 while (mProcessesToGc.size() > 0) { 15512 ProcessRecord proc = mProcessesToGc.remove(0); 15513 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ || proc.reportLowMemory) { 15514 if ((proc.lastRequestedGc+GC_MIN_INTERVAL) 15515 <= SystemClock.uptimeMillis()) { 15516 // To avoid spamming the system, we will GC processes one 15517 // at a time, waiting a few seconds between each. 15518 performAppGcLocked(proc); 15519 scheduleAppGcsLocked(); 15520 return; 15521 } else { 15522 // It hasn't been long enough since we last GCed this 15523 // process... put it in the list to wait for its time. 15524 addProcessToGcListLocked(proc); 15525 break; 15526 } 15527 } 15528 } 15529 15530 scheduleAppGcsLocked(); 15531 } 15532 } 15533 15534 /** 15535 * If all looks good, perform GCs on all processes waiting for them. 15536 */ 15537 final void performAppGcsIfAppropriateLocked() { 15538 if (canGcNowLocked()) { 15539 performAppGcsLocked(); 15540 return; 15541 } 15542 // Still not idle, wait some more. 15543 scheduleAppGcsLocked(); 15544 } 15545 15546 /** 15547 * Schedule the execution of all pending app GCs. 15548 */ 15549 final void scheduleAppGcsLocked() { 15550 mHandler.removeMessages(GC_BACKGROUND_PROCESSES_MSG); 15551 15552 if (mProcessesToGc.size() > 0) { 15553 // Schedule a GC for the time to the next process. 15554 ProcessRecord proc = mProcessesToGc.get(0); 15555 Message msg = mHandler.obtainMessage(GC_BACKGROUND_PROCESSES_MSG); 15556 15557 long when = proc.lastRequestedGc + GC_MIN_INTERVAL; 15558 long now = SystemClock.uptimeMillis(); 15559 if (when < (now+GC_TIMEOUT)) { 15560 when = now + GC_TIMEOUT; 15561 } 15562 mHandler.sendMessageAtTime(msg, when); 15563 } 15564 } 15565 15566 /** 15567 * Add a process to the array of processes waiting to be GCed. Keeps the 15568 * list in sorted order by the last GC time. The process can't already be 15569 * on the list. 15570 */ 15571 final void addProcessToGcListLocked(ProcessRecord proc) { 15572 boolean added = false; 15573 for (int i=mProcessesToGc.size()-1; i>=0; i--) { 15574 if (mProcessesToGc.get(i).lastRequestedGc < 15575 proc.lastRequestedGc) { 15576 added = true; 15577 mProcessesToGc.add(i+1, proc); 15578 break; 15579 } 15580 } 15581 if (!added) { 15582 mProcessesToGc.add(0, proc); 15583 } 15584 } 15585 15586 /** 15587 * Set up to ask a process to GC itself. This will either do it 15588 * immediately, or put it on the list of processes to gc the next 15589 * time things are idle. 15590 */ 15591 final void scheduleAppGcLocked(ProcessRecord app) { 15592 long now = SystemClock.uptimeMillis(); 15593 if ((app.lastRequestedGc+GC_MIN_INTERVAL) > now) { 15594 return; 15595 } 15596 if (!mProcessesToGc.contains(app)) { 15597 addProcessToGcListLocked(app); 15598 scheduleAppGcsLocked(); 15599 } 15600 } 15601 15602 final void checkExcessivePowerUsageLocked(boolean doKills) { 15603 updateCpuStatsNow(); 15604 15605 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 15606 boolean doWakeKills = doKills; 15607 boolean doCpuKills = doKills; 15608 if (mLastPowerCheckRealtime == 0) { 15609 doWakeKills = false; 15610 } 15611 if (mLastPowerCheckUptime == 0) { 15612 doCpuKills = false; 15613 } 15614 if (stats.isScreenOn()) { 15615 doWakeKills = false; 15616 } 15617 final long curRealtime = SystemClock.elapsedRealtime(); 15618 final long realtimeSince = curRealtime - mLastPowerCheckRealtime; 15619 final long curUptime = SystemClock.uptimeMillis(); 15620 final long uptimeSince = curUptime - mLastPowerCheckUptime; 15621 mLastPowerCheckRealtime = curRealtime; 15622 mLastPowerCheckUptime = curUptime; 15623 if (realtimeSince < WAKE_LOCK_MIN_CHECK_DURATION) { 15624 doWakeKills = false; 15625 } 15626 if (uptimeSince < CPU_MIN_CHECK_DURATION) { 15627 doCpuKills = false; 15628 } 15629 int i = mLruProcesses.size(); 15630 while (i > 0) { 15631 i--; 15632 ProcessRecord app = mLruProcesses.get(i); 15633 if (!app.keeping) { 15634 long wtime; 15635 synchronized (stats) { 15636 wtime = stats.getProcessWakeTime(app.info.uid, 15637 app.pid, curRealtime); 15638 } 15639 long wtimeUsed = wtime - app.lastWakeTime; 15640 long cputimeUsed = app.curCpuTime - app.lastCpuTime; 15641 if (DEBUG_POWER) { 15642 StringBuilder sb = new StringBuilder(128); 15643 sb.append("Wake for "); 15644 app.toShortString(sb); 15645 sb.append(": over "); 15646 TimeUtils.formatDuration(realtimeSince, sb); 15647 sb.append(" used "); 15648 TimeUtils.formatDuration(wtimeUsed, sb); 15649 sb.append(" ("); 15650 sb.append((wtimeUsed*100)/realtimeSince); 15651 sb.append("%)"); 15652 Slog.i(TAG, sb.toString()); 15653 sb.setLength(0); 15654 sb.append("CPU for "); 15655 app.toShortString(sb); 15656 sb.append(": over "); 15657 TimeUtils.formatDuration(uptimeSince, sb); 15658 sb.append(" used "); 15659 TimeUtils.formatDuration(cputimeUsed, sb); 15660 sb.append(" ("); 15661 sb.append((cputimeUsed*100)/uptimeSince); 15662 sb.append("%)"); 15663 Slog.i(TAG, sb.toString()); 15664 } 15665 // If a process has held a wake lock for more 15666 // than 50% of the time during this period, 15667 // that sounds bad. Kill! 15668 if (doWakeKills && realtimeSince > 0 15669 && ((wtimeUsed*100)/realtimeSince) >= 50) { 15670 synchronized (stats) { 15671 stats.reportExcessiveWakeLocked(app.info.uid, app.processName, 15672 realtimeSince, wtimeUsed); 15673 } 15674 killUnneededProcessLocked(app, "excessive wake held " + wtimeUsed 15675 + " during " + realtimeSince); 15676 app.baseProcessTracker.reportExcessiveWake(app.pkgList); 15677 } else if (doCpuKills && uptimeSince > 0 15678 && ((cputimeUsed*100)/uptimeSince) >= 50) { 15679 synchronized (stats) { 15680 stats.reportExcessiveCpuLocked(app.info.uid, app.processName, 15681 uptimeSince, cputimeUsed); 15682 } 15683 killUnneededProcessLocked(app, "excessive cpu " + cputimeUsed 15684 + " during " + uptimeSince); 15685 app.baseProcessTracker.reportExcessiveCpu(app.pkgList); 15686 } else { 15687 app.lastWakeTime = wtime; 15688 app.lastCpuTime = app.curCpuTime; 15689 } 15690 } 15691 } 15692 } 15693 15694 private final boolean applyOomAdjLocked(ProcessRecord app, boolean wasKeeping, 15695 ProcessRecord TOP_APP, boolean doingAll, long now) { 15696 boolean success = true; 15697 15698 if (app.curRawAdj != app.setRawAdj) { 15699 if (wasKeeping && !app.keeping) { 15700 // This app is no longer something we want to keep. Note 15701 // its current wake lock time to later know to kill it if 15702 // it is not behaving well. 15703 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 15704 synchronized (stats) { 15705 app.lastWakeTime = stats.getProcessWakeTime(app.info.uid, 15706 app.pid, SystemClock.elapsedRealtime()); 15707 } 15708 app.lastCpuTime = app.curCpuTime; 15709 } 15710 15711 app.setRawAdj = app.curRawAdj; 15712 } 15713 15714 int changes = 0; 15715 15716 if (app.curAdj != app.setAdj) { 15717 ProcessList.setOomAdj(app.pid, app.curAdj); 15718 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v( 15719 TAG, "Set " + app.pid + " " + app.processName + 15720 " adj " + app.curAdj + ": " + app.adjType); 15721 app.setAdj = app.curAdj; 15722 } 15723 15724 if (app.setSchedGroup != app.curSchedGroup) { 15725 app.setSchedGroup = app.curSchedGroup; 15726 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 15727 "Setting process group of " + app.processName 15728 + " to " + app.curSchedGroup); 15729 if (app.waitingToKill != null && 15730 app.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 15731 killUnneededProcessLocked(app, app.waitingToKill); 15732 success = false; 15733 } else { 15734 if (true) { 15735 long oldId = Binder.clearCallingIdentity(); 15736 try { 15737 Process.setProcessGroup(app.pid, app.curSchedGroup); 15738 } catch (Exception e) { 15739 Slog.w(TAG, "Failed setting process group of " + app.pid 15740 + " to " + app.curSchedGroup); 15741 e.printStackTrace(); 15742 } finally { 15743 Binder.restoreCallingIdentity(oldId); 15744 } 15745 } else { 15746 if (app.thread != null) { 15747 try { 15748 app.thread.setSchedulingGroup(app.curSchedGroup); 15749 } catch (RemoteException e) { 15750 } 15751 } 15752 } 15753 Process.setSwappiness(app.pid, 15754 app.curSchedGroup <= Process.THREAD_GROUP_BG_NONINTERACTIVE); 15755 } 15756 } 15757 if (app.repForegroundActivities != app.foregroundActivities) { 15758 app.repForegroundActivities = app.foregroundActivities; 15759 changes |= ProcessChangeItem.CHANGE_ACTIVITIES; 15760 } 15761 if (app.repProcState != app.curProcState) { 15762 app.repProcState = app.curProcState; 15763 changes |= ProcessChangeItem.CHANGE_PROCESS_STATE; 15764 if (app.thread != null) { 15765 try { 15766 if (false) { 15767 //RuntimeException h = new RuntimeException("here"); 15768 Slog.i(TAG, "Sending new process state " + app.repProcState 15769 + " to " + app /*, h*/); 15770 } 15771 app.thread.setProcessState(app.repProcState); 15772 } catch (RemoteException e) { 15773 } 15774 } 15775 } 15776 if (app.setProcState < 0 || ProcessList.procStatesDifferForMem(app.curProcState, 15777 app.setProcState)) { 15778 app.lastStateTime = now; 15779 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 15780 isSleeping(), now); 15781 if (DEBUG_PSS) Slog.d(TAG, "Process state change from " 15782 + ProcessList.makeProcStateString(app.setProcState) + " to " 15783 + ProcessList.makeProcStateString(app.curProcState) + " next pss in " 15784 + (app.nextPssTime-now) + ": " + app); 15785 } else { 15786 if (now > app.nextPssTime || (now > (app.lastPssTime+ProcessList.PSS_MAX_INTERVAL) 15787 && now > (app.lastStateTime+ProcessList.PSS_MIN_TIME_FROM_STATE_CHANGE))) { 15788 requestPssLocked(app, app.setProcState); 15789 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, false, 15790 isSleeping(), now); 15791 } else if (false && DEBUG_PSS) { 15792 Slog.d(TAG, "Not requesting PSS of " + app + ": next=" + (app.nextPssTime-now)); 15793 } 15794 } 15795 if (app.setProcState != app.curProcState) { 15796 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 15797 "Proc state change of " + app.processName 15798 + " to " + app.curProcState); 15799 app.setProcState = app.curProcState; 15800 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 15801 app.notCachedSinceIdle = false; 15802 } 15803 if (!doingAll) { 15804 setProcessTrackerState(app, mProcessStats.getMemFactorLocked(), now); 15805 } else { 15806 app.procStateChanged = true; 15807 } 15808 } 15809 15810 if (changes != 0) { 15811 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Changes in " + app + ": " + changes); 15812 int i = mPendingProcessChanges.size()-1; 15813 ProcessChangeItem item = null; 15814 while (i >= 0) { 15815 item = mPendingProcessChanges.get(i); 15816 if (item.pid == app.pid) { 15817 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Re-using existing item: " + item); 15818 break; 15819 } 15820 i--; 15821 } 15822 if (i < 0) { 15823 // No existing item in pending changes; need a new one. 15824 final int NA = mAvailProcessChanges.size(); 15825 if (NA > 0) { 15826 item = mAvailProcessChanges.remove(NA-1); 15827 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Retreiving available item: " + item); 15828 } else { 15829 item = new ProcessChangeItem(); 15830 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Allocating new item: " + item); 15831 } 15832 item.changes = 0; 15833 item.pid = app.pid; 15834 item.uid = app.info.uid; 15835 if (mPendingProcessChanges.size() == 0) { 15836 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, 15837 "*** Enqueueing dispatch processes changed!"); 15838 mHandler.obtainMessage(DISPATCH_PROCESSES_CHANGED).sendToTarget(); 15839 } 15840 mPendingProcessChanges.add(item); 15841 } 15842 item.changes |= changes; 15843 item.processState = app.repProcState; 15844 item.foregroundActivities = app.repForegroundActivities; 15845 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Item " 15846 + Integer.toHexString(System.identityHashCode(item)) 15847 + " " + app.toShortString() + ": changes=" + item.changes 15848 + " procState=" + item.processState 15849 + " foreground=" + item.foregroundActivities 15850 + " type=" + app.adjType + " source=" + app.adjSource 15851 + " target=" + app.adjTarget); 15852 } 15853 15854 return success; 15855 } 15856 15857 private final void setProcessTrackerState(ProcessRecord proc, int memFactor, long now) { 15858 if (proc.thread != null && proc.baseProcessTracker != null) { 15859 proc.baseProcessTracker.setState(proc.repProcState, memFactor, now, proc.pkgList); 15860 } 15861 } 15862 15863 private final boolean updateOomAdjLocked(ProcessRecord app, int cachedAdj, 15864 ProcessRecord TOP_APP, boolean doingAll, long now) { 15865 if (app.thread == null) { 15866 return false; 15867 } 15868 15869 final boolean wasKeeping = app.keeping; 15870 15871 computeOomAdjLocked(app, cachedAdj, TOP_APP, doingAll, now); 15872 15873 return applyOomAdjLocked(app, wasKeeping, TOP_APP, doingAll, now); 15874 } 15875 15876 final void updateProcessForegroundLocked(ProcessRecord proc, boolean isForeground, 15877 boolean oomAdj) { 15878 if (isForeground != proc.foregroundServices) { 15879 proc.foregroundServices = isForeground; 15880 ArrayList<ProcessRecord> curProcs = mForegroundPackages.get(proc.info.packageName, 15881 proc.info.uid); 15882 if (isForeground) { 15883 if (curProcs == null) { 15884 curProcs = new ArrayList<ProcessRecord>(); 15885 mForegroundPackages.put(proc.info.packageName, proc.info.uid, curProcs); 15886 } 15887 if (!curProcs.contains(proc)) { 15888 curProcs.add(proc); 15889 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_FOREGROUND_START, 15890 proc.info.packageName, proc.info.uid); 15891 } 15892 } else { 15893 if (curProcs != null) { 15894 if (curProcs.remove(proc)) { 15895 mBatteryStatsService.noteEvent( 15896 BatteryStats.HistoryItem.EVENT_FOREGROUND_FINISH, 15897 proc.info.packageName, proc.info.uid); 15898 if (curProcs.size() <= 0) { 15899 mForegroundPackages.remove(proc.info.packageName, proc.info.uid); 15900 } 15901 } 15902 } 15903 } 15904 if (oomAdj) { 15905 updateOomAdjLocked(); 15906 } 15907 } 15908 } 15909 15910 private final ActivityRecord resumedAppLocked() { 15911 ActivityRecord act = mStackSupervisor.resumedAppLocked(); 15912 String pkg; 15913 int uid; 15914 if (act != null && !act.sleeping) { 15915 pkg = act.packageName; 15916 uid = act.info.applicationInfo.uid; 15917 } else { 15918 pkg = null; 15919 uid = -1; 15920 } 15921 // Has the UID or resumed package name changed? 15922 if (uid != mCurResumedUid || (pkg != mCurResumedPackage 15923 && (pkg == null || !pkg.equals(mCurResumedPackage)))) { 15924 if (mCurResumedPackage != null) { 15925 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_FINISH, 15926 mCurResumedPackage, mCurResumedUid); 15927 } 15928 mCurResumedPackage = pkg; 15929 mCurResumedUid = uid; 15930 if (mCurResumedPackage != null) { 15931 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_START, 15932 mCurResumedPackage, mCurResumedUid); 15933 } 15934 } 15935 return act; 15936 } 15937 15938 final boolean updateOomAdjLocked(ProcessRecord app) { 15939 final ActivityRecord TOP_ACT = resumedAppLocked(); 15940 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 15941 final boolean wasCached = app.cached; 15942 15943 mAdjSeq++; 15944 15945 // This is the desired cached adjusment we want to tell it to use. 15946 // If our app is currently cached, we know it, and that is it. Otherwise, 15947 // we don't know it yet, and it needs to now be cached we will then 15948 // need to do a complete oom adj. 15949 final int cachedAdj = app.curRawAdj >= ProcessList.CACHED_APP_MIN_ADJ 15950 ? app.curRawAdj : ProcessList.UNKNOWN_ADJ; 15951 boolean success = updateOomAdjLocked(app, cachedAdj, TOP_APP, false, 15952 SystemClock.uptimeMillis()); 15953 if (wasCached != app.cached || app.curRawAdj == ProcessList.UNKNOWN_ADJ) { 15954 // Changed to/from cached state, so apps after it in the LRU 15955 // list may also be changed. 15956 updateOomAdjLocked(); 15957 } 15958 return success; 15959 } 15960 15961 final void updateOomAdjLocked() { 15962 final ActivityRecord TOP_ACT = resumedAppLocked(); 15963 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 15964 final long now = SystemClock.uptimeMillis(); 15965 final long oldTime = now - ProcessList.MAX_EMPTY_TIME; 15966 final int N = mLruProcesses.size(); 15967 15968 if (false) { 15969 RuntimeException e = new RuntimeException(); 15970 e.fillInStackTrace(); 15971 Slog.i(TAG, "updateOomAdj: top=" + TOP_ACT, e); 15972 } 15973 15974 mAdjSeq++; 15975 mNewNumServiceProcs = 0; 15976 mNewNumAServiceProcs = 0; 15977 15978 final int emptyProcessLimit; 15979 final int cachedProcessLimit; 15980 if (mProcessLimit <= 0) { 15981 emptyProcessLimit = cachedProcessLimit = 0; 15982 } else if (mProcessLimit == 1) { 15983 emptyProcessLimit = 1; 15984 cachedProcessLimit = 0; 15985 } else { 15986 emptyProcessLimit = ProcessList.computeEmptyProcessLimit(mProcessLimit); 15987 cachedProcessLimit = mProcessLimit - emptyProcessLimit; 15988 } 15989 15990 // Let's determine how many processes we have running vs. 15991 // how many slots we have for background processes; we may want 15992 // to put multiple processes in a slot of there are enough of 15993 // them. 15994 int numSlots = (ProcessList.CACHED_APP_MAX_ADJ 15995 - ProcessList.CACHED_APP_MIN_ADJ + 1) / 2; 15996 int numEmptyProcs = N - mNumNonCachedProcs - mNumCachedHiddenProcs; 15997 if (numEmptyProcs > cachedProcessLimit) { 15998 // If there are more empty processes than our limit on cached 15999 // processes, then use the cached process limit for the factor. 16000 // This ensures that the really old empty processes get pushed 16001 // down to the bottom, so if we are running low on memory we will 16002 // have a better chance at keeping around more cached processes 16003 // instead of a gazillion empty processes. 16004 numEmptyProcs = cachedProcessLimit; 16005 } 16006 int emptyFactor = numEmptyProcs/numSlots; 16007 if (emptyFactor < 1) emptyFactor = 1; 16008 int cachedFactor = (mNumCachedHiddenProcs > 0 ? mNumCachedHiddenProcs : 1)/numSlots; 16009 if (cachedFactor < 1) cachedFactor = 1; 16010 int stepCached = 0; 16011 int stepEmpty = 0; 16012 int numCached = 0; 16013 int numEmpty = 0; 16014 int numTrimming = 0; 16015 16016 mNumNonCachedProcs = 0; 16017 mNumCachedHiddenProcs = 0; 16018 16019 // First update the OOM adjustment for each of the 16020 // application processes based on their current state. 16021 int curCachedAdj = ProcessList.CACHED_APP_MIN_ADJ; 16022 int nextCachedAdj = curCachedAdj+1; 16023 int curEmptyAdj = ProcessList.CACHED_APP_MIN_ADJ; 16024 int nextEmptyAdj = curEmptyAdj+2; 16025 for (int i=N-1; i>=0; i--) { 16026 ProcessRecord app = mLruProcesses.get(i); 16027 if (!app.killedByAm && app.thread != null) { 16028 app.procStateChanged = false; 16029 final boolean wasKeeping = app.keeping; 16030 computeOomAdjLocked(app, ProcessList.UNKNOWN_ADJ, TOP_APP, true, now); 16031 16032 // If we haven't yet assigned the final cached adj 16033 // to the process, do that now. 16034 if (app.curAdj >= ProcessList.UNKNOWN_ADJ) { 16035 switch (app.curProcState) { 16036 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 16037 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 16038 // This process is a cached process holding activities... 16039 // assign it the next cached value for that type, and then 16040 // step that cached level. 16041 app.curRawAdj = curCachedAdj; 16042 app.curAdj = app.modifyRawOomAdj(curCachedAdj); 16043 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning activity LRU #" + i 16044 + " adj: " + app.curAdj + " (curCachedAdj=" + curCachedAdj 16045 + ")"); 16046 if (curCachedAdj != nextCachedAdj) { 16047 stepCached++; 16048 if (stepCached >= cachedFactor) { 16049 stepCached = 0; 16050 curCachedAdj = nextCachedAdj; 16051 nextCachedAdj += 2; 16052 if (nextCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) { 16053 nextCachedAdj = ProcessList.CACHED_APP_MAX_ADJ; 16054 } 16055 } 16056 } 16057 break; 16058 default: 16059 // For everything else, assign next empty cached process 16060 // level and bump that up. Note that this means that 16061 // long-running services that have dropped down to the 16062 // cached level will be treated as empty (since their process 16063 // state is still as a service), which is what we want. 16064 app.curRawAdj = curEmptyAdj; 16065 app.curAdj = app.modifyRawOomAdj(curEmptyAdj); 16066 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning empty LRU #" + i 16067 + " adj: " + app.curAdj + " (curEmptyAdj=" + curEmptyAdj 16068 + ")"); 16069 if (curEmptyAdj != nextEmptyAdj) { 16070 stepEmpty++; 16071 if (stepEmpty >= emptyFactor) { 16072 stepEmpty = 0; 16073 curEmptyAdj = nextEmptyAdj; 16074 nextEmptyAdj += 2; 16075 if (nextEmptyAdj > ProcessList.CACHED_APP_MAX_ADJ) { 16076 nextEmptyAdj = ProcessList.CACHED_APP_MAX_ADJ; 16077 } 16078 } 16079 } 16080 break; 16081 } 16082 } 16083 16084 applyOomAdjLocked(app, wasKeeping, TOP_APP, true, now); 16085 16086 // Count the number of process types. 16087 switch (app.curProcState) { 16088 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 16089 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 16090 mNumCachedHiddenProcs++; 16091 numCached++; 16092 if (numCached > cachedProcessLimit) { 16093 killUnneededProcessLocked(app, "cached #" + numCached); 16094 } 16095 break; 16096 case ActivityManager.PROCESS_STATE_CACHED_EMPTY: 16097 if (numEmpty > ProcessList.TRIM_EMPTY_APPS 16098 && app.lastActivityTime < oldTime) { 16099 killUnneededProcessLocked(app, "empty for " 16100 + ((oldTime + ProcessList.MAX_EMPTY_TIME - app.lastActivityTime) 16101 / 1000) + "s"); 16102 } else { 16103 numEmpty++; 16104 if (numEmpty > emptyProcessLimit) { 16105 killUnneededProcessLocked(app, "empty #" + numEmpty); 16106 } 16107 } 16108 break; 16109 default: 16110 mNumNonCachedProcs++; 16111 break; 16112 } 16113 16114 if (app.isolated && app.services.size() <= 0) { 16115 // If this is an isolated process, and there are no 16116 // services running in it, then the process is no longer 16117 // needed. We agressively kill these because we can by 16118 // definition not re-use the same process again, and it is 16119 // good to avoid having whatever code was running in them 16120 // left sitting around after no longer needed. 16121 killUnneededProcessLocked(app, "isolated not needed"); 16122 } 16123 16124 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 16125 && !app.killedByAm) { 16126 numTrimming++; 16127 } 16128 } 16129 } 16130 16131 mNumServiceProcs = mNewNumServiceProcs; 16132 16133 // Now determine the memory trimming level of background processes. 16134 // Unfortunately we need to start at the back of the list to do this 16135 // properly. We only do this if the number of background apps we 16136 // are managing to keep around is less than half the maximum we desire; 16137 // if we are keeping a good number around, we'll let them use whatever 16138 // memory they want. 16139 final int numCachedAndEmpty = numCached + numEmpty; 16140 int memFactor; 16141 if (numCached <= ProcessList.TRIM_CACHED_APPS 16142 && numEmpty <= ProcessList.TRIM_EMPTY_APPS) { 16143 if (numCachedAndEmpty <= ProcessList.TRIM_CRITICAL_THRESHOLD) { 16144 memFactor = ProcessStats.ADJ_MEM_FACTOR_CRITICAL; 16145 } else if (numCachedAndEmpty <= ProcessList.TRIM_LOW_THRESHOLD) { 16146 memFactor = ProcessStats.ADJ_MEM_FACTOR_LOW; 16147 } else { 16148 memFactor = ProcessStats.ADJ_MEM_FACTOR_MODERATE; 16149 } 16150 } else { 16151 memFactor = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 16152 } 16153 // We always allow the memory level to go up (better). We only allow it to go 16154 // down if we are in a state where that is allowed, *and* the total number of processes 16155 // has gone down since last time. 16156 if (DEBUG_OOM_ADJ) Slog.d(TAG, "oom: memFactor=" + memFactor + " last=" + mLastMemoryLevel 16157 + " allowLow=" + mAllowLowerMemLevel + " numProcs=" + mLruProcesses.size() 16158 + " last=" + mLastNumProcesses); 16159 if (memFactor > mLastMemoryLevel) { 16160 if (!mAllowLowerMemLevel || mLruProcesses.size() >= mLastNumProcesses) { 16161 memFactor = mLastMemoryLevel; 16162 if (DEBUG_OOM_ADJ) Slog.d(TAG, "Keeping last mem factor!"); 16163 } 16164 } 16165 mLastMemoryLevel = memFactor; 16166 mLastNumProcesses = mLruProcesses.size(); 16167 boolean allChanged = mProcessStats.setMemFactorLocked(memFactor, !isSleeping(), now); 16168 final int trackerMemFactor = mProcessStats.getMemFactorLocked(); 16169 if (memFactor != ProcessStats.ADJ_MEM_FACTOR_NORMAL) { 16170 if (mLowRamStartTime == 0) { 16171 mLowRamStartTime = now; 16172 } 16173 int step = 0; 16174 int fgTrimLevel; 16175 switch (memFactor) { 16176 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 16177 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_CRITICAL; 16178 break; 16179 case ProcessStats.ADJ_MEM_FACTOR_LOW: 16180 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_LOW; 16181 break; 16182 default: 16183 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_MODERATE; 16184 break; 16185 } 16186 int factor = numTrimming/3; 16187 int minFactor = 2; 16188 if (mHomeProcess != null) minFactor++; 16189 if (mPreviousProcess != null) minFactor++; 16190 if (factor < minFactor) factor = minFactor; 16191 int curLevel = ComponentCallbacks2.TRIM_MEMORY_COMPLETE; 16192 for (int i=N-1; i>=0; i--) { 16193 ProcessRecord app = mLruProcesses.get(i); 16194 if (allChanged || app.procStateChanged) { 16195 setProcessTrackerState(app, trackerMemFactor, now); 16196 app.procStateChanged = false; 16197 } 16198 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 16199 && !app.killedByAm) { 16200 if (app.trimMemoryLevel < curLevel && app.thread != null) { 16201 try { 16202 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16203 "Trimming memory of " + app.processName 16204 + " to " + curLevel); 16205 app.thread.scheduleTrimMemory(curLevel); 16206 } catch (RemoteException e) { 16207 } 16208 if (false) { 16209 // For now we won't do this; our memory trimming seems 16210 // to be good enough at this point that destroying 16211 // activities causes more harm than good. 16212 if (curLevel >= ComponentCallbacks2.TRIM_MEMORY_COMPLETE 16213 && app != mHomeProcess && app != mPreviousProcess) { 16214 // Need to do this on its own message because the stack may not 16215 // be in a consistent state at this point. 16216 // For these apps we will also finish their activities 16217 // to help them free memory. 16218 mStackSupervisor.scheduleDestroyAllActivities(app, "trim"); 16219 } 16220 } 16221 } 16222 app.trimMemoryLevel = curLevel; 16223 step++; 16224 if (step >= factor) { 16225 step = 0; 16226 switch (curLevel) { 16227 case ComponentCallbacks2.TRIM_MEMORY_COMPLETE: 16228 curLevel = ComponentCallbacks2.TRIM_MEMORY_MODERATE; 16229 break; 16230 case ComponentCallbacks2.TRIM_MEMORY_MODERATE: 16231 curLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 16232 break; 16233 } 16234 } 16235 } else if (app.curProcState == ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 16236 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_BACKGROUND 16237 && app.thread != null) { 16238 try { 16239 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16240 "Trimming memory of heavy-weight " + app.processName 16241 + " to " + ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 16242 app.thread.scheduleTrimMemory( 16243 ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 16244 } catch (RemoteException e) { 16245 } 16246 } 16247 app.trimMemoryLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 16248 } else { 16249 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 16250 || app.systemNoUi) && app.pendingUiClean) { 16251 // If this application is now in the background and it 16252 // had done UI, then give it the special trim level to 16253 // have it free UI resources. 16254 final int level = ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN; 16255 if (app.trimMemoryLevel < level && app.thread != null) { 16256 try { 16257 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16258 "Trimming memory of bg-ui " + app.processName 16259 + " to " + level); 16260 app.thread.scheduleTrimMemory(level); 16261 } catch (RemoteException e) { 16262 } 16263 } 16264 app.pendingUiClean = false; 16265 } 16266 if (app.trimMemoryLevel < fgTrimLevel && app.thread != null) { 16267 try { 16268 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16269 "Trimming memory of fg " + app.processName 16270 + " to " + fgTrimLevel); 16271 app.thread.scheduleTrimMemory(fgTrimLevel); 16272 } catch (RemoteException e) { 16273 } 16274 } 16275 app.trimMemoryLevel = fgTrimLevel; 16276 } 16277 } 16278 } else { 16279 if (mLowRamStartTime != 0) { 16280 mLowRamTimeSinceLastIdle += now - mLowRamStartTime; 16281 mLowRamStartTime = 0; 16282 } 16283 for (int i=N-1; i>=0; i--) { 16284 ProcessRecord app = mLruProcesses.get(i); 16285 if (allChanged || app.procStateChanged) { 16286 setProcessTrackerState(app, trackerMemFactor, now); 16287 app.procStateChanged = false; 16288 } 16289 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 16290 || app.systemNoUi) && app.pendingUiClean) { 16291 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN 16292 && app.thread != null) { 16293 try { 16294 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16295 "Trimming memory of ui hidden " + app.processName 16296 + " to " + ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 16297 app.thread.scheduleTrimMemory( 16298 ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 16299 } catch (RemoteException e) { 16300 } 16301 } 16302 app.pendingUiClean = false; 16303 } 16304 app.trimMemoryLevel = 0; 16305 } 16306 } 16307 16308 if (mAlwaysFinishActivities) { 16309 // Need to do this on its own message because the stack may not 16310 // be in a consistent state at this point. 16311 mStackSupervisor.scheduleDestroyAllActivities(null, "always-finish"); 16312 } 16313 16314 if (allChanged) { 16315 requestPssAllProcsLocked(now, false, mProcessStats.isMemFactorLowered()); 16316 } 16317 16318 if (mProcessStats.shouldWriteNowLocked(now)) { 16319 mHandler.post(new Runnable() { 16320 @Override public void run() { 16321 synchronized (ActivityManagerService.this) { 16322 mProcessStats.writeStateAsyncLocked(); 16323 } 16324 } 16325 }); 16326 } 16327 16328 if (DEBUG_OOM_ADJ) { 16329 Slog.d(TAG, "Did OOM ADJ in " + (SystemClock.uptimeMillis()-now) + "ms"); 16330 } 16331 } 16332 16333 final void trimApplications() { 16334 synchronized (this) { 16335 int i; 16336 16337 // First remove any unused application processes whose package 16338 // has been removed. 16339 for (i=mRemovedProcesses.size()-1; i>=0; i--) { 16340 final ProcessRecord app = mRemovedProcesses.get(i); 16341 if (app.activities.size() == 0 16342 && app.curReceiver == null && app.services.size() == 0) { 16343 Slog.i( 16344 TAG, "Exiting empty application process " 16345 + app.processName + " (" 16346 + (app.thread != null ? app.thread.asBinder() : null) 16347 + ")\n"); 16348 if (app.pid > 0 && app.pid != MY_PID) { 16349 EventLog.writeEvent(EventLogTags.AM_KILL, app.userId, app.pid, 16350 app.processName, app.setAdj, "empty"); 16351 app.killedByAm = true; 16352 Process.killProcessQuiet(app.pid); 16353 } else { 16354 try { 16355 app.thread.scheduleExit(); 16356 } catch (Exception e) { 16357 // Ignore exceptions. 16358 } 16359 } 16360 cleanUpApplicationRecordLocked(app, false, true, -1); 16361 mRemovedProcesses.remove(i); 16362 16363 if (app.persistent) { 16364 if (app.persistent) { 16365 addAppLocked(app.info, false, null /* ABI override */); 16366 } 16367 } 16368 } 16369 } 16370 16371 // Now update the oom adj for all processes. 16372 updateOomAdjLocked(); 16373 } 16374 } 16375 16376 /** This method sends the specified signal to each of the persistent apps */ 16377 public void signalPersistentProcesses(int sig) throws RemoteException { 16378 if (sig != Process.SIGNAL_USR1) { 16379 throw new SecurityException("Only SIGNAL_USR1 is allowed"); 16380 } 16381 16382 synchronized (this) { 16383 if (checkCallingPermission(android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES) 16384 != PackageManager.PERMISSION_GRANTED) { 16385 throw new SecurityException("Requires permission " 16386 + android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES); 16387 } 16388 16389 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 16390 ProcessRecord r = mLruProcesses.get(i); 16391 if (r.thread != null && r.persistent) { 16392 Process.sendSignal(r.pid, sig); 16393 } 16394 } 16395 } 16396 } 16397 16398 private void stopProfilerLocked(ProcessRecord proc, String path, int profileType) { 16399 if (proc == null || proc == mProfileProc) { 16400 proc = mProfileProc; 16401 path = mProfileFile; 16402 profileType = mProfileType; 16403 clearProfilerLocked(); 16404 } 16405 if (proc == null) { 16406 return; 16407 } 16408 try { 16409 proc.thread.profilerControl(false, path, null, profileType); 16410 } catch (RemoteException e) { 16411 throw new IllegalStateException("Process disappeared"); 16412 } 16413 } 16414 16415 private void clearProfilerLocked() { 16416 if (mProfileFd != null) { 16417 try { 16418 mProfileFd.close(); 16419 } catch (IOException e) { 16420 } 16421 } 16422 mProfileApp = null; 16423 mProfileProc = null; 16424 mProfileFile = null; 16425 mProfileType = 0; 16426 mAutoStopProfiler = false; 16427 } 16428 16429 public boolean profileControl(String process, int userId, boolean start, 16430 String path, ParcelFileDescriptor fd, int profileType) throws RemoteException { 16431 16432 try { 16433 synchronized (this) { 16434 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 16435 // its own permission. 16436 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 16437 != PackageManager.PERMISSION_GRANTED) { 16438 throw new SecurityException("Requires permission " 16439 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 16440 } 16441 16442 if (start && fd == null) { 16443 throw new IllegalArgumentException("null fd"); 16444 } 16445 16446 ProcessRecord proc = null; 16447 if (process != null) { 16448 proc = findProcessLocked(process, userId, "profileControl"); 16449 } 16450 16451 if (start && (proc == null || proc.thread == null)) { 16452 throw new IllegalArgumentException("Unknown process: " + process); 16453 } 16454 16455 if (start) { 16456 stopProfilerLocked(null, null, 0); 16457 setProfileApp(proc.info, proc.processName, path, fd, false); 16458 mProfileProc = proc; 16459 mProfileType = profileType; 16460 try { 16461 fd = fd.dup(); 16462 } catch (IOException e) { 16463 fd = null; 16464 } 16465 proc.thread.profilerControl(start, path, fd, profileType); 16466 fd = null; 16467 mProfileFd = null; 16468 } else { 16469 stopProfilerLocked(proc, path, profileType); 16470 if (fd != null) { 16471 try { 16472 fd.close(); 16473 } catch (IOException e) { 16474 } 16475 } 16476 } 16477 16478 return true; 16479 } 16480 } catch (RemoteException e) { 16481 throw new IllegalStateException("Process disappeared"); 16482 } finally { 16483 if (fd != null) { 16484 try { 16485 fd.close(); 16486 } catch (IOException e) { 16487 } 16488 } 16489 } 16490 } 16491 16492 private ProcessRecord findProcessLocked(String process, int userId, String callName) { 16493 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 16494 userId, true, true, callName, null); 16495 ProcessRecord proc = null; 16496 try { 16497 int pid = Integer.parseInt(process); 16498 synchronized (mPidsSelfLocked) { 16499 proc = mPidsSelfLocked.get(pid); 16500 } 16501 } catch (NumberFormatException e) { 16502 } 16503 16504 if (proc == null) { 16505 ArrayMap<String, SparseArray<ProcessRecord>> all 16506 = mProcessNames.getMap(); 16507 SparseArray<ProcessRecord> procs = all.get(process); 16508 if (procs != null && procs.size() > 0) { 16509 proc = procs.valueAt(0); 16510 if (userId != UserHandle.USER_ALL && proc.userId != userId) { 16511 for (int i=1; i<procs.size(); i++) { 16512 ProcessRecord thisProc = procs.valueAt(i); 16513 if (thisProc.userId == userId) { 16514 proc = thisProc; 16515 break; 16516 } 16517 } 16518 } 16519 } 16520 } 16521 16522 return proc; 16523 } 16524 16525 public boolean dumpHeap(String process, int userId, boolean managed, 16526 String path, ParcelFileDescriptor fd) throws RemoteException { 16527 16528 try { 16529 synchronized (this) { 16530 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 16531 // its own permission (same as profileControl). 16532 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 16533 != PackageManager.PERMISSION_GRANTED) { 16534 throw new SecurityException("Requires permission " 16535 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 16536 } 16537 16538 if (fd == null) { 16539 throw new IllegalArgumentException("null fd"); 16540 } 16541 16542 ProcessRecord proc = findProcessLocked(process, userId, "dumpHeap"); 16543 if (proc == null || proc.thread == null) { 16544 throw new IllegalArgumentException("Unknown process: " + process); 16545 } 16546 16547 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 16548 if (!isDebuggable) { 16549 if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 16550 throw new SecurityException("Process not debuggable: " + proc); 16551 } 16552 } 16553 16554 proc.thread.dumpHeap(managed, path, fd); 16555 fd = null; 16556 return true; 16557 } 16558 } catch (RemoteException e) { 16559 throw new IllegalStateException("Process disappeared"); 16560 } finally { 16561 if (fd != null) { 16562 try { 16563 fd.close(); 16564 } catch (IOException e) { 16565 } 16566 } 16567 } 16568 } 16569 16570 /** In this method we try to acquire our lock to make sure that we have not deadlocked */ 16571 public void monitor() { 16572 synchronized (this) { } 16573 } 16574 16575 void onCoreSettingsChange(Bundle settings) { 16576 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 16577 ProcessRecord processRecord = mLruProcesses.get(i); 16578 try { 16579 if (processRecord.thread != null) { 16580 processRecord.thread.setCoreSettings(settings); 16581 } 16582 } catch (RemoteException re) { 16583 /* ignore */ 16584 } 16585 } 16586 } 16587 16588 // Multi-user methods 16589 16590 /** 16591 * Start user, if its not already running, but don't bring it to foreground. 16592 */ 16593 @Override 16594 public boolean startUserInBackground(final int userId) { 16595 return startUser(userId, /* foreground */ false); 16596 } 16597 16598 /** 16599 * Refreshes the list of users related to the current user when either a 16600 * user switch happens or when a new related user is started in the 16601 * background. 16602 */ 16603 private void updateCurrentProfileIdsLocked() { 16604 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 16605 mCurrentUserId, false /* enabledOnly */); 16606 int[] currentProfileIds = new int[profiles.size()]; // profiles will not be null 16607 for (int i = 0; i < currentProfileIds.length; i++) { 16608 currentProfileIds[i] = profiles.get(i).id; 16609 } 16610 mCurrentProfileIds = currentProfileIds; 16611 } 16612 16613 private Set getProfileIdsLocked(int userId) { 16614 Set userIds = new HashSet<Integer>(); 16615 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 16616 userId, false /* enabledOnly */); 16617 for (UserInfo user : profiles) { 16618 userIds.add(Integer.valueOf(user.id)); 16619 } 16620 return userIds; 16621 } 16622 16623 @Override 16624 public boolean switchUser(final int userId) { 16625 return startUser(userId, /* foregound */ true); 16626 } 16627 16628 private boolean startUser(final int userId, boolean foreground) { 16629 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 16630 != PackageManager.PERMISSION_GRANTED) { 16631 String msg = "Permission Denial: switchUser() from pid=" 16632 + Binder.getCallingPid() 16633 + ", uid=" + Binder.getCallingUid() 16634 + " requires " + INTERACT_ACROSS_USERS_FULL; 16635 Slog.w(TAG, msg); 16636 throw new SecurityException(msg); 16637 } 16638 16639 if (DEBUG_MU) Slog.i(TAG_MU, "starting userid:" + userId + " fore:" + foreground); 16640 16641 final long ident = Binder.clearCallingIdentity(); 16642 try { 16643 synchronized (this) { 16644 final int oldUserId = mCurrentUserId; 16645 if (oldUserId == userId) { 16646 return true; 16647 } 16648 16649 mStackSupervisor.setLockTaskModeLocked(null); 16650 16651 final UserInfo userInfo = getUserManagerLocked().getUserInfo(userId); 16652 if (userInfo == null) { 16653 Slog.w(TAG, "No user info for user #" + userId); 16654 return false; 16655 } 16656 16657 if (foreground) { 16658 mWindowManager.startFreezingScreen(R.anim.screen_user_exit, 16659 R.anim.screen_user_enter); 16660 } 16661 16662 boolean needStart = false; 16663 16664 // If the user we are switching to is not currently started, then 16665 // we need to start it now. 16666 if (mStartedUsers.get(userId) == null) { 16667 mStartedUsers.put(userId, new UserStartedState(new UserHandle(userId), false)); 16668 updateStartedUserArrayLocked(); 16669 needStart = true; 16670 } 16671 16672 final Integer userIdInt = Integer.valueOf(userId); 16673 mUserLru.remove(userIdInt); 16674 mUserLru.add(userIdInt); 16675 16676 if (foreground) { 16677 mCurrentUserId = userId; 16678 updateCurrentProfileIdsLocked(); 16679 mWindowManager.setCurrentUser(userId, mCurrentProfileIds); 16680 // Once the internal notion of the active user has switched, we lock the device 16681 // with the option to show the user switcher on the keyguard. 16682 mWindowManager.lockNow(null); 16683 } else { 16684 final Integer currentUserIdInt = Integer.valueOf(mCurrentUserId); 16685 updateCurrentProfileIdsLocked(); 16686 mWindowManager.setCurrentProfileIds(mCurrentProfileIds); 16687 mUserLru.remove(currentUserIdInt); 16688 mUserLru.add(currentUserIdInt); 16689 } 16690 16691 final UserStartedState uss = mStartedUsers.get(userId); 16692 16693 // Make sure user is in the started state. If it is currently 16694 // stopping, we need to knock that off. 16695 if (uss.mState == UserStartedState.STATE_STOPPING) { 16696 // If we are stopping, we haven't sent ACTION_SHUTDOWN, 16697 // so we can just fairly silently bring the user back from 16698 // the almost-dead. 16699 uss.mState = UserStartedState.STATE_RUNNING; 16700 updateStartedUserArrayLocked(); 16701 needStart = true; 16702 } else if (uss.mState == UserStartedState.STATE_SHUTDOWN) { 16703 // This means ACTION_SHUTDOWN has been sent, so we will 16704 // need to treat this as a new boot of the user. 16705 uss.mState = UserStartedState.STATE_BOOTING; 16706 updateStartedUserArrayLocked(); 16707 needStart = true; 16708 } 16709 16710 if (uss.mState == UserStartedState.STATE_BOOTING) { 16711 // Booting up a new user, need to tell system services about it. 16712 // Note that this is on the same handler as scheduling of broadcasts, 16713 // which is important because it needs to go first. 16714 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_START_MSG, userId)); 16715 } 16716 16717 if (foreground) { 16718 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_CURRENT_MSG, userId)); 16719 mHandler.removeMessages(REPORT_USER_SWITCH_MSG); 16720 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 16721 mHandler.sendMessage(mHandler.obtainMessage(REPORT_USER_SWITCH_MSG, 16722 oldUserId, userId, uss)); 16723 mHandler.sendMessageDelayed(mHandler.obtainMessage(USER_SWITCH_TIMEOUT_MSG, 16724 oldUserId, userId, uss), USER_SWITCH_TIMEOUT); 16725 } 16726 16727 if (needStart) { 16728 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 16729 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 16730 | Intent.FLAG_RECEIVER_FOREGROUND); 16731 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 16732 broadcastIntentLocked(null, null, intent, 16733 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 16734 false, false, MY_PID, Process.SYSTEM_UID, userId); 16735 } 16736 16737 if ((userInfo.flags&UserInfo.FLAG_INITIALIZED) == 0) { 16738 if (userId != UserHandle.USER_OWNER) { 16739 Intent intent = new Intent(Intent.ACTION_USER_INITIALIZE); 16740 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 16741 broadcastIntentLocked(null, null, intent, null, 16742 new IIntentReceiver.Stub() { 16743 public void performReceive(Intent intent, int resultCode, 16744 String data, Bundle extras, boolean ordered, 16745 boolean sticky, int sendingUser) { 16746 userInitialized(uss, userId); 16747 } 16748 }, 0, null, null, null, AppOpsManager.OP_NONE, 16749 true, false, MY_PID, Process.SYSTEM_UID, 16750 userId); 16751 uss.initializing = true; 16752 } else { 16753 getUserManagerLocked().makeInitialized(userInfo.id); 16754 } 16755 } 16756 16757 if (foreground) { 16758 boolean homeInFront = mStackSupervisor.switchUserLocked(userId, uss); 16759 if (homeInFront) { 16760 startHomeActivityLocked(userId); 16761 } else { 16762 mStackSupervisor.resumeTopActivitiesLocked(); 16763 } 16764 EventLogTags.writeAmSwitchUser(userId); 16765 getUserManagerLocked().userForeground(userId); 16766 sendUserSwitchBroadcastsLocked(oldUserId, userId); 16767 } else { 16768 mStackSupervisor.startBackgroundUserLocked(userId, uss); 16769 } 16770 16771 if (needStart) { 16772 Intent intent = new Intent(Intent.ACTION_USER_STARTING); 16773 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 16774 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 16775 broadcastIntentLocked(null, null, intent, 16776 null, new IIntentReceiver.Stub() { 16777 @Override 16778 public void performReceive(Intent intent, int resultCode, String data, 16779 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 16780 throws RemoteException { 16781 } 16782 }, 0, null, null, 16783 android.Manifest.permission.INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 16784 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 16785 } 16786 } 16787 } finally { 16788 Binder.restoreCallingIdentity(ident); 16789 } 16790 16791 return true; 16792 } 16793 16794 void sendUserSwitchBroadcastsLocked(int oldUserId, int newUserId) { 16795 long ident = Binder.clearCallingIdentity(); 16796 try { 16797 Intent intent; 16798 if (oldUserId >= 0) { 16799 intent = new Intent(Intent.ACTION_USER_BACKGROUND); 16800 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 16801 | Intent.FLAG_RECEIVER_FOREGROUND); 16802 intent.putExtra(Intent.EXTRA_USER_HANDLE, oldUserId); 16803 broadcastIntentLocked(null, null, intent, 16804 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 16805 false, false, MY_PID, Process.SYSTEM_UID, oldUserId); 16806 } 16807 if (newUserId >= 0) { 16808 intent = new Intent(Intent.ACTION_USER_FOREGROUND); 16809 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 16810 | Intent.FLAG_RECEIVER_FOREGROUND); 16811 intent.putExtra(Intent.EXTRA_USER_HANDLE, newUserId); 16812 broadcastIntentLocked(null, null, intent, 16813 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 16814 false, false, MY_PID, Process.SYSTEM_UID, newUserId); 16815 intent = new Intent(Intent.ACTION_USER_SWITCHED); 16816 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 16817 | Intent.FLAG_RECEIVER_FOREGROUND); 16818 intent.putExtra(Intent.EXTRA_USER_HANDLE, newUserId); 16819 broadcastIntentLocked(null, null, intent, 16820 null, null, 0, null, null, 16821 android.Manifest.permission.MANAGE_USERS, AppOpsManager.OP_NONE, 16822 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 16823 } 16824 } finally { 16825 Binder.restoreCallingIdentity(ident); 16826 } 16827 } 16828 16829 void dispatchUserSwitch(final UserStartedState uss, final int oldUserId, 16830 final int newUserId) { 16831 final int N = mUserSwitchObservers.beginBroadcast(); 16832 if (N > 0) { 16833 final IRemoteCallback callback = new IRemoteCallback.Stub() { 16834 int mCount = 0; 16835 @Override 16836 public void sendResult(Bundle data) throws RemoteException { 16837 synchronized (ActivityManagerService.this) { 16838 if (mCurUserSwitchCallback == this) { 16839 mCount++; 16840 if (mCount == N) { 16841 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 16842 } 16843 } 16844 } 16845 } 16846 }; 16847 synchronized (this) { 16848 uss.switching = true; 16849 mCurUserSwitchCallback = callback; 16850 } 16851 for (int i=0; i<N; i++) { 16852 try { 16853 mUserSwitchObservers.getBroadcastItem(i).onUserSwitching( 16854 newUserId, callback); 16855 } catch (RemoteException e) { 16856 } 16857 } 16858 } else { 16859 synchronized (this) { 16860 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 16861 } 16862 } 16863 mUserSwitchObservers.finishBroadcast(); 16864 } 16865 16866 void timeoutUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 16867 synchronized (this) { 16868 Slog.w(TAG, "User switch timeout: from " + oldUserId + " to " + newUserId); 16869 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 16870 } 16871 } 16872 16873 void sendContinueUserSwitchLocked(UserStartedState uss, int oldUserId, int newUserId) { 16874 mCurUserSwitchCallback = null; 16875 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 16876 mHandler.sendMessage(mHandler.obtainMessage(CONTINUE_USER_SWITCH_MSG, 16877 oldUserId, newUserId, uss)); 16878 } 16879 16880 void userInitialized(UserStartedState uss, int newUserId) { 16881 completeSwitchAndInitalize(uss, newUserId, true, false); 16882 } 16883 16884 void continueUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 16885 completeSwitchAndInitalize(uss, newUserId, false, true); 16886 } 16887 16888 void completeSwitchAndInitalize(UserStartedState uss, int newUserId, 16889 boolean clearInitializing, boolean clearSwitching) { 16890 boolean unfrozen = false; 16891 synchronized (this) { 16892 if (clearInitializing) { 16893 uss.initializing = false; 16894 getUserManagerLocked().makeInitialized(uss.mHandle.getIdentifier()); 16895 } 16896 if (clearSwitching) { 16897 uss.switching = false; 16898 } 16899 if (!uss.switching && !uss.initializing) { 16900 mWindowManager.stopFreezingScreen(); 16901 unfrozen = true; 16902 } 16903 } 16904 if (unfrozen) { 16905 final int N = mUserSwitchObservers.beginBroadcast(); 16906 for (int i=0; i<N; i++) { 16907 try { 16908 mUserSwitchObservers.getBroadcastItem(i).onUserSwitchComplete(newUserId); 16909 } catch (RemoteException e) { 16910 } 16911 } 16912 mUserSwitchObservers.finishBroadcast(); 16913 } 16914 } 16915 16916 void scheduleStartProfilesLocked() { 16917 if (!mHandler.hasMessages(START_PROFILES_MSG)) { 16918 mHandler.sendMessageDelayed(mHandler.obtainMessage(START_PROFILES_MSG), 16919 DateUtils.SECOND_IN_MILLIS); 16920 } 16921 } 16922 16923 void startProfilesLocked() { 16924 if (DEBUG_MU) Slog.i(TAG_MU, "startProfilesLocked"); 16925 List<UserInfo> profiles = getUserManagerLocked().getProfiles( 16926 mCurrentUserId, false /* enabledOnly */); 16927 List<UserInfo> toStart = new ArrayList<UserInfo>(profiles.size()); 16928 for (UserInfo user : profiles) { 16929 if ((user.flags & UserInfo.FLAG_INITIALIZED) == UserInfo.FLAG_INITIALIZED 16930 && user.id != mCurrentUserId) { 16931 toStart.add(user); 16932 } 16933 } 16934 final int n = toStart.size(); 16935 int i = 0; 16936 for (; i < n && i < (MAX_RUNNING_USERS - 1); ++i) { 16937 startUserInBackground(toStart.get(i).id); 16938 } 16939 if (i < n) { 16940 Slog.w(TAG_MU, "More profiles than MAX_RUNNING_USERS"); 16941 } 16942 } 16943 16944 void finishUserBoot(UserStartedState uss) { 16945 synchronized (this) { 16946 if (uss.mState == UserStartedState.STATE_BOOTING 16947 && mStartedUsers.get(uss.mHandle.getIdentifier()) == uss) { 16948 uss.mState = UserStartedState.STATE_RUNNING; 16949 final int userId = uss.mHandle.getIdentifier(); 16950 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 16951 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 16952 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 16953 broadcastIntentLocked(null, null, intent, 16954 null, null, 0, null, null, 16955 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, AppOpsManager.OP_NONE, 16956 true, false, MY_PID, Process.SYSTEM_UID, userId); 16957 } 16958 } 16959 } 16960 16961 void finishUserSwitch(UserStartedState uss) { 16962 synchronized (this) { 16963 finishUserBoot(uss); 16964 16965 startProfilesLocked(); 16966 16967 int num = mUserLru.size(); 16968 int i = 0; 16969 while (num > MAX_RUNNING_USERS && i < mUserLru.size()) { 16970 Integer oldUserId = mUserLru.get(i); 16971 UserStartedState oldUss = mStartedUsers.get(oldUserId); 16972 if (oldUss == null) { 16973 // Shouldn't happen, but be sane if it does. 16974 mUserLru.remove(i); 16975 num--; 16976 continue; 16977 } 16978 if (oldUss.mState == UserStartedState.STATE_STOPPING 16979 || oldUss.mState == UserStartedState.STATE_SHUTDOWN) { 16980 // This user is already stopping, doesn't count. 16981 num--; 16982 i++; 16983 continue; 16984 } 16985 if (oldUserId == UserHandle.USER_OWNER || oldUserId == mCurrentUserId) { 16986 // Owner and current can't be stopped, but count as running. 16987 i++; 16988 continue; 16989 } 16990 // This is a user to be stopped. 16991 stopUserLocked(oldUserId, null); 16992 num--; 16993 i++; 16994 } 16995 } 16996 } 16997 16998 @Override 16999 public int stopUser(final int userId, final IStopUserCallback callback) { 17000 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17001 != PackageManager.PERMISSION_GRANTED) { 17002 String msg = "Permission Denial: switchUser() from pid=" 17003 + Binder.getCallingPid() 17004 + ", uid=" + Binder.getCallingUid() 17005 + " requires " + INTERACT_ACROSS_USERS_FULL; 17006 Slog.w(TAG, msg); 17007 throw new SecurityException(msg); 17008 } 17009 if (userId <= 0) { 17010 throw new IllegalArgumentException("Can't stop primary user " + userId); 17011 } 17012 synchronized (this) { 17013 return stopUserLocked(userId, callback); 17014 } 17015 } 17016 17017 private int stopUserLocked(final int userId, final IStopUserCallback callback) { 17018 if (DEBUG_MU) Slog.i(TAG_MU, "stopUserLocked userId=" + userId); 17019 if (mCurrentUserId == userId) { 17020 return ActivityManager.USER_OP_IS_CURRENT; 17021 } 17022 17023 final UserStartedState uss = mStartedUsers.get(userId); 17024 if (uss == null) { 17025 // User is not started, nothing to do... but we do need to 17026 // callback if requested. 17027 if (callback != null) { 17028 mHandler.post(new Runnable() { 17029 @Override 17030 public void run() { 17031 try { 17032 callback.userStopped(userId); 17033 } catch (RemoteException e) { 17034 } 17035 } 17036 }); 17037 } 17038 return ActivityManager.USER_OP_SUCCESS; 17039 } 17040 17041 if (callback != null) { 17042 uss.mStopCallbacks.add(callback); 17043 } 17044 17045 if (uss.mState != UserStartedState.STATE_STOPPING 17046 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17047 uss.mState = UserStartedState.STATE_STOPPING; 17048 updateStartedUserArrayLocked(); 17049 17050 long ident = Binder.clearCallingIdentity(); 17051 try { 17052 // We are going to broadcast ACTION_USER_STOPPING and then 17053 // once that is done send a final ACTION_SHUTDOWN and then 17054 // stop the user. 17055 final Intent stoppingIntent = new Intent(Intent.ACTION_USER_STOPPING); 17056 stoppingIntent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 17057 stoppingIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17058 stoppingIntent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 17059 final Intent shutdownIntent = new Intent(Intent.ACTION_SHUTDOWN); 17060 // This is the result receiver for the final shutdown broadcast. 17061 final IIntentReceiver shutdownReceiver = new IIntentReceiver.Stub() { 17062 @Override 17063 public void performReceive(Intent intent, int resultCode, String data, 17064 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 17065 finishUserStop(uss); 17066 } 17067 }; 17068 // This is the result receiver for the initial stopping broadcast. 17069 final IIntentReceiver stoppingReceiver = new IIntentReceiver.Stub() { 17070 @Override 17071 public void performReceive(Intent intent, int resultCode, String data, 17072 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 17073 // On to the next. 17074 synchronized (ActivityManagerService.this) { 17075 if (uss.mState != UserStartedState.STATE_STOPPING) { 17076 // Whoops, we are being started back up. Abort, abort! 17077 return; 17078 } 17079 uss.mState = UserStartedState.STATE_SHUTDOWN; 17080 } 17081 mSystemServiceManager.stopUser(userId); 17082 broadcastIntentLocked(null, null, shutdownIntent, 17083 null, shutdownReceiver, 0, null, null, null, AppOpsManager.OP_NONE, 17084 true, false, MY_PID, Process.SYSTEM_UID, userId); 17085 } 17086 }; 17087 // Kick things off. 17088 broadcastIntentLocked(null, null, stoppingIntent, 17089 null, stoppingReceiver, 0, null, null, 17090 android.Manifest.permission.INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 17091 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 17092 } finally { 17093 Binder.restoreCallingIdentity(ident); 17094 } 17095 } 17096 17097 return ActivityManager.USER_OP_SUCCESS; 17098 } 17099 17100 void finishUserStop(UserStartedState uss) { 17101 final int userId = uss.mHandle.getIdentifier(); 17102 boolean stopped; 17103 ArrayList<IStopUserCallback> callbacks; 17104 synchronized (this) { 17105 callbacks = new ArrayList<IStopUserCallback>(uss.mStopCallbacks); 17106 if (mStartedUsers.get(userId) != uss) { 17107 stopped = false; 17108 } else if (uss.mState != UserStartedState.STATE_SHUTDOWN) { 17109 stopped = false; 17110 } else { 17111 stopped = true; 17112 // User can no longer run. 17113 mStartedUsers.remove(userId); 17114 mUserLru.remove(Integer.valueOf(userId)); 17115 updateStartedUserArrayLocked(); 17116 17117 // Clean up all state and processes associated with the user. 17118 // Kill all the processes for the user. 17119 forceStopUserLocked(userId, "finish user"); 17120 } 17121 } 17122 17123 for (int i=0; i<callbacks.size(); i++) { 17124 try { 17125 if (stopped) callbacks.get(i).userStopped(userId); 17126 else callbacks.get(i).userStopAborted(userId); 17127 } catch (RemoteException e) { 17128 } 17129 } 17130 17131 if (stopped) { 17132 mSystemServiceManager.cleanupUser(userId); 17133 synchronized (this) { 17134 mStackSupervisor.removeUserLocked(userId); 17135 } 17136 } 17137 } 17138 17139 @Override 17140 public UserInfo getCurrentUser() { 17141 if ((checkCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS) 17142 != PackageManager.PERMISSION_GRANTED) && ( 17143 checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17144 != PackageManager.PERMISSION_GRANTED)) { 17145 String msg = "Permission Denial: getCurrentUser() from pid=" 17146 + Binder.getCallingPid() 17147 + ", uid=" + Binder.getCallingUid() 17148 + " requires " + android.Manifest.permission.INTERACT_ACROSS_USERS; 17149 Slog.w(TAG, msg); 17150 throw new SecurityException(msg); 17151 } 17152 synchronized (this) { 17153 return getUserManagerLocked().getUserInfo(mCurrentUserId); 17154 } 17155 } 17156 17157 int getCurrentUserIdLocked() { 17158 return mCurrentUserId; 17159 } 17160 17161 @Override 17162 public boolean isUserRunning(int userId, boolean orStopped) { 17163 if (checkCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS) 17164 != PackageManager.PERMISSION_GRANTED) { 17165 String msg = "Permission Denial: isUserRunning() from pid=" 17166 + Binder.getCallingPid() 17167 + ", uid=" + Binder.getCallingUid() 17168 + " requires " + android.Manifest.permission.INTERACT_ACROSS_USERS; 17169 Slog.w(TAG, msg); 17170 throw new SecurityException(msg); 17171 } 17172 synchronized (this) { 17173 return isUserRunningLocked(userId, orStopped); 17174 } 17175 } 17176 17177 boolean isUserRunningLocked(int userId, boolean orStopped) { 17178 UserStartedState state = mStartedUsers.get(userId); 17179 if (state == null) { 17180 return false; 17181 } 17182 if (orStopped) { 17183 return true; 17184 } 17185 return state.mState != UserStartedState.STATE_STOPPING 17186 && state.mState != UserStartedState.STATE_SHUTDOWN; 17187 } 17188 17189 @Override 17190 public int[] getRunningUserIds() { 17191 if (checkCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS) 17192 != PackageManager.PERMISSION_GRANTED) { 17193 String msg = "Permission Denial: isUserRunning() from pid=" 17194 + Binder.getCallingPid() 17195 + ", uid=" + Binder.getCallingUid() 17196 + " requires " + android.Manifest.permission.INTERACT_ACROSS_USERS; 17197 Slog.w(TAG, msg); 17198 throw new SecurityException(msg); 17199 } 17200 synchronized (this) { 17201 return mStartedUserArray; 17202 } 17203 } 17204 17205 private void updateStartedUserArrayLocked() { 17206 int num = 0; 17207 for (int i=0; i<mStartedUsers.size(); i++) { 17208 UserStartedState uss = mStartedUsers.valueAt(i); 17209 // This list does not include stopping users. 17210 if (uss.mState != UserStartedState.STATE_STOPPING 17211 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17212 num++; 17213 } 17214 } 17215 mStartedUserArray = new int[num]; 17216 num = 0; 17217 for (int i=0; i<mStartedUsers.size(); i++) { 17218 UserStartedState uss = mStartedUsers.valueAt(i); 17219 if (uss.mState != UserStartedState.STATE_STOPPING 17220 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17221 mStartedUserArray[num] = mStartedUsers.keyAt(i); 17222 num++; 17223 } 17224 } 17225 } 17226 17227 @Override 17228 public void registerUserSwitchObserver(IUserSwitchObserver observer) { 17229 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17230 != PackageManager.PERMISSION_GRANTED) { 17231 String msg = "Permission Denial: registerUserSwitchObserver() from pid=" 17232 + Binder.getCallingPid() 17233 + ", uid=" + Binder.getCallingUid() 17234 + " requires " + INTERACT_ACROSS_USERS_FULL; 17235 Slog.w(TAG, msg); 17236 throw new SecurityException(msg); 17237 } 17238 17239 mUserSwitchObservers.register(observer); 17240 } 17241 17242 @Override 17243 public void unregisterUserSwitchObserver(IUserSwitchObserver observer) { 17244 mUserSwitchObservers.unregister(observer); 17245 } 17246 17247 private boolean userExists(int userId) { 17248 if (userId == 0) { 17249 return true; 17250 } 17251 UserManagerService ums = getUserManagerLocked(); 17252 return ums != null ? (ums.getUserInfo(userId) != null) : false; 17253 } 17254 17255 int[] getUsersLocked() { 17256 UserManagerService ums = getUserManagerLocked(); 17257 return ums != null ? ums.getUserIds() : new int[] { 0 }; 17258 } 17259 17260 UserManagerService getUserManagerLocked() { 17261 if (mUserManager == null) { 17262 IBinder b = ServiceManager.getService(Context.USER_SERVICE); 17263 mUserManager = (UserManagerService)IUserManager.Stub.asInterface(b); 17264 } 17265 return mUserManager; 17266 } 17267 17268 private int applyUserId(int uid, int userId) { 17269 return UserHandle.getUid(userId, uid); 17270 } 17271 17272 ApplicationInfo getAppInfoForUser(ApplicationInfo info, int userId) { 17273 if (info == null) return null; 17274 ApplicationInfo newInfo = new ApplicationInfo(info); 17275 newInfo.uid = applyUserId(info.uid, userId); 17276 newInfo.dataDir = USER_DATA_DIR + userId + "/" 17277 + info.packageName; 17278 return newInfo; 17279 } 17280 17281 ActivityInfo getActivityInfoForUser(ActivityInfo aInfo, int userId) { 17282 if (aInfo == null 17283 || (userId < 1 && aInfo.applicationInfo.uid < UserHandle.PER_USER_RANGE)) { 17284 return aInfo; 17285 } 17286 17287 ActivityInfo info = new ActivityInfo(aInfo); 17288 info.applicationInfo = getAppInfoForUser(info.applicationInfo, userId); 17289 return info; 17290 } 17291 17292 private final class LocalService extends ActivityManagerInternal { 17293 @Override 17294 public void goingToSleep() { 17295 ActivityManagerService.this.goingToSleep(); 17296 } 17297 17298 @Override 17299 public void wakingUp() { 17300 ActivityManagerService.this.wakingUp(); 17301 } 17302 } 17303 17304 /** 17305 * An implementation of IAppTask, that allows an app to manage its own tasks via 17306 * {@link android.app.ActivityManager.AppTask}. We keep track of the callingUid to ensure that 17307 * only the process that calls getAppTasks() can call the AppTask methods. 17308 */ 17309 class AppTaskImpl extends IAppTask.Stub { 17310 private int mTaskId; 17311 private int mCallingUid; 17312 17313 public AppTaskImpl(int taskId, int callingUid) { 17314 mTaskId = taskId; 17315 mCallingUid = callingUid; 17316 } 17317 17318 @Override 17319 public void finishAndRemoveTask() { 17320 // Ensure that we are called from the same process that created this AppTask 17321 if (mCallingUid != Binder.getCallingUid()) { 17322 Slog.w(TAG, "finishAndRemoveTask: caller " + mCallingUid 17323 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 17324 return; 17325 } 17326 17327 synchronized (ActivityManagerService.this) { 17328 long origId = Binder.clearCallingIdentity(); 17329 try { 17330 TaskRecord tr = recentTaskForIdLocked(mTaskId); 17331 if (tr != null) { 17332 // Only kill the process if we are not a new document 17333 int flags = tr.getBaseIntent().getFlags(); 17334 boolean isDocument = (flags & Intent.FLAG_ACTIVITY_NEW_DOCUMENT) == 17335 Intent.FLAG_ACTIVITY_NEW_DOCUMENT; 17336 removeTaskByIdLocked(mTaskId, 17337 !isDocument ? ActivityManager.REMOVE_TASK_KILL_PROCESS : 0); 17338 } 17339 } finally { 17340 Binder.restoreCallingIdentity(origId); 17341 } 17342 } 17343 } 17344 17345 @Override 17346 public ActivityManager.RecentTaskInfo getTaskInfo() { 17347 // Ensure that we are called from the same process that created this AppTask 17348 if (mCallingUid != Binder.getCallingUid()) { 17349 Slog.w(TAG, "finishAndRemoveTask: caller " + mCallingUid 17350 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 17351 return null; 17352 } 17353 17354 synchronized (ActivityManagerService.this) { 17355 long origId = Binder.clearCallingIdentity(); 17356 try { 17357 TaskRecord tr = recentTaskForIdLocked(mTaskId); 17358 if (tr != null) { 17359 return createRecentTaskInfoFromTaskRecord(tr); 17360 } 17361 } finally { 17362 Binder.restoreCallingIdentity(origId); 17363 } 17364 return null; 17365 } 17366 } 17367 } 17368} 17369