ActivityManagerService.java revision 6d2a9492e2b19421165f0cd918d9f28595bfb770
1/* 2 * Copyright (C) 2006-2008 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17package com.android.server.am; 18 19import static android.Manifest.permission.INTERACT_ACROSS_USERS; 20import static android.Manifest.permission.INTERACT_ACROSS_USERS_FULL; 21import static android.Manifest.permission.START_TASKS_FROM_RECENTS; 22import static android.content.pm.PackageManager.PERMISSION_GRANTED; 23import static com.android.internal.util.XmlUtils.readBooleanAttribute; 24import static com.android.internal.util.XmlUtils.readIntAttribute; 25import static com.android.internal.util.XmlUtils.readLongAttribute; 26import static com.android.internal.util.XmlUtils.writeBooleanAttribute; 27import static com.android.internal.util.XmlUtils.writeIntAttribute; 28import static com.android.internal.util.XmlUtils.writeLongAttribute; 29import static com.android.server.Watchdog.NATIVE_STACKS_OF_INTEREST; 30import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT; 31import static org.xmlpull.v1.XmlPullParser.START_TAG; 32import static com.android.server.am.ActivityStackSupervisor.HOME_STACK_ID; 33 34import android.Manifest; 35import android.app.AppOpsManager; 36import android.app.IActivityContainer; 37import android.app.IActivityContainerCallback; 38import android.app.IAppTask; 39import android.app.admin.DevicePolicyManager; 40import android.app.usage.UsageEvents; 41import android.app.usage.UsageStatsManagerInternal; 42import android.appwidget.AppWidgetManager; 43import android.graphics.Rect; 44import android.os.BatteryStats; 45import android.os.PersistableBundle; 46import android.service.voice.IVoiceInteractionSession; 47import android.util.ArrayMap; 48import android.util.ArraySet; 49import android.util.SparseIntArray; 50 51import com.android.internal.R; 52import com.android.internal.annotations.GuardedBy; 53import com.android.internal.app.IAppOpsService; 54import com.android.internal.app.IVoiceInteractor; 55import com.android.internal.app.ProcessMap; 56import com.android.internal.app.ProcessStats; 57import com.android.internal.content.PackageMonitor; 58import com.android.internal.os.BackgroundThread; 59import com.android.internal.os.BatteryStatsImpl; 60import com.android.internal.os.ProcessCpuTracker; 61import com.android.internal.os.TransferPipe; 62import com.android.internal.os.Zygote; 63import com.android.internal.util.FastPrintWriter; 64import com.android.internal.util.FastXmlSerializer; 65import com.android.internal.util.MemInfoReader; 66import com.android.internal.util.Preconditions; 67import com.android.server.AppOpsService; 68import com.android.server.AttributeCache; 69import com.android.server.IntentResolver; 70import com.android.server.LocalServices; 71import com.android.server.ServiceThread; 72import com.android.server.SystemService; 73import com.android.server.SystemServiceManager; 74import com.android.server.Watchdog; 75import com.android.server.am.ActivityStack.ActivityState; 76import com.android.server.firewall.IntentFirewall; 77import com.android.server.pm.UserManagerService; 78import com.android.server.wm.AppTransition; 79import com.android.server.wm.WindowManagerService; 80import com.google.android.collect.Lists; 81import com.google.android.collect.Maps; 82 83import libcore.io.IoUtils; 84 85import org.xmlpull.v1.XmlPullParser; 86import org.xmlpull.v1.XmlPullParserException; 87import org.xmlpull.v1.XmlSerializer; 88 89import android.app.Activity; 90import android.app.ActivityManager; 91import android.app.ActivityManager.RunningTaskInfo; 92import android.app.ActivityManager.StackInfo; 93import android.app.ActivityManagerInternal; 94import android.app.ActivityManagerNative; 95import android.app.ActivityOptions; 96import android.app.ActivityThread; 97import android.app.AlertDialog; 98import android.app.AppGlobals; 99import android.app.ApplicationErrorReport; 100import android.app.Dialog; 101import android.app.IActivityController; 102import android.app.IApplicationThread; 103import android.app.IInstrumentationWatcher; 104import android.app.INotificationManager; 105import android.app.IProcessObserver; 106import android.app.IServiceConnection; 107import android.app.IStopUserCallback; 108import android.app.IUiAutomationConnection; 109import android.app.IUserSwitchObserver; 110import android.app.Instrumentation; 111import android.app.Notification; 112import android.app.NotificationManager; 113import android.app.PendingIntent; 114import android.app.backup.IBackupManager; 115import android.content.ActivityNotFoundException; 116import android.content.BroadcastReceiver; 117import android.content.ClipData; 118import android.content.ComponentCallbacks2; 119import android.content.ComponentName; 120import android.content.ContentProvider; 121import android.content.ContentResolver; 122import android.content.Context; 123import android.content.DialogInterface; 124import android.content.IContentProvider; 125import android.content.IIntentReceiver; 126import android.content.IIntentSender; 127import android.content.Intent; 128import android.content.IntentFilter; 129import android.content.IntentSender; 130import android.content.pm.ActivityInfo; 131import android.content.pm.ApplicationInfo; 132import android.content.pm.ConfigurationInfo; 133import android.content.pm.IPackageDataObserver; 134import android.content.pm.IPackageManager; 135import android.content.pm.InstrumentationInfo; 136import android.content.pm.PackageInfo; 137import android.content.pm.PackageManager; 138import android.content.pm.ParceledListSlice; 139import android.content.pm.UserInfo; 140import android.content.pm.PackageManager.NameNotFoundException; 141import android.content.pm.PathPermission; 142import android.content.pm.ProviderInfo; 143import android.content.pm.ResolveInfo; 144import android.content.pm.ServiceInfo; 145import android.content.res.CompatibilityInfo; 146import android.content.res.Configuration; 147import android.net.Proxy; 148import android.net.ProxyInfo; 149import android.net.Uri; 150import android.os.Binder; 151import android.os.Build; 152import android.os.Bundle; 153import android.os.Debug; 154import android.os.DropBoxManager; 155import android.os.Environment; 156import android.os.FactoryTest; 157import android.os.FileObserver; 158import android.os.FileUtils; 159import android.os.Handler; 160import android.os.IBinder; 161import android.os.IPermissionController; 162import android.os.IRemoteCallback; 163import android.os.IUserManager; 164import android.os.Looper; 165import android.os.Message; 166import android.os.Parcel; 167import android.os.ParcelFileDescriptor; 168import android.os.Process; 169import android.os.RemoteCallbackList; 170import android.os.RemoteException; 171import android.os.SELinux; 172import android.os.ServiceManager; 173import android.os.StrictMode; 174import android.os.SystemClock; 175import android.os.SystemProperties; 176import android.os.UpdateLock; 177import android.os.UserHandle; 178import android.provider.Settings; 179import android.text.format.DateUtils; 180import android.text.format.Time; 181import android.util.AtomicFile; 182import android.util.EventLog; 183import android.util.Log; 184import android.util.Pair; 185import android.util.PrintWriterPrinter; 186import android.util.Slog; 187import android.util.SparseArray; 188import android.util.TimeUtils; 189import android.util.Xml; 190import android.view.Gravity; 191import android.view.LayoutInflater; 192import android.view.View; 193import android.view.WindowManager; 194 195import java.io.BufferedInputStream; 196import java.io.BufferedOutputStream; 197import java.io.DataInputStream; 198import java.io.DataOutputStream; 199import java.io.File; 200import java.io.FileDescriptor; 201import java.io.FileInputStream; 202import java.io.FileNotFoundException; 203import java.io.FileOutputStream; 204import java.io.IOException; 205import java.io.InputStreamReader; 206import java.io.PrintWriter; 207import java.io.StringWriter; 208import java.lang.ref.WeakReference; 209import java.util.ArrayList; 210import java.util.Arrays; 211import java.util.Collections; 212import java.util.Comparator; 213import java.util.HashMap; 214import java.util.HashSet; 215import java.util.Iterator; 216import java.util.List; 217import java.util.Locale; 218import java.util.Map; 219import java.util.Set; 220import java.util.concurrent.atomic.AtomicBoolean; 221import java.util.concurrent.atomic.AtomicLong; 222 223public final class ActivityManagerService extends ActivityManagerNative 224 implements Watchdog.Monitor, BatteryStatsImpl.BatteryCallback { 225 226 private static final String USER_DATA_DIR = "/data/user/"; 227 // File that stores last updated system version and called preboot receivers 228 static final String CALLED_PRE_BOOTS_FILENAME = "called_pre_boots.dat"; 229 230 static final String TAG = "ActivityManager"; 231 static final String TAG_MU = "ActivityManagerServiceMU"; 232 static final boolean DEBUG = false; 233 static final boolean localLOGV = DEBUG; 234 static final boolean DEBUG_BACKUP = localLOGV || false; 235 static final boolean DEBUG_BROADCAST = localLOGV || false; 236 static final boolean DEBUG_BROADCAST_LIGHT = DEBUG_BROADCAST || false; 237 static final boolean DEBUG_BACKGROUND_BROADCAST = DEBUG_BROADCAST || false; 238 static final boolean DEBUG_CLEANUP = localLOGV || false; 239 static final boolean DEBUG_CONFIGURATION = localLOGV || false; 240 static final boolean DEBUG_FOCUS = false; 241 static final boolean DEBUG_IMMERSIVE = localLOGV || false; 242 static final boolean DEBUG_MU = localLOGV || false; 243 static final boolean DEBUG_OOM_ADJ = localLOGV || false; 244 static final boolean DEBUG_LRU = localLOGV || false; 245 static final boolean DEBUG_PAUSE = localLOGV || false; 246 static final boolean DEBUG_POWER = localLOGV || false; 247 static final boolean DEBUG_POWER_QUICK = DEBUG_POWER || false; 248 static final boolean DEBUG_PROCESS_OBSERVERS = localLOGV || false; 249 static final boolean DEBUG_PROCESSES = localLOGV || false; 250 static final boolean DEBUG_PROVIDER = localLOGV || false; 251 static final boolean DEBUG_RESULTS = localLOGV || false; 252 static final boolean DEBUG_SERVICE = localLOGV || false; 253 static final boolean DEBUG_SERVICE_EXECUTING = localLOGV || false; 254 static final boolean DEBUG_STACK = localLOGV || false; 255 static final boolean DEBUG_SWITCH = localLOGV || false; 256 static final boolean DEBUG_TASKS = localLOGV || false; 257 static final boolean DEBUG_THUMBNAILS = localLOGV || false; 258 static final boolean DEBUG_TRANSITION = localLOGV || false; 259 static final boolean DEBUG_URI_PERMISSION = localLOGV || false; 260 static final boolean DEBUG_USER_LEAVING = localLOGV || false; 261 static final boolean DEBUG_VISBILITY = localLOGV || false; 262 static final boolean DEBUG_PSS = localLOGV || false; 263 static final boolean DEBUG_LOCKSCREEN = localLOGV || false; 264 static final boolean VALIDATE_TOKENS = false; 265 static final boolean SHOW_ACTIVITY_START_TIME = true; 266 267 // Control over CPU and battery monitoring. 268 static final long BATTERY_STATS_TIME = 30*60*1000; // write battery stats every 30 minutes. 269 static final boolean MONITOR_CPU_USAGE = true; 270 static final long MONITOR_CPU_MIN_TIME = 5*1000; // don't sample cpu less than every 5 seconds. 271 static final long MONITOR_CPU_MAX_TIME = 0x0fffffff; // wait possibly forever for next cpu sample. 272 static final boolean MONITOR_THREAD_CPU_USAGE = false; 273 274 // The flags that are set for all calls we make to the package manager. 275 static final int STOCK_PM_FLAGS = PackageManager.GET_SHARED_LIBRARY_FILES; 276 277 private static final String SYSTEM_DEBUGGABLE = "ro.debuggable"; 278 279 static final boolean IS_USER_BUILD = "user".equals(Build.TYPE); 280 281 // Maximum number of recent tasks that we can remember. 282 static final int MAX_RECENT_TASKS = ActivityManager.isLowRamDeviceStatic() ? 100 : 200; 283 284 // Maximum number recent bitmaps to keep in memory. 285 static final int MAX_RECENT_BITMAPS = 5; 286 287 // Amount of time after a call to stopAppSwitches() during which we will 288 // prevent further untrusted switches from happening. 289 static final long APP_SWITCH_DELAY_TIME = 5*1000; 290 291 // How long we wait for a launched process to attach to the activity manager 292 // before we decide it's never going to come up for real. 293 static final int PROC_START_TIMEOUT = 10*1000; 294 295 // How long we wait for a launched process to attach to the activity manager 296 // before we decide it's never going to come up for real, when the process was 297 // started with a wrapper for instrumentation (such as Valgrind) because it 298 // could take much longer than usual. 299 static final int PROC_START_TIMEOUT_WITH_WRAPPER = 1200*1000; 300 301 // How long to wait after going idle before forcing apps to GC. 302 static final int GC_TIMEOUT = 5*1000; 303 304 // The minimum amount of time between successive GC requests for a process. 305 static final int GC_MIN_INTERVAL = 60*1000; 306 307 // The minimum amount of time between successive PSS requests for a process. 308 static final int FULL_PSS_MIN_INTERVAL = 10*60*1000; 309 310 // The minimum amount of time between successive PSS requests for a process 311 // when the request is due to the memory state being lowered. 312 static final int FULL_PSS_LOWERED_INTERVAL = 2*60*1000; 313 314 // The rate at which we check for apps using excessive power -- 15 mins. 315 static final int POWER_CHECK_DELAY = (DEBUG_POWER_QUICK ? 2 : 15) * 60*1000; 316 317 // The minimum sample duration we will allow before deciding we have 318 // enough data on wake locks to start killing things. 319 static final int WAKE_LOCK_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 320 321 // The minimum sample duration we will allow before deciding we have 322 // enough data on CPU usage to start killing things. 323 static final int CPU_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 324 325 // How long we allow a receiver to run before giving up on it. 326 static final int BROADCAST_FG_TIMEOUT = 10*1000; 327 static final int BROADCAST_BG_TIMEOUT = 60*1000; 328 329 // How long we wait until we timeout on key dispatching. 330 static final int KEY_DISPATCHING_TIMEOUT = 5*1000; 331 332 // How long we wait until we timeout on key dispatching during instrumentation. 333 static final int INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT = 60*1000; 334 335 // Amount of time we wait for observers to handle a user switch before 336 // giving up on them and unfreezing the screen. 337 static final int USER_SWITCH_TIMEOUT = 2*1000; 338 339 // Maximum number of users we allow to be running at a time. 340 static final int MAX_RUNNING_USERS = 3; 341 342 // How long to wait in getAssistContextExtras for the activity and foreground services 343 // to respond with the result. 344 static final int PENDING_ASSIST_EXTRAS_TIMEOUT = 500; 345 346 // Maximum number of persisted Uri grants a package is allowed 347 static final int MAX_PERSISTED_URI_GRANTS = 128; 348 349 static final int MY_PID = Process.myPid(); 350 351 static final String[] EMPTY_STRING_ARRAY = new String[0]; 352 353 // How many bytes to write into the dropbox log before truncating 354 static final int DROPBOX_MAX_SIZE = 256 * 1024; 355 356 // Access modes for handleIncomingUser. 357 static final int ALLOW_NON_FULL = 0; 358 static final int ALLOW_NON_FULL_IN_PROFILE = 1; 359 static final int ALLOW_FULL_ONLY = 2; 360 361 static final int LAST_PREBOOT_DELIVERED_FILE_VERSION = 10000; 362 363 /** All system services */ 364 SystemServiceManager mSystemServiceManager; 365 366 /** Run all ActivityStacks through this */ 367 ActivityStackSupervisor mStackSupervisor; 368 369 public IntentFirewall mIntentFirewall; 370 371 // Whether we should show our dialogs (ANR, crash, etc) or just perform their 372 // default actuion automatically. Important for devices without direct input 373 // devices. 374 private boolean mShowDialogs = true; 375 376 BroadcastQueue mFgBroadcastQueue; 377 BroadcastQueue mBgBroadcastQueue; 378 // Convenient for easy iteration over the queues. Foreground is first 379 // so that dispatch of foreground broadcasts gets precedence. 380 final BroadcastQueue[] mBroadcastQueues = new BroadcastQueue[2]; 381 382 BroadcastQueue broadcastQueueForIntent(Intent intent) { 383 final boolean isFg = (intent.getFlags() & Intent.FLAG_RECEIVER_FOREGROUND) != 0; 384 if (DEBUG_BACKGROUND_BROADCAST) { 385 Slog.i(TAG, "Broadcast intent " + intent + " on " 386 + (isFg ? "foreground" : "background") 387 + " queue"); 388 } 389 return (isFg) ? mFgBroadcastQueue : mBgBroadcastQueue; 390 } 391 392 BroadcastRecord broadcastRecordForReceiverLocked(IBinder receiver) { 393 for (BroadcastQueue queue : mBroadcastQueues) { 394 BroadcastRecord r = queue.getMatchingOrderedReceiver(receiver); 395 if (r != null) { 396 return r; 397 } 398 } 399 return null; 400 } 401 402 /** 403 * Activity we have told the window manager to have key focus. 404 */ 405 ActivityRecord mFocusedActivity = null; 406 407 /** 408 * List of intents that were used to start the most recent tasks. 409 */ 410 ArrayList<TaskRecord> mRecentTasks; 411 ArraySet<TaskRecord> mTmpRecents = new ArraySet<TaskRecord>(); 412 413 public class PendingAssistExtras extends Binder implements Runnable { 414 public final ActivityRecord activity; 415 public boolean haveResult = false; 416 public Bundle result = null; 417 public PendingAssistExtras(ActivityRecord _activity) { 418 activity = _activity; 419 } 420 @Override 421 public void run() { 422 Slog.w(TAG, "getAssistContextExtras failed: timeout retrieving from " + activity); 423 synchronized (this) { 424 haveResult = true; 425 notifyAll(); 426 } 427 } 428 } 429 430 final ArrayList<PendingAssistExtras> mPendingAssistExtras 431 = new ArrayList<PendingAssistExtras>(); 432 433 /** 434 * Process management. 435 */ 436 final ProcessList mProcessList = new ProcessList(); 437 438 /** 439 * All of the applications we currently have running organized by name. 440 * The keys are strings of the application package name (as 441 * returned by the package manager), and the keys are ApplicationRecord 442 * objects. 443 */ 444 final ProcessMap<ProcessRecord> mProcessNames = new ProcessMap<ProcessRecord>(); 445 446 /** 447 * Tracking long-term execution of processes to look for abuse and other 448 * bad app behavior. 449 */ 450 final ProcessStatsService mProcessStats; 451 452 /** 453 * The currently running isolated processes. 454 */ 455 final SparseArray<ProcessRecord> mIsolatedProcesses = new SparseArray<ProcessRecord>(); 456 457 /** 458 * Counter for assigning isolated process uids, to avoid frequently reusing the 459 * same ones. 460 */ 461 int mNextIsolatedProcessUid = 0; 462 463 /** 464 * The currently running heavy-weight process, if any. 465 */ 466 ProcessRecord mHeavyWeightProcess = null; 467 468 /** 469 * The last time that various processes have crashed. 470 */ 471 final ProcessMap<Long> mProcessCrashTimes = new ProcessMap<Long>(); 472 473 /** 474 * Information about a process that is currently marked as bad. 475 */ 476 static final class BadProcessInfo { 477 BadProcessInfo(long time, String shortMsg, String longMsg, String stack) { 478 this.time = time; 479 this.shortMsg = shortMsg; 480 this.longMsg = longMsg; 481 this.stack = stack; 482 } 483 484 final long time; 485 final String shortMsg; 486 final String longMsg; 487 final String stack; 488 } 489 490 /** 491 * Set of applications that we consider to be bad, and will reject 492 * incoming broadcasts from (which the user has no control over). 493 * Processes are added to this set when they have crashed twice within 494 * a minimum amount of time; they are removed from it when they are 495 * later restarted (hopefully due to some user action). The value is the 496 * time it was added to the list. 497 */ 498 final ProcessMap<BadProcessInfo> mBadProcesses = new ProcessMap<BadProcessInfo>(); 499 500 /** 501 * All of the processes we currently have running organized by pid. 502 * The keys are the pid running the application. 503 * 504 * <p>NOTE: This object is protected by its own lock, NOT the global 505 * activity manager lock! 506 */ 507 final SparseArray<ProcessRecord> mPidsSelfLocked = new SparseArray<ProcessRecord>(); 508 509 /** 510 * All of the processes that have been forced to be foreground. The key 511 * is the pid of the caller who requested it (we hold a death 512 * link on it). 513 */ 514 abstract class ForegroundToken implements IBinder.DeathRecipient { 515 int pid; 516 IBinder token; 517 } 518 final SparseArray<ForegroundToken> mForegroundProcesses = new SparseArray<ForegroundToken>(); 519 520 /** 521 * List of records for processes that someone had tried to start before the 522 * system was ready. We don't start them at that point, but ensure they 523 * are started by the time booting is complete. 524 */ 525 final ArrayList<ProcessRecord> mProcessesOnHold = new ArrayList<ProcessRecord>(); 526 527 /** 528 * List of persistent applications that are in the process 529 * of being started. 530 */ 531 final ArrayList<ProcessRecord> mPersistentStartingProcesses = new ArrayList<ProcessRecord>(); 532 533 /** 534 * Processes that are being forcibly torn down. 535 */ 536 final ArrayList<ProcessRecord> mRemovedProcesses = new ArrayList<ProcessRecord>(); 537 538 /** 539 * List of running applications, sorted by recent usage. 540 * The first entry in the list is the least recently used. 541 */ 542 final ArrayList<ProcessRecord> mLruProcesses = new ArrayList<ProcessRecord>(); 543 544 /** 545 * Where in mLruProcesses that the processes hosting activities start. 546 */ 547 int mLruProcessActivityStart = 0; 548 549 /** 550 * Where in mLruProcesses that the processes hosting services start. 551 * This is after (lower index) than mLruProcessesActivityStart. 552 */ 553 int mLruProcessServiceStart = 0; 554 555 /** 556 * List of processes that should gc as soon as things are idle. 557 */ 558 final ArrayList<ProcessRecord> mProcessesToGc = new ArrayList<ProcessRecord>(); 559 560 /** 561 * Processes we want to collect PSS data from. 562 */ 563 final ArrayList<ProcessRecord> mPendingPssProcesses = new ArrayList<ProcessRecord>(); 564 565 /** 566 * Last time we requested PSS data of all processes. 567 */ 568 long mLastFullPssTime = SystemClock.uptimeMillis(); 569 570 /** 571 * If set, the next time we collect PSS data we should do a full collection 572 * with data from native processes and the kernel. 573 */ 574 boolean mFullPssPending = false; 575 576 /** 577 * This is the process holding what we currently consider to be 578 * the "home" activity. 579 */ 580 ProcessRecord mHomeProcess; 581 582 /** 583 * This is the process holding the activity the user last visited that 584 * is in a different process from the one they are currently in. 585 */ 586 ProcessRecord mPreviousProcess; 587 588 /** 589 * The time at which the previous process was last visible. 590 */ 591 long mPreviousProcessVisibleTime; 592 593 /** 594 * Which uses have been started, so are allowed to run code. 595 */ 596 final SparseArray<UserStartedState> mStartedUsers = new SparseArray<UserStartedState>(); 597 598 /** 599 * LRU list of history of current users. Most recently current is at the end. 600 */ 601 final ArrayList<Integer> mUserLru = new ArrayList<Integer>(); 602 603 /** 604 * Constant array of the users that are currently started. 605 */ 606 int[] mStartedUserArray = new int[] { 0 }; 607 608 /** 609 * Registered observers of the user switching mechanics. 610 */ 611 final RemoteCallbackList<IUserSwitchObserver> mUserSwitchObservers 612 = new RemoteCallbackList<IUserSwitchObserver>(); 613 614 /** 615 * Currently active user switch. 616 */ 617 Object mCurUserSwitchCallback; 618 619 /** 620 * Packages that the user has asked to have run in screen size 621 * compatibility mode instead of filling the screen. 622 */ 623 final CompatModePackages mCompatModePackages; 624 625 /** 626 * Set of IntentSenderRecord objects that are currently active. 627 */ 628 final HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>> mIntentSenderRecords 629 = new HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>>(); 630 631 /** 632 * Fingerprints (hashCode()) of stack traces that we've 633 * already logged DropBox entries for. Guarded by itself. If 634 * something (rogue user app) forces this over 635 * MAX_DUP_SUPPRESSED_STACKS entries, the contents are cleared. 636 */ 637 private final HashSet<Integer> mAlreadyLoggedViolatedStacks = new HashSet<Integer>(); 638 private static final int MAX_DUP_SUPPRESSED_STACKS = 5000; 639 640 /** 641 * Strict Mode background batched logging state. 642 * 643 * The string buffer is guarded by itself, and its lock is also 644 * used to determine if another batched write is already 645 * in-flight. 646 */ 647 private final StringBuilder mStrictModeBuffer = new StringBuilder(); 648 649 /** 650 * Keeps track of all IIntentReceivers that have been registered for 651 * broadcasts. Hash keys are the receiver IBinder, hash value is 652 * a ReceiverList. 653 */ 654 final HashMap<IBinder, ReceiverList> mRegisteredReceivers = 655 new HashMap<IBinder, ReceiverList>(); 656 657 /** 658 * Resolver for broadcast intents to registered receivers. 659 * Holds BroadcastFilter (subclass of IntentFilter). 660 */ 661 final IntentResolver<BroadcastFilter, BroadcastFilter> mReceiverResolver 662 = new IntentResolver<BroadcastFilter, BroadcastFilter>() { 663 @Override 664 protected boolean allowFilterResult( 665 BroadcastFilter filter, List<BroadcastFilter> dest) { 666 IBinder target = filter.receiverList.receiver.asBinder(); 667 for (int i=dest.size()-1; i>=0; i--) { 668 if (dest.get(i).receiverList.receiver.asBinder() == target) { 669 return false; 670 } 671 } 672 return true; 673 } 674 675 @Override 676 protected BroadcastFilter newResult(BroadcastFilter filter, int match, int userId) { 677 if (userId == UserHandle.USER_ALL || filter.owningUserId == UserHandle.USER_ALL 678 || userId == filter.owningUserId) { 679 return super.newResult(filter, match, userId); 680 } 681 return null; 682 } 683 684 @Override 685 protected BroadcastFilter[] newArray(int size) { 686 return new BroadcastFilter[size]; 687 } 688 689 @Override 690 protected boolean isPackageForFilter(String packageName, BroadcastFilter filter) { 691 return packageName.equals(filter.packageName); 692 } 693 }; 694 695 /** 696 * State of all active sticky broadcasts per user. Keys are the action of the 697 * sticky Intent, values are an ArrayList of all broadcasted intents with 698 * that action (which should usually be one). The SparseArray is keyed 699 * by the user ID the sticky is for, and can include UserHandle.USER_ALL 700 * for stickies that are sent to all users. 701 */ 702 final SparseArray<ArrayMap<String, ArrayList<Intent>>> mStickyBroadcasts = 703 new SparseArray<ArrayMap<String, ArrayList<Intent>>>(); 704 705 final ActiveServices mServices; 706 707 /** 708 * Backup/restore process management 709 */ 710 String mBackupAppName = null; 711 BackupRecord mBackupTarget = null; 712 713 final ProviderMap mProviderMap; 714 715 /** 716 * List of content providers who have clients waiting for them. The 717 * application is currently being launched and the provider will be 718 * removed from this list once it is published. 719 */ 720 final ArrayList<ContentProviderRecord> mLaunchingProviders 721 = new ArrayList<ContentProviderRecord>(); 722 723 /** 724 * File storing persisted {@link #mGrantedUriPermissions}. 725 */ 726 private final AtomicFile mGrantFile; 727 728 /** XML constants used in {@link #mGrantFile} */ 729 private static final String TAG_URI_GRANTS = "uri-grants"; 730 private static final String TAG_URI_GRANT = "uri-grant"; 731 private static final String ATTR_USER_HANDLE = "userHandle"; 732 private static final String ATTR_SOURCE_USER_ID = "sourceUserId"; 733 private static final String ATTR_TARGET_USER_ID = "targetUserId"; 734 private static final String ATTR_SOURCE_PKG = "sourcePkg"; 735 private static final String ATTR_TARGET_PKG = "targetPkg"; 736 private static final String ATTR_URI = "uri"; 737 private static final String ATTR_MODE_FLAGS = "modeFlags"; 738 private static final String ATTR_CREATED_TIME = "createdTime"; 739 private static final String ATTR_PREFIX = "prefix"; 740 741 /** 742 * Global set of specific {@link Uri} permissions that have been granted. 743 * This optimized lookup structure maps from {@link UriPermission#targetUid} 744 * to {@link UriPermission#uri} to {@link UriPermission}. 745 */ 746 @GuardedBy("this") 747 private final SparseArray<ArrayMap<GrantUri, UriPermission>> 748 mGrantedUriPermissions = new SparseArray<ArrayMap<GrantUri, UriPermission>>(); 749 750 public static class GrantUri { 751 public final int sourceUserId; 752 public final Uri uri; 753 public boolean prefix; 754 755 public GrantUri(int sourceUserId, Uri uri, boolean prefix) { 756 this.sourceUserId = sourceUserId; 757 this.uri = uri; 758 this.prefix = prefix; 759 } 760 761 @Override 762 public int hashCode() { 763 return toString().hashCode(); 764 } 765 766 @Override 767 public boolean equals(Object o) { 768 if (o instanceof GrantUri) { 769 GrantUri other = (GrantUri) o; 770 return uri.equals(other.uri) && (sourceUserId == other.sourceUserId) 771 && prefix == other.prefix; 772 } 773 return false; 774 } 775 776 @Override 777 public String toString() { 778 String result = Integer.toString(sourceUserId) + " @ " + uri.toString(); 779 if (prefix) result += " [prefix]"; 780 return result; 781 } 782 783 public String toSafeString() { 784 String result = Integer.toString(sourceUserId) + " @ " + uri.toSafeString(); 785 if (prefix) result += " [prefix]"; 786 return result; 787 } 788 789 public static GrantUri resolve(int defaultSourceUserHandle, Uri uri) { 790 return new GrantUri(ContentProvider.getUserIdFromUri(uri, defaultSourceUserHandle), 791 ContentProvider.getUriWithoutUserId(uri), false); 792 } 793 } 794 795 CoreSettingsObserver mCoreSettingsObserver; 796 797 /** 798 * Thread-local storage used to carry caller permissions over through 799 * indirect content-provider access. 800 */ 801 private class Identity { 802 public int pid; 803 public int uid; 804 805 Identity(int _pid, int _uid) { 806 pid = _pid; 807 uid = _uid; 808 } 809 } 810 811 private static final ThreadLocal<Identity> sCallerIdentity = new ThreadLocal<Identity>(); 812 813 /** 814 * All information we have collected about the runtime performance of 815 * any user id that can impact battery performance. 816 */ 817 final BatteryStatsService mBatteryStatsService; 818 819 /** 820 * Information about component usage 821 */ 822 UsageStatsManagerInternal mUsageStatsService; 823 824 /** 825 * Information about and control over application operations 826 */ 827 final AppOpsService mAppOpsService; 828 829 /** 830 * Save recent tasks information across reboots. 831 */ 832 final TaskPersister mTaskPersister; 833 834 /** 835 * Current configuration information. HistoryRecord objects are given 836 * a reference to this object to indicate which configuration they are 837 * currently running in, so this object must be kept immutable. 838 */ 839 Configuration mConfiguration = new Configuration(); 840 841 /** 842 * Current sequencing integer of the configuration, for skipping old 843 * configurations. 844 */ 845 int mConfigurationSeq = 0; 846 847 /** 848 * Hardware-reported OpenGLES version. 849 */ 850 final int GL_ES_VERSION; 851 852 /** 853 * List of initialization arguments to pass to all processes when binding applications to them. 854 * For example, references to the commonly used services. 855 */ 856 HashMap<String, IBinder> mAppBindArgs; 857 858 /** 859 * Temporary to avoid allocations. Protected by main lock. 860 */ 861 final StringBuilder mStringBuilder = new StringBuilder(256); 862 863 /** 864 * Used to control how we initialize the service. 865 */ 866 ComponentName mTopComponent; 867 String mTopAction = Intent.ACTION_MAIN; 868 String mTopData; 869 boolean mProcessesReady = false; 870 boolean mSystemReady = false; 871 boolean mBooting = false; 872 boolean mWaitingUpdate = false; 873 boolean mDidUpdate = false; 874 boolean mOnBattery = false; 875 boolean mLaunchWarningShown = false; 876 877 Context mContext; 878 879 int mFactoryTest; 880 881 boolean mCheckedForSetup; 882 883 /** 884 * The time at which we will allow normal application switches again, 885 * after a call to {@link #stopAppSwitches()}. 886 */ 887 long mAppSwitchesAllowedTime; 888 889 /** 890 * This is set to true after the first switch after mAppSwitchesAllowedTime 891 * is set; any switches after that will clear the time. 892 */ 893 boolean mDidAppSwitch; 894 895 /** 896 * Last time (in realtime) at which we checked for power usage. 897 */ 898 long mLastPowerCheckRealtime; 899 900 /** 901 * Last time (in uptime) at which we checked for power usage. 902 */ 903 long mLastPowerCheckUptime; 904 905 /** 906 * Set while we are wanting to sleep, to prevent any 907 * activities from being started/resumed. 908 */ 909 private boolean mSleeping = false; 910 911 /** 912 * Set while we are running a voice interaction. This overrides 913 * sleeping while it is active. 914 */ 915 private boolean mRunningVoice = false; 916 917 /** 918 * State of external calls telling us if the device is asleep. 919 */ 920 private boolean mWentToSleep = false; 921 922 /** 923 * State of external call telling us if the lock screen is shown. 924 */ 925 private boolean mLockScreenShown = false; 926 927 /** 928 * Set if we are shutting down the system, similar to sleeping. 929 */ 930 boolean mShuttingDown = false; 931 932 /** 933 * Current sequence id for oom_adj computation traversal. 934 */ 935 int mAdjSeq = 0; 936 937 /** 938 * Current sequence id for process LRU updating. 939 */ 940 int mLruSeq = 0; 941 942 /** 943 * Keep track of the non-cached/empty process we last found, to help 944 * determine how to distribute cached/empty processes next time. 945 */ 946 int mNumNonCachedProcs = 0; 947 948 /** 949 * Keep track of the number of cached hidden procs, to balance oom adj 950 * distribution between those and empty procs. 951 */ 952 int mNumCachedHiddenProcs = 0; 953 954 /** 955 * Keep track of the number of service processes we last found, to 956 * determine on the next iteration which should be B services. 957 */ 958 int mNumServiceProcs = 0; 959 int mNewNumAServiceProcs = 0; 960 int mNewNumServiceProcs = 0; 961 962 /** 963 * Allow the current computed overall memory level of the system to go down? 964 * This is set to false when we are killing processes for reasons other than 965 * memory management, so that the now smaller process list will not be taken as 966 * an indication that memory is tighter. 967 */ 968 boolean mAllowLowerMemLevel = false; 969 970 /** 971 * The last computed memory level, for holding when we are in a state that 972 * processes are going away for other reasons. 973 */ 974 int mLastMemoryLevel = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 975 976 /** 977 * The last total number of process we have, to determine if changes actually look 978 * like a shrinking number of process due to lower RAM. 979 */ 980 int mLastNumProcesses; 981 982 /** 983 * The uptime of the last time we performed idle maintenance. 984 */ 985 long mLastIdleTime = SystemClock.uptimeMillis(); 986 987 /** 988 * Total time spent with RAM that has been added in the past since the last idle time. 989 */ 990 long mLowRamTimeSinceLastIdle = 0; 991 992 /** 993 * If RAM is currently low, when that horrible situation started. 994 */ 995 long mLowRamStartTime = 0; 996 997 /** 998 * For reporting to battery stats the current top application. 999 */ 1000 private String mCurResumedPackage = null; 1001 private int mCurResumedUid = -1; 1002 1003 /** 1004 * For reporting to battery stats the apps currently running foreground 1005 * service. The ProcessMap is package/uid tuples; each of these contain 1006 * an array of the currently foreground processes. 1007 */ 1008 final ProcessMap<ArrayList<ProcessRecord>> mForegroundPackages 1009 = new ProcessMap<ArrayList<ProcessRecord>>(); 1010 1011 /** 1012 * This is set if we had to do a delayed dexopt of an app before launching 1013 * it, to increase the ANR timeouts in that case. 1014 */ 1015 boolean mDidDexOpt; 1016 1017 /** 1018 * Set if the systemServer made a call to enterSafeMode. 1019 */ 1020 boolean mSafeMode; 1021 1022 String mDebugApp = null; 1023 boolean mWaitForDebugger = false; 1024 boolean mDebugTransient = false; 1025 String mOrigDebugApp = null; 1026 boolean mOrigWaitForDebugger = false; 1027 boolean mAlwaysFinishActivities = false; 1028 IActivityController mController = null; 1029 String mProfileApp = null; 1030 ProcessRecord mProfileProc = null; 1031 String mProfileFile; 1032 ParcelFileDescriptor mProfileFd; 1033 int mProfileType = 0; 1034 boolean mAutoStopProfiler = false; 1035 String mOpenGlTraceApp = null; 1036 1037 static class ProcessChangeItem { 1038 static final int CHANGE_ACTIVITIES = 1<<0; 1039 static final int CHANGE_PROCESS_STATE = 1<<1; 1040 int changes; 1041 int uid; 1042 int pid; 1043 int processState; 1044 boolean foregroundActivities; 1045 } 1046 1047 final RemoteCallbackList<IProcessObserver> mProcessObservers 1048 = new RemoteCallbackList<IProcessObserver>(); 1049 ProcessChangeItem[] mActiveProcessChanges = new ProcessChangeItem[5]; 1050 1051 final ArrayList<ProcessChangeItem> mPendingProcessChanges 1052 = new ArrayList<ProcessChangeItem>(); 1053 final ArrayList<ProcessChangeItem> mAvailProcessChanges 1054 = new ArrayList<ProcessChangeItem>(); 1055 1056 /** 1057 * Runtime CPU use collection thread. This object's lock is used to 1058 * protect all related state. 1059 */ 1060 final Thread mProcessCpuThread; 1061 1062 /** 1063 * Used to collect process stats when showing not responding dialog. 1064 * Protected by mProcessCpuThread. 1065 */ 1066 final ProcessCpuTracker mProcessCpuTracker = new ProcessCpuTracker( 1067 MONITOR_THREAD_CPU_USAGE); 1068 final AtomicLong mLastCpuTime = new AtomicLong(0); 1069 final AtomicBoolean mProcessCpuMutexFree = new AtomicBoolean(true); 1070 1071 long mLastWriteTime = 0; 1072 1073 /** 1074 * Used to retain an update lock when the foreground activity is in 1075 * immersive mode. 1076 */ 1077 final UpdateLock mUpdateLock = new UpdateLock("immersive"); 1078 1079 /** 1080 * Set to true after the system has finished booting. 1081 */ 1082 boolean mBooted = false; 1083 1084 int mProcessLimit = ProcessList.MAX_CACHED_APPS; 1085 int mProcessLimitOverride = -1; 1086 1087 WindowManagerService mWindowManager; 1088 1089 final ActivityThread mSystemThread; 1090 1091 int mCurrentUserId = 0; 1092 int[] mCurrentProfileIds = new int[] {UserHandle.USER_OWNER}; // Accessed by ActivityStack 1093 1094 /** 1095 * Mapping from each known user ID to the profile group ID it is associated with. 1096 */ 1097 SparseIntArray mUserProfileGroupIdsSelfLocked = new SparseIntArray(); 1098 1099 private UserManagerService mUserManager; 1100 1101 private final class AppDeathRecipient implements IBinder.DeathRecipient { 1102 final ProcessRecord mApp; 1103 final int mPid; 1104 final IApplicationThread mAppThread; 1105 1106 AppDeathRecipient(ProcessRecord app, int pid, 1107 IApplicationThread thread) { 1108 if (localLOGV) Slog.v( 1109 TAG, "New death recipient " + this 1110 + " for thread " + thread.asBinder()); 1111 mApp = app; 1112 mPid = pid; 1113 mAppThread = thread; 1114 } 1115 1116 @Override 1117 public void binderDied() { 1118 if (localLOGV) Slog.v( 1119 TAG, "Death received in " + this 1120 + " for thread " + mAppThread.asBinder()); 1121 synchronized(ActivityManagerService.this) { 1122 appDiedLocked(mApp, mPid, mAppThread); 1123 } 1124 } 1125 } 1126 1127 static final int SHOW_ERROR_MSG = 1; 1128 static final int SHOW_NOT_RESPONDING_MSG = 2; 1129 static final int SHOW_FACTORY_ERROR_MSG = 3; 1130 static final int UPDATE_CONFIGURATION_MSG = 4; 1131 static final int GC_BACKGROUND_PROCESSES_MSG = 5; 1132 static final int WAIT_FOR_DEBUGGER_MSG = 6; 1133 static final int SERVICE_TIMEOUT_MSG = 12; 1134 static final int UPDATE_TIME_ZONE = 13; 1135 static final int SHOW_UID_ERROR_MSG = 14; 1136 static final int IM_FEELING_LUCKY_MSG = 15; 1137 static final int PROC_START_TIMEOUT_MSG = 20; 1138 static final int DO_PENDING_ACTIVITY_LAUNCHES_MSG = 21; 1139 static final int KILL_APPLICATION_MSG = 22; 1140 static final int FINALIZE_PENDING_INTENT_MSG = 23; 1141 static final int POST_HEAVY_NOTIFICATION_MSG = 24; 1142 static final int CANCEL_HEAVY_NOTIFICATION_MSG = 25; 1143 static final int SHOW_STRICT_MODE_VIOLATION_MSG = 26; 1144 static final int CHECK_EXCESSIVE_WAKE_LOCKS_MSG = 27; 1145 static final int CLEAR_DNS_CACHE_MSG = 28; 1146 static final int UPDATE_HTTP_PROXY_MSG = 29; 1147 static final int SHOW_COMPAT_MODE_DIALOG_MSG = 30; 1148 static final int DISPATCH_PROCESSES_CHANGED = 31; 1149 static final int DISPATCH_PROCESS_DIED = 32; 1150 static final int REPORT_MEM_USAGE_MSG = 33; 1151 static final int REPORT_USER_SWITCH_MSG = 34; 1152 static final int CONTINUE_USER_SWITCH_MSG = 35; 1153 static final int USER_SWITCH_TIMEOUT_MSG = 36; 1154 static final int IMMERSIVE_MODE_LOCK_MSG = 37; 1155 static final int PERSIST_URI_GRANTS_MSG = 38; 1156 static final int REQUEST_ALL_PSS_MSG = 39; 1157 static final int START_PROFILES_MSG = 40; 1158 static final int UPDATE_TIME = 41; 1159 static final int SYSTEM_USER_START_MSG = 42; 1160 static final int SYSTEM_USER_CURRENT_MSG = 43; 1161 static final int ENTER_ANIMATION_COMPLETE_MSG = 44; 1162 static final int ENABLE_SCREEN_AFTER_BOOT_MSG = 45; 1163 1164 static final int FIRST_ACTIVITY_STACK_MSG = 100; 1165 static final int FIRST_BROADCAST_QUEUE_MSG = 200; 1166 static final int FIRST_COMPAT_MODE_MSG = 300; 1167 static final int FIRST_SUPERVISOR_STACK_MSG = 100; 1168 1169 AlertDialog mUidAlert; 1170 CompatModeDialog mCompatModeDialog; 1171 long mLastMemUsageReportTime = 0; 1172 1173 private LockToAppRequestDialog mLockToAppRequest; 1174 1175 /** 1176 * Flag whether the current user is a "monkey", i.e. whether 1177 * the UI is driven by a UI automation tool. 1178 */ 1179 private boolean mUserIsMonkey; 1180 1181 /** Flag whether the device has a recents UI */ 1182 final boolean mHasRecents; 1183 1184 final ServiceThread mHandlerThread; 1185 final MainHandler mHandler; 1186 1187 final class MainHandler extends Handler { 1188 public MainHandler(Looper looper) { 1189 super(looper, null, true); 1190 } 1191 1192 @Override 1193 public void handleMessage(Message msg) { 1194 switch (msg.what) { 1195 case SHOW_ERROR_MSG: { 1196 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1197 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 1198 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 1199 synchronized (ActivityManagerService.this) { 1200 ProcessRecord proc = (ProcessRecord)data.get("app"); 1201 AppErrorResult res = (AppErrorResult) data.get("result"); 1202 if (proc != null && proc.crashDialog != null) { 1203 Slog.e(TAG, "App already has crash dialog: " + proc); 1204 if (res != null) { 1205 res.set(0); 1206 } 1207 return; 1208 } 1209 boolean isBackground = (UserHandle.getAppId(proc.uid) 1210 >= Process.FIRST_APPLICATION_UID 1211 && proc.pid != MY_PID); 1212 for (int userId : mCurrentProfileIds) { 1213 isBackground &= (proc.userId != userId); 1214 } 1215 if (isBackground && !showBackground) { 1216 Slog.w(TAG, "Skipping crash dialog of " + proc + ": background"); 1217 if (res != null) { 1218 res.set(0); 1219 } 1220 return; 1221 } 1222 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1223 Dialog d = new AppErrorDialog(mContext, 1224 ActivityManagerService.this, res, proc); 1225 d.show(); 1226 proc.crashDialog = d; 1227 } else { 1228 // The device is asleep, so just pretend that the user 1229 // saw a crash dialog and hit "force quit". 1230 if (res != null) { 1231 res.set(0); 1232 } 1233 } 1234 } 1235 1236 ensureBootCompleted(); 1237 } break; 1238 case SHOW_NOT_RESPONDING_MSG: { 1239 synchronized (ActivityManagerService.this) { 1240 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1241 ProcessRecord proc = (ProcessRecord)data.get("app"); 1242 if (proc != null && proc.anrDialog != null) { 1243 Slog.e(TAG, "App already has anr dialog: " + proc); 1244 return; 1245 } 1246 1247 Intent intent = new Intent("android.intent.action.ANR"); 1248 if (!mProcessesReady) { 1249 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 1250 | Intent.FLAG_RECEIVER_FOREGROUND); 1251 } 1252 broadcastIntentLocked(null, null, intent, 1253 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 1254 false, false, MY_PID, Process.SYSTEM_UID, 0 /* TODO: Verify */); 1255 1256 if (mShowDialogs) { 1257 Dialog d = new AppNotRespondingDialog(ActivityManagerService.this, 1258 mContext, proc, (ActivityRecord)data.get("activity"), 1259 msg.arg1 != 0); 1260 d.show(); 1261 proc.anrDialog = d; 1262 } else { 1263 // Just kill the app if there is no dialog to be shown. 1264 killAppAtUsersRequest(proc, null); 1265 } 1266 } 1267 1268 ensureBootCompleted(); 1269 } break; 1270 case SHOW_STRICT_MODE_VIOLATION_MSG: { 1271 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1272 synchronized (ActivityManagerService.this) { 1273 ProcessRecord proc = (ProcessRecord) data.get("app"); 1274 if (proc == null) { 1275 Slog.e(TAG, "App not found when showing strict mode dialog."); 1276 break; 1277 } 1278 if (proc.crashDialog != null) { 1279 Slog.e(TAG, "App already has strict mode dialog: " + proc); 1280 return; 1281 } 1282 AppErrorResult res = (AppErrorResult) data.get("result"); 1283 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1284 Dialog d = new StrictModeViolationDialog(mContext, 1285 ActivityManagerService.this, res, proc); 1286 d.show(); 1287 proc.crashDialog = d; 1288 } else { 1289 // The device is asleep, so just pretend that the user 1290 // saw a crash dialog and hit "force quit". 1291 res.set(0); 1292 } 1293 } 1294 ensureBootCompleted(); 1295 } break; 1296 case SHOW_FACTORY_ERROR_MSG: { 1297 Dialog d = new FactoryErrorDialog( 1298 mContext, msg.getData().getCharSequence("msg")); 1299 d.show(); 1300 ensureBootCompleted(); 1301 } break; 1302 case UPDATE_CONFIGURATION_MSG: { 1303 final ContentResolver resolver = mContext.getContentResolver(); 1304 Settings.System.putConfiguration(resolver, (Configuration)msg.obj); 1305 } break; 1306 case GC_BACKGROUND_PROCESSES_MSG: { 1307 synchronized (ActivityManagerService.this) { 1308 performAppGcsIfAppropriateLocked(); 1309 } 1310 } break; 1311 case WAIT_FOR_DEBUGGER_MSG: { 1312 synchronized (ActivityManagerService.this) { 1313 ProcessRecord app = (ProcessRecord)msg.obj; 1314 if (msg.arg1 != 0) { 1315 if (!app.waitedForDebugger) { 1316 Dialog d = new AppWaitingForDebuggerDialog( 1317 ActivityManagerService.this, 1318 mContext, app); 1319 app.waitDialog = d; 1320 app.waitedForDebugger = true; 1321 d.show(); 1322 } 1323 } else { 1324 if (app.waitDialog != null) { 1325 app.waitDialog.dismiss(); 1326 app.waitDialog = null; 1327 } 1328 } 1329 } 1330 } break; 1331 case SERVICE_TIMEOUT_MSG: { 1332 if (mDidDexOpt) { 1333 mDidDexOpt = false; 1334 Message nmsg = mHandler.obtainMessage(SERVICE_TIMEOUT_MSG); 1335 nmsg.obj = msg.obj; 1336 mHandler.sendMessageDelayed(nmsg, ActiveServices.SERVICE_TIMEOUT); 1337 return; 1338 } 1339 mServices.serviceTimeout((ProcessRecord)msg.obj); 1340 } break; 1341 case UPDATE_TIME_ZONE: { 1342 synchronized (ActivityManagerService.this) { 1343 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1344 ProcessRecord r = mLruProcesses.get(i); 1345 if (r.thread != null) { 1346 try { 1347 r.thread.updateTimeZone(); 1348 } catch (RemoteException ex) { 1349 Slog.w(TAG, "Failed to update time zone for: " + r.info.processName); 1350 } 1351 } 1352 } 1353 } 1354 } break; 1355 case CLEAR_DNS_CACHE_MSG: { 1356 synchronized (ActivityManagerService.this) { 1357 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1358 ProcessRecord r = mLruProcesses.get(i); 1359 if (r.thread != null) { 1360 try { 1361 r.thread.clearDnsCache(); 1362 } catch (RemoteException ex) { 1363 Slog.w(TAG, "Failed to clear dns cache for: " + r.info.processName); 1364 } 1365 } 1366 } 1367 } 1368 } break; 1369 case UPDATE_HTTP_PROXY_MSG: { 1370 ProxyInfo proxy = (ProxyInfo)msg.obj; 1371 String host = ""; 1372 String port = ""; 1373 String exclList = ""; 1374 Uri pacFileUrl = Uri.EMPTY; 1375 if (proxy != null) { 1376 host = proxy.getHost(); 1377 port = Integer.toString(proxy.getPort()); 1378 exclList = proxy.getExclusionListAsString(); 1379 pacFileUrl = proxy.getPacFileUrl(); 1380 } 1381 synchronized (ActivityManagerService.this) { 1382 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1383 ProcessRecord r = mLruProcesses.get(i); 1384 if (r.thread != null) { 1385 try { 1386 r.thread.setHttpProxy(host, port, exclList, pacFileUrl); 1387 } catch (RemoteException ex) { 1388 Slog.w(TAG, "Failed to update http proxy for: " + 1389 r.info.processName); 1390 } 1391 } 1392 } 1393 } 1394 } break; 1395 case SHOW_UID_ERROR_MSG: { 1396 String title = "System UIDs Inconsistent"; 1397 String text = "UIDs on the system are inconsistent, you need to wipe your" 1398 + " data partition or your device will be unstable."; 1399 Log.e(TAG, title + ": " + text); 1400 if (mShowDialogs) { 1401 // XXX This is a temporary dialog, no need to localize. 1402 AlertDialog d = new BaseErrorDialog(mContext); 1403 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 1404 d.setCancelable(false); 1405 d.setTitle(title); 1406 d.setMessage(text); 1407 d.setButton(DialogInterface.BUTTON_POSITIVE, "I'm Feeling Lucky", 1408 mHandler.obtainMessage(IM_FEELING_LUCKY_MSG)); 1409 mUidAlert = d; 1410 d.show(); 1411 } 1412 } break; 1413 case IM_FEELING_LUCKY_MSG: { 1414 if (mUidAlert != null) { 1415 mUidAlert.dismiss(); 1416 mUidAlert = null; 1417 } 1418 } break; 1419 case PROC_START_TIMEOUT_MSG: { 1420 if (mDidDexOpt) { 1421 mDidDexOpt = false; 1422 Message nmsg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 1423 nmsg.obj = msg.obj; 1424 mHandler.sendMessageDelayed(nmsg, PROC_START_TIMEOUT); 1425 return; 1426 } 1427 ProcessRecord app = (ProcessRecord)msg.obj; 1428 synchronized (ActivityManagerService.this) { 1429 processStartTimedOutLocked(app); 1430 } 1431 } break; 1432 case DO_PENDING_ACTIVITY_LAUNCHES_MSG: { 1433 synchronized (ActivityManagerService.this) { 1434 mStackSupervisor.doPendingActivityLaunchesLocked(true); 1435 } 1436 } break; 1437 case KILL_APPLICATION_MSG: { 1438 synchronized (ActivityManagerService.this) { 1439 int appid = msg.arg1; 1440 boolean restart = (msg.arg2 == 1); 1441 Bundle bundle = (Bundle)msg.obj; 1442 String pkg = bundle.getString("pkg"); 1443 String reason = bundle.getString("reason"); 1444 forceStopPackageLocked(pkg, appid, restart, false, true, false, 1445 false, UserHandle.USER_ALL, reason); 1446 } 1447 } break; 1448 case FINALIZE_PENDING_INTENT_MSG: { 1449 ((PendingIntentRecord)msg.obj).completeFinalize(); 1450 } break; 1451 case POST_HEAVY_NOTIFICATION_MSG: { 1452 INotificationManager inm = NotificationManager.getService(); 1453 if (inm == null) { 1454 return; 1455 } 1456 1457 ActivityRecord root = (ActivityRecord)msg.obj; 1458 ProcessRecord process = root.app; 1459 if (process == null) { 1460 return; 1461 } 1462 1463 try { 1464 Context context = mContext.createPackageContext(process.info.packageName, 0); 1465 String text = mContext.getString(R.string.heavy_weight_notification, 1466 context.getApplicationInfo().loadLabel(context.getPackageManager())); 1467 Notification notification = new Notification(); 1468 notification.icon = com.android.internal.R.drawable.stat_sys_adb; //context.getApplicationInfo().icon; 1469 notification.when = 0; 1470 notification.flags = Notification.FLAG_ONGOING_EVENT; 1471 notification.tickerText = text; 1472 notification.defaults = 0; // please be quiet 1473 notification.sound = null; 1474 notification.vibrate = null; 1475 notification.setLatestEventInfo(context, text, 1476 mContext.getText(R.string.heavy_weight_notification_detail), 1477 PendingIntent.getActivityAsUser(mContext, 0, root.intent, 1478 PendingIntent.FLAG_CANCEL_CURRENT, null, 1479 new UserHandle(root.userId))); 1480 1481 try { 1482 int[] outId = new int[1]; 1483 inm.enqueueNotificationWithTag("android", "android", null, 1484 R.string.heavy_weight_notification, 1485 notification, outId, root.userId); 1486 } catch (RuntimeException e) { 1487 Slog.w(ActivityManagerService.TAG, 1488 "Error showing notification for heavy-weight app", e); 1489 } catch (RemoteException e) { 1490 } 1491 } catch (NameNotFoundException e) { 1492 Slog.w(TAG, "Unable to create context for heavy notification", e); 1493 } 1494 } break; 1495 case CANCEL_HEAVY_NOTIFICATION_MSG: { 1496 INotificationManager inm = NotificationManager.getService(); 1497 if (inm == null) { 1498 return; 1499 } 1500 try { 1501 inm.cancelNotificationWithTag("android", null, 1502 R.string.heavy_weight_notification, msg.arg1); 1503 } catch (RuntimeException e) { 1504 Slog.w(ActivityManagerService.TAG, 1505 "Error canceling notification for service", e); 1506 } catch (RemoteException e) { 1507 } 1508 } break; 1509 case CHECK_EXCESSIVE_WAKE_LOCKS_MSG: { 1510 synchronized (ActivityManagerService.this) { 1511 checkExcessivePowerUsageLocked(true); 1512 removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1513 Message nmsg = obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1514 sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 1515 } 1516 } break; 1517 case SHOW_COMPAT_MODE_DIALOG_MSG: { 1518 synchronized (ActivityManagerService.this) { 1519 ActivityRecord ar = (ActivityRecord)msg.obj; 1520 if (mCompatModeDialog != null) { 1521 if (mCompatModeDialog.mAppInfo.packageName.equals( 1522 ar.info.applicationInfo.packageName)) { 1523 return; 1524 } 1525 mCompatModeDialog.dismiss(); 1526 mCompatModeDialog = null; 1527 } 1528 if (ar != null && false) { 1529 if (mCompatModePackages.getPackageAskCompatModeLocked( 1530 ar.packageName)) { 1531 int mode = mCompatModePackages.computeCompatModeLocked( 1532 ar.info.applicationInfo); 1533 if (mode == ActivityManager.COMPAT_MODE_DISABLED 1534 || mode == ActivityManager.COMPAT_MODE_ENABLED) { 1535 mCompatModeDialog = new CompatModeDialog( 1536 ActivityManagerService.this, mContext, 1537 ar.info.applicationInfo); 1538 mCompatModeDialog.show(); 1539 } 1540 } 1541 } 1542 } 1543 break; 1544 } 1545 case DISPATCH_PROCESSES_CHANGED: { 1546 dispatchProcessesChanged(); 1547 break; 1548 } 1549 case DISPATCH_PROCESS_DIED: { 1550 final int pid = msg.arg1; 1551 final int uid = msg.arg2; 1552 dispatchProcessDied(pid, uid); 1553 break; 1554 } 1555 case REPORT_MEM_USAGE_MSG: { 1556 final ArrayList<ProcessMemInfo> memInfos = (ArrayList<ProcessMemInfo>)msg.obj; 1557 Thread thread = new Thread() { 1558 @Override public void run() { 1559 final SparseArray<ProcessMemInfo> infoMap 1560 = new SparseArray<ProcessMemInfo>(memInfos.size()); 1561 for (int i=0, N=memInfos.size(); i<N; i++) { 1562 ProcessMemInfo mi = memInfos.get(i); 1563 infoMap.put(mi.pid, mi); 1564 } 1565 updateCpuStatsNow(); 1566 synchronized (mProcessCpuThread) { 1567 final int N = mProcessCpuTracker.countStats(); 1568 for (int i=0; i<N; i++) { 1569 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 1570 if (st.vsize > 0) { 1571 long pss = Debug.getPss(st.pid, null); 1572 if (pss > 0) { 1573 if (infoMap.indexOfKey(st.pid) < 0) { 1574 ProcessMemInfo mi = new ProcessMemInfo(st.name, st.pid, 1575 ProcessList.NATIVE_ADJ, -1, "native", null); 1576 mi.pss = pss; 1577 memInfos.add(mi); 1578 } 1579 } 1580 } 1581 } 1582 } 1583 1584 long totalPss = 0; 1585 for (int i=0, N=memInfos.size(); i<N; i++) { 1586 ProcessMemInfo mi = memInfos.get(i); 1587 if (mi.pss == 0) { 1588 mi.pss = Debug.getPss(mi.pid, null); 1589 } 1590 totalPss += mi.pss; 1591 } 1592 Collections.sort(memInfos, new Comparator<ProcessMemInfo>() { 1593 @Override public int compare(ProcessMemInfo lhs, ProcessMemInfo rhs) { 1594 if (lhs.oomAdj != rhs.oomAdj) { 1595 return lhs.oomAdj < rhs.oomAdj ? -1 : 1; 1596 } 1597 if (lhs.pss != rhs.pss) { 1598 return lhs.pss < rhs.pss ? 1 : -1; 1599 } 1600 return 0; 1601 } 1602 }); 1603 1604 StringBuilder tag = new StringBuilder(128); 1605 StringBuilder stack = new StringBuilder(128); 1606 tag.append("Low on memory -- "); 1607 appendMemBucket(tag, totalPss, "total", false); 1608 appendMemBucket(stack, totalPss, "total", true); 1609 1610 StringBuilder logBuilder = new StringBuilder(1024); 1611 logBuilder.append("Low on memory:\n"); 1612 1613 boolean firstLine = true; 1614 int lastOomAdj = Integer.MIN_VALUE; 1615 for (int i=0, N=memInfos.size(); i<N; i++) { 1616 ProcessMemInfo mi = memInfos.get(i); 1617 1618 if (mi.oomAdj != ProcessList.NATIVE_ADJ 1619 && (mi.oomAdj < ProcessList.SERVICE_ADJ 1620 || mi.oomAdj == ProcessList.HOME_APP_ADJ 1621 || mi.oomAdj == ProcessList.PREVIOUS_APP_ADJ)) { 1622 if (lastOomAdj != mi.oomAdj) { 1623 lastOomAdj = mi.oomAdj; 1624 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1625 tag.append(" / "); 1626 } 1627 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ) { 1628 if (firstLine) { 1629 stack.append(":"); 1630 firstLine = false; 1631 } 1632 stack.append("\n\t at "); 1633 } else { 1634 stack.append("$"); 1635 } 1636 } else { 1637 tag.append(" "); 1638 stack.append("$"); 1639 } 1640 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1641 appendMemBucket(tag, mi.pss, mi.name, false); 1642 } 1643 appendMemBucket(stack, mi.pss, mi.name, true); 1644 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ 1645 && ((i+1) >= N || memInfos.get(i+1).oomAdj != lastOomAdj)) { 1646 stack.append("("); 1647 for (int k=0; k<DUMP_MEM_OOM_ADJ.length; k++) { 1648 if (DUMP_MEM_OOM_ADJ[k] == mi.oomAdj) { 1649 stack.append(DUMP_MEM_OOM_LABEL[k]); 1650 stack.append(":"); 1651 stack.append(DUMP_MEM_OOM_ADJ[k]); 1652 } 1653 } 1654 stack.append(")"); 1655 } 1656 } 1657 1658 logBuilder.append(" "); 1659 logBuilder.append(ProcessList.makeOomAdjString(mi.oomAdj)); 1660 logBuilder.append(' '); 1661 logBuilder.append(ProcessList.makeProcStateString(mi.procState)); 1662 logBuilder.append(' '); 1663 ProcessList.appendRamKb(logBuilder, mi.pss); 1664 logBuilder.append(" kB: "); 1665 logBuilder.append(mi.name); 1666 logBuilder.append(" ("); 1667 logBuilder.append(mi.pid); 1668 logBuilder.append(") "); 1669 logBuilder.append(mi.adjType); 1670 logBuilder.append('\n'); 1671 if (mi.adjReason != null) { 1672 logBuilder.append(" "); 1673 logBuilder.append(mi.adjReason); 1674 logBuilder.append('\n'); 1675 } 1676 } 1677 1678 logBuilder.append(" "); 1679 ProcessList.appendRamKb(logBuilder, totalPss); 1680 logBuilder.append(" kB: TOTAL\n"); 1681 1682 long[] infos = new long[Debug.MEMINFO_COUNT]; 1683 Debug.getMemInfo(infos); 1684 logBuilder.append(" MemInfo: "); 1685 logBuilder.append(infos[Debug.MEMINFO_SLAB]).append(" kB slab, "); 1686 logBuilder.append(infos[Debug.MEMINFO_SHMEM]).append(" kB shmem, "); 1687 logBuilder.append(infos[Debug.MEMINFO_BUFFERS]).append(" kB buffers, "); 1688 logBuilder.append(infos[Debug.MEMINFO_CACHED]).append(" kB cached, "); 1689 logBuilder.append(infos[Debug.MEMINFO_FREE]).append(" kB free\n"); 1690 if (infos[Debug.MEMINFO_ZRAM_TOTAL] != 0) { 1691 logBuilder.append(" ZRAM: "); 1692 logBuilder.append(infos[Debug.MEMINFO_ZRAM_TOTAL]); 1693 logBuilder.append(" kB RAM, "); 1694 logBuilder.append(infos[Debug.MEMINFO_SWAP_TOTAL]); 1695 logBuilder.append(" kB swap total, "); 1696 logBuilder.append(infos[Debug.MEMINFO_SWAP_FREE]); 1697 logBuilder.append(" kB swap free\n"); 1698 } 1699 Slog.i(TAG, logBuilder.toString()); 1700 1701 StringBuilder dropBuilder = new StringBuilder(1024); 1702 /* 1703 StringWriter oomSw = new StringWriter(); 1704 PrintWriter oomPw = new FastPrintWriter(oomSw, false, 256); 1705 StringWriter catSw = new StringWriter(); 1706 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1707 String[] emptyArgs = new String[] { }; 1708 dumpApplicationMemoryUsage(null, oomPw, " ", emptyArgs, true, catPw); 1709 oomPw.flush(); 1710 String oomString = oomSw.toString(); 1711 */ 1712 dropBuilder.append(stack); 1713 dropBuilder.append('\n'); 1714 dropBuilder.append('\n'); 1715 dropBuilder.append(logBuilder); 1716 dropBuilder.append('\n'); 1717 /* 1718 dropBuilder.append(oomString); 1719 dropBuilder.append('\n'); 1720 */ 1721 StringWriter catSw = new StringWriter(); 1722 synchronized (ActivityManagerService.this) { 1723 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1724 String[] emptyArgs = new String[] { }; 1725 catPw.println(); 1726 dumpProcessesLocked(null, catPw, emptyArgs, 0, false, null); 1727 catPw.println(); 1728 mServices.dumpServicesLocked(null, catPw, emptyArgs, 0, 1729 false, false, null); 1730 catPw.println(); 1731 dumpActivitiesLocked(null, catPw, emptyArgs, 0, false, false, null); 1732 catPw.flush(); 1733 } 1734 dropBuilder.append(catSw.toString()); 1735 addErrorToDropBox("lowmem", null, "system_server", null, 1736 null, tag.toString(), dropBuilder.toString(), null, null); 1737 //Slog.i(TAG, "Sent to dropbox:"); 1738 //Slog.i(TAG, dropBuilder.toString()); 1739 synchronized (ActivityManagerService.this) { 1740 long now = SystemClock.uptimeMillis(); 1741 if (mLastMemUsageReportTime < now) { 1742 mLastMemUsageReportTime = now; 1743 } 1744 } 1745 } 1746 }; 1747 thread.start(); 1748 break; 1749 } 1750 case REPORT_USER_SWITCH_MSG: { 1751 dispatchUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1752 break; 1753 } 1754 case CONTINUE_USER_SWITCH_MSG: { 1755 continueUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1756 break; 1757 } 1758 case USER_SWITCH_TIMEOUT_MSG: { 1759 timeoutUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1760 break; 1761 } 1762 case IMMERSIVE_MODE_LOCK_MSG: { 1763 final boolean nextState = (msg.arg1 != 0); 1764 if (mUpdateLock.isHeld() != nextState) { 1765 if (DEBUG_IMMERSIVE) { 1766 final ActivityRecord r = (ActivityRecord) msg.obj; 1767 Slog.d(TAG, "Applying new update lock state '" + nextState + "' for " + r); 1768 } 1769 if (nextState) { 1770 mUpdateLock.acquire(); 1771 } else { 1772 mUpdateLock.release(); 1773 } 1774 } 1775 break; 1776 } 1777 case PERSIST_URI_GRANTS_MSG: { 1778 writeGrantedUriPermissions(); 1779 break; 1780 } 1781 case REQUEST_ALL_PSS_MSG: { 1782 requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, false); 1783 break; 1784 } 1785 case START_PROFILES_MSG: { 1786 synchronized (ActivityManagerService.this) { 1787 startProfilesLocked(); 1788 } 1789 break; 1790 } 1791 case UPDATE_TIME: { 1792 synchronized (ActivityManagerService.this) { 1793 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1794 ProcessRecord r = mLruProcesses.get(i); 1795 if (r.thread != null) { 1796 try { 1797 r.thread.updateTimePrefs(msg.arg1 == 0 ? false : true); 1798 } catch (RemoteException ex) { 1799 Slog.w(TAG, "Failed to update preferences for: " + r.info.processName); 1800 } 1801 } 1802 } 1803 } 1804 break; 1805 } 1806 case SYSTEM_USER_START_MSG: { 1807 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 1808 Integer.toString(msg.arg1), msg.arg1); 1809 mSystemServiceManager.startUser(msg.arg1); 1810 break; 1811 } 1812 case SYSTEM_USER_CURRENT_MSG: { 1813 mBatteryStatsService.noteEvent( 1814 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_FINISH, 1815 Integer.toString(msg.arg2), msg.arg2); 1816 mBatteryStatsService.noteEvent( 1817 BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 1818 Integer.toString(msg.arg1), msg.arg1); 1819 mSystemServiceManager.switchUser(msg.arg1); 1820 break; 1821 } 1822 case ENTER_ANIMATION_COMPLETE_MSG: { 1823 synchronized (ActivityManagerService.this) { 1824 ActivityRecord r = ActivityRecord.forToken((IBinder) msg.obj); 1825 if (r != null && r.app != null && r.app.thread != null) { 1826 try { 1827 r.app.thread.scheduleEnterAnimationComplete(r.appToken); 1828 } catch (RemoteException e) { 1829 } 1830 } 1831 } 1832 break; 1833 } 1834 case ENABLE_SCREEN_AFTER_BOOT_MSG: { 1835 enableScreenAfterBoot(); 1836 break; 1837 } 1838 } 1839 } 1840 }; 1841 1842 static final int COLLECT_PSS_BG_MSG = 1; 1843 1844 final Handler mBgHandler = new Handler(BackgroundThread.getHandler().getLooper()) { 1845 @Override 1846 public void handleMessage(Message msg) { 1847 switch (msg.what) { 1848 case COLLECT_PSS_BG_MSG: { 1849 long start = SystemClock.uptimeMillis(); 1850 MemInfoReader memInfo = null; 1851 synchronized (ActivityManagerService.this) { 1852 if (mFullPssPending) { 1853 mFullPssPending = false; 1854 memInfo = new MemInfoReader(); 1855 } 1856 } 1857 if (memInfo != null) { 1858 updateCpuStatsNow(); 1859 long nativeTotalPss = 0; 1860 synchronized (mProcessCpuThread) { 1861 final int N = mProcessCpuTracker.countStats(); 1862 for (int j=0; j<N; j++) { 1863 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(j); 1864 if (st.vsize <= 0 || st.uid >= Process.FIRST_APPLICATION_UID) { 1865 // This is definitely an application process; skip it. 1866 continue; 1867 } 1868 synchronized (mPidsSelfLocked) { 1869 if (mPidsSelfLocked.indexOfKey(st.pid) >= 0) { 1870 // This is one of our own processes; skip it. 1871 continue; 1872 } 1873 } 1874 nativeTotalPss += Debug.getPss(st.pid, null); 1875 } 1876 } 1877 memInfo.readMemInfo(); 1878 synchronized (this) { 1879 if (DEBUG_PSS) Slog.d(TAG, "Collected native and kernel memory in " 1880 + (SystemClock.uptimeMillis()-start) + "ms"); 1881 mProcessStats.addSysMemUsageLocked(memInfo.getCachedSizeKb(), 1882 memInfo.getFreeSizeKb(), memInfo.getZramTotalSizeKb(), 1883 memInfo.getBuffersSizeKb()+memInfo.getShmemSizeKb() 1884 +memInfo.getSlabSizeKb(), 1885 nativeTotalPss); 1886 } 1887 } 1888 1889 int i=0, num=0; 1890 long[] tmp = new long[1]; 1891 do { 1892 ProcessRecord proc; 1893 int procState; 1894 int pid; 1895 synchronized (ActivityManagerService.this) { 1896 if (i >= mPendingPssProcesses.size()) { 1897 if (DEBUG_PSS) Slog.d(TAG, "Collected PSS of " + num + " of " + i 1898 + " processes in " + (SystemClock.uptimeMillis()-start) + "ms"); 1899 mPendingPssProcesses.clear(); 1900 return; 1901 } 1902 proc = mPendingPssProcesses.get(i); 1903 procState = proc.pssProcState; 1904 if (proc.thread != null && procState == proc.setProcState) { 1905 pid = proc.pid; 1906 } else { 1907 proc = null; 1908 pid = 0; 1909 } 1910 i++; 1911 } 1912 if (proc != null) { 1913 long pss = Debug.getPss(pid, tmp); 1914 synchronized (ActivityManagerService.this) { 1915 if (proc.thread != null && proc.setProcState == procState 1916 && proc.pid == pid) { 1917 num++; 1918 proc.lastPssTime = SystemClock.uptimeMillis(); 1919 proc.baseProcessTracker.addPss(pss, tmp[0], true, proc.pkgList); 1920 if (DEBUG_PSS) Slog.d(TAG, "PSS of " + proc.toShortString() 1921 + ": " + pss + " lastPss=" + proc.lastPss 1922 + " state=" + ProcessList.makeProcStateString(procState)); 1923 if (proc.initialIdlePss == 0) { 1924 proc.initialIdlePss = pss; 1925 } 1926 proc.lastPss = pss; 1927 if (procState >= ActivityManager.PROCESS_STATE_HOME) { 1928 proc.lastCachedPss = pss; 1929 } 1930 } 1931 } 1932 } 1933 } while (true); 1934 } 1935 } 1936 } 1937 }; 1938 1939 /** 1940 * Monitor for package changes and update our internal state. 1941 */ 1942 private final PackageMonitor mPackageMonitor = new PackageMonitor() { 1943 @Override 1944 public void onPackageRemoved(String packageName, int uid) { 1945 // Remove all tasks with activities in the specified package from the list of recent tasks 1946 synchronized (ActivityManagerService.this) { 1947 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 1948 TaskRecord tr = mRecentTasks.get(i); 1949 ComponentName cn = tr.intent.getComponent(); 1950 if (cn != null && cn.getPackageName().equals(packageName)) { 1951 // If the package name matches, remove the task and kill the process 1952 removeTaskByIdLocked(tr.taskId, ActivityManager.REMOVE_TASK_KILL_PROCESS); 1953 } 1954 } 1955 } 1956 } 1957 1958 @Override 1959 public boolean onPackageChanged(String packageName, int uid, String[] components) { 1960 onPackageModified(packageName); 1961 return true; 1962 } 1963 1964 @Override 1965 public void onPackageModified(String packageName) { 1966 final PackageManager pm = mContext.getPackageManager(); 1967 final ArrayList<Pair<Intent, Integer>> recentTaskIntents = 1968 new ArrayList<Pair<Intent, Integer>>(); 1969 final ArrayList<Integer> tasksToRemove = new ArrayList<Integer>(); 1970 // Copy the list of recent tasks so that we don't hold onto the lock on 1971 // ActivityManagerService for long periods while checking if components exist. 1972 synchronized (ActivityManagerService.this) { 1973 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 1974 TaskRecord tr = mRecentTasks.get(i); 1975 recentTaskIntents.add(new Pair<Intent, Integer>(tr.intent, tr.taskId)); 1976 } 1977 } 1978 // Check the recent tasks and filter out all tasks with components that no longer exist. 1979 Intent tmpI = new Intent(); 1980 for (int i = recentTaskIntents.size() - 1; i >= 0; i--) { 1981 Pair<Intent, Integer> p = recentTaskIntents.get(i); 1982 ComponentName cn = p.first.getComponent(); 1983 if (cn != null && cn.getPackageName().equals(packageName)) { 1984 try { 1985 // Add the task to the list to remove if the component no longer exists 1986 tmpI.setComponent(cn); 1987 if (pm.queryIntentActivities(tmpI, PackageManager.MATCH_DEFAULT_ONLY).isEmpty()) { 1988 tasksToRemove.add(p.second); 1989 } 1990 } catch (Exception e) {} 1991 } 1992 } 1993 // Prune all the tasks with removed components from the list of recent tasks 1994 synchronized (ActivityManagerService.this) { 1995 for (int i = tasksToRemove.size() - 1; i >= 0; i--) { 1996 // Remove the task but don't kill the process (since other components in that 1997 // package may still be running and in the background) 1998 removeTaskByIdLocked(tasksToRemove.get(i), 0); 1999 } 2000 } 2001 } 2002 2003 @Override 2004 public boolean onHandleForceStop(Intent intent, String[] packages, int uid, boolean doit) { 2005 // Force stop the specified packages 2006 if (packages != null) { 2007 for (String pkg : packages) { 2008 synchronized (ActivityManagerService.this) { 2009 if (forceStopPackageLocked(pkg, -1, false, false, false, false, false, 0, 2010 "finished booting")) { 2011 return true; 2012 } 2013 } 2014 } 2015 } 2016 return false; 2017 } 2018 }; 2019 2020 public void setSystemProcess() { 2021 try { 2022 ServiceManager.addService(Context.ACTIVITY_SERVICE, this, true); 2023 ServiceManager.addService(ProcessStats.SERVICE_NAME, mProcessStats); 2024 ServiceManager.addService("meminfo", new MemBinder(this)); 2025 ServiceManager.addService("gfxinfo", new GraphicsBinder(this)); 2026 ServiceManager.addService("dbinfo", new DbBinder(this)); 2027 if (MONITOR_CPU_USAGE) { 2028 ServiceManager.addService("cpuinfo", new CpuBinder(this)); 2029 } 2030 ServiceManager.addService("permission", new PermissionController(this)); 2031 2032 ApplicationInfo info = mContext.getPackageManager().getApplicationInfo( 2033 "android", STOCK_PM_FLAGS); 2034 mSystemThread.installSystemApplicationInfo(info); 2035 2036 synchronized (this) { 2037 ProcessRecord app = newProcessRecordLocked(info, info.processName, false, 0); 2038 app.persistent = true; 2039 app.pid = MY_PID; 2040 app.maxAdj = ProcessList.SYSTEM_ADJ; 2041 app.makeActive(mSystemThread.getApplicationThread(), mProcessStats); 2042 mProcessNames.put(app.processName, app.uid, app); 2043 synchronized (mPidsSelfLocked) { 2044 mPidsSelfLocked.put(app.pid, app); 2045 } 2046 updateLruProcessLocked(app, false, null); 2047 updateOomAdjLocked(); 2048 } 2049 } catch (PackageManager.NameNotFoundException e) { 2050 throw new RuntimeException( 2051 "Unable to find android system package", e); 2052 } 2053 } 2054 2055 public void setWindowManager(WindowManagerService wm) { 2056 mWindowManager = wm; 2057 mStackSupervisor.setWindowManager(wm); 2058 } 2059 2060 public void setUsageStatsManager(UsageStatsManagerInternal usageStatsManager) { 2061 mUsageStatsService = usageStatsManager; 2062 } 2063 2064 public void startObservingNativeCrashes() { 2065 final NativeCrashListener ncl = new NativeCrashListener(this); 2066 ncl.start(); 2067 } 2068 2069 public IAppOpsService getAppOpsService() { 2070 return mAppOpsService; 2071 } 2072 2073 static class MemBinder extends Binder { 2074 ActivityManagerService mActivityManagerService; 2075 MemBinder(ActivityManagerService activityManagerService) { 2076 mActivityManagerService = activityManagerService; 2077 } 2078 2079 @Override 2080 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2081 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2082 != PackageManager.PERMISSION_GRANTED) { 2083 pw.println("Permission Denial: can't dump meminfo from from pid=" 2084 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2085 + " without permission " + android.Manifest.permission.DUMP); 2086 return; 2087 } 2088 2089 mActivityManagerService.dumpApplicationMemoryUsage(fd, pw, " ", args, false, null); 2090 } 2091 } 2092 2093 static class GraphicsBinder extends Binder { 2094 ActivityManagerService mActivityManagerService; 2095 GraphicsBinder(ActivityManagerService activityManagerService) { 2096 mActivityManagerService = activityManagerService; 2097 } 2098 2099 @Override 2100 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2101 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2102 != PackageManager.PERMISSION_GRANTED) { 2103 pw.println("Permission Denial: can't dump gfxinfo from from pid=" 2104 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2105 + " without permission " + android.Manifest.permission.DUMP); 2106 return; 2107 } 2108 2109 mActivityManagerService.dumpGraphicsHardwareUsage(fd, pw, args); 2110 } 2111 } 2112 2113 static class DbBinder extends Binder { 2114 ActivityManagerService mActivityManagerService; 2115 DbBinder(ActivityManagerService activityManagerService) { 2116 mActivityManagerService = activityManagerService; 2117 } 2118 2119 @Override 2120 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2121 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2122 != PackageManager.PERMISSION_GRANTED) { 2123 pw.println("Permission Denial: can't dump dbinfo from from pid=" 2124 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2125 + " without permission " + android.Manifest.permission.DUMP); 2126 return; 2127 } 2128 2129 mActivityManagerService.dumpDbInfo(fd, pw, args); 2130 } 2131 } 2132 2133 static class CpuBinder extends Binder { 2134 ActivityManagerService mActivityManagerService; 2135 CpuBinder(ActivityManagerService activityManagerService) { 2136 mActivityManagerService = activityManagerService; 2137 } 2138 2139 @Override 2140 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2141 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2142 != PackageManager.PERMISSION_GRANTED) { 2143 pw.println("Permission Denial: can't dump cpuinfo from from pid=" 2144 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2145 + " without permission " + android.Manifest.permission.DUMP); 2146 return; 2147 } 2148 2149 synchronized (mActivityManagerService.mProcessCpuThread) { 2150 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentLoad()); 2151 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentState( 2152 SystemClock.uptimeMillis())); 2153 } 2154 } 2155 } 2156 2157 public static final class Lifecycle extends SystemService { 2158 private final ActivityManagerService mService; 2159 2160 public Lifecycle(Context context) { 2161 super(context); 2162 mService = new ActivityManagerService(context); 2163 } 2164 2165 @Override 2166 public void onStart() { 2167 mService.start(); 2168 } 2169 2170 public ActivityManagerService getService() { 2171 return mService; 2172 } 2173 } 2174 2175 // Note: This method is invoked on the main thread but may need to attach various 2176 // handlers to other threads. So take care to be explicit about the looper. 2177 public ActivityManagerService(Context systemContext) { 2178 mContext = systemContext; 2179 mFactoryTest = FactoryTest.getMode(); 2180 mSystemThread = ActivityThread.currentActivityThread(); 2181 2182 Slog.i(TAG, "Memory class: " + ActivityManager.staticGetMemoryClass()); 2183 2184 mHandlerThread = new ServiceThread(TAG, 2185 android.os.Process.THREAD_PRIORITY_FOREGROUND, false /*allowIo*/); 2186 mHandlerThread.start(); 2187 mHandler = new MainHandler(mHandlerThread.getLooper()); 2188 2189 mFgBroadcastQueue = new BroadcastQueue(this, mHandler, 2190 "foreground", BROADCAST_FG_TIMEOUT, false); 2191 mBgBroadcastQueue = new BroadcastQueue(this, mHandler, 2192 "background", BROADCAST_BG_TIMEOUT, true); 2193 mBroadcastQueues[0] = mFgBroadcastQueue; 2194 mBroadcastQueues[1] = mBgBroadcastQueue; 2195 2196 mServices = new ActiveServices(this); 2197 mProviderMap = new ProviderMap(this); 2198 2199 // TODO: Move creation of battery stats service outside of activity manager service. 2200 File dataDir = Environment.getDataDirectory(); 2201 File systemDir = new File(dataDir, "system"); 2202 systemDir.mkdirs(); 2203 mBatteryStatsService = new BatteryStatsService(systemDir, mHandler); 2204 mBatteryStatsService.getActiveStatistics().readLocked(); 2205 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2206 mOnBattery = DEBUG_POWER ? true 2207 : mBatteryStatsService.getActiveStatistics().getIsOnBattery(); 2208 mBatteryStatsService.getActiveStatistics().setCallback(this); 2209 2210 mProcessStats = new ProcessStatsService(this, new File(systemDir, "procstats")); 2211 2212 mAppOpsService = new AppOpsService(new File(systemDir, "appops.xml"), mHandler); 2213 2214 mGrantFile = new AtomicFile(new File(systemDir, "urigrants.xml")); 2215 2216 // User 0 is the first and only user that runs at boot. 2217 mStartedUsers.put(0, new UserStartedState(new UserHandle(0), true)); 2218 mUserLru.add(Integer.valueOf(0)); 2219 updateStartedUserArrayLocked(); 2220 2221 GL_ES_VERSION = SystemProperties.getInt("ro.opengles.version", 2222 ConfigurationInfo.GL_ES_VERSION_UNDEFINED); 2223 2224 mConfiguration.setToDefaults(); 2225 mConfiguration.setLocale(Locale.getDefault()); 2226 2227 mConfigurationSeq = mConfiguration.seq = 1; 2228 mProcessCpuTracker.init(); 2229 2230 mHasRecents = mContext.getResources().getBoolean( 2231 com.android.internal.R.bool.config_hasRecents); 2232 2233 mCompatModePackages = new CompatModePackages(this, systemDir, mHandler); 2234 mIntentFirewall = new IntentFirewall(new IntentFirewallInterface(), mHandler); 2235 mStackSupervisor = new ActivityStackSupervisor(this); 2236 mTaskPersister = new TaskPersister(systemDir, mStackSupervisor); 2237 2238 mProcessCpuThread = new Thread("CpuTracker") { 2239 @Override 2240 public void run() { 2241 while (true) { 2242 try { 2243 try { 2244 synchronized(this) { 2245 final long now = SystemClock.uptimeMillis(); 2246 long nextCpuDelay = (mLastCpuTime.get()+MONITOR_CPU_MAX_TIME)-now; 2247 long nextWriteDelay = (mLastWriteTime+BATTERY_STATS_TIME)-now; 2248 //Slog.i(TAG, "Cpu delay=" + nextCpuDelay 2249 // + ", write delay=" + nextWriteDelay); 2250 if (nextWriteDelay < nextCpuDelay) { 2251 nextCpuDelay = nextWriteDelay; 2252 } 2253 if (nextCpuDelay > 0) { 2254 mProcessCpuMutexFree.set(true); 2255 this.wait(nextCpuDelay); 2256 } 2257 } 2258 } catch (InterruptedException e) { 2259 } 2260 updateCpuStatsNow(); 2261 } catch (Exception e) { 2262 Slog.e(TAG, "Unexpected exception collecting process stats", e); 2263 } 2264 } 2265 } 2266 }; 2267 2268 mLockToAppRequest = new LockToAppRequestDialog(mContext, this); 2269 2270 Watchdog.getInstance().addMonitor(this); 2271 Watchdog.getInstance().addThread(mHandler); 2272 } 2273 2274 public void setSystemServiceManager(SystemServiceManager mgr) { 2275 mSystemServiceManager = mgr; 2276 } 2277 2278 private void start() { 2279 Process.removeAllProcessGroups(); 2280 mProcessCpuThread.start(); 2281 2282 mBatteryStatsService.publish(mContext); 2283 mAppOpsService.publish(mContext); 2284 Slog.d("AppOps", "AppOpsService published"); 2285 LocalServices.addService(ActivityManagerInternal.class, new LocalService()); 2286 } 2287 2288 public void initPowerManagement() { 2289 mStackSupervisor.initPowerManagement(); 2290 mBatteryStatsService.initPowerManagement(); 2291 } 2292 2293 @Override 2294 public boolean onTransact(int code, Parcel data, Parcel reply, int flags) 2295 throws RemoteException { 2296 if (code == SYSPROPS_TRANSACTION) { 2297 // We need to tell all apps about the system property change. 2298 ArrayList<IBinder> procs = new ArrayList<IBinder>(); 2299 synchronized(this) { 2300 final int NP = mProcessNames.getMap().size(); 2301 for (int ip=0; ip<NP; ip++) { 2302 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 2303 final int NA = apps.size(); 2304 for (int ia=0; ia<NA; ia++) { 2305 ProcessRecord app = apps.valueAt(ia); 2306 if (app.thread != null) { 2307 procs.add(app.thread.asBinder()); 2308 } 2309 } 2310 } 2311 } 2312 2313 int N = procs.size(); 2314 for (int i=0; i<N; i++) { 2315 Parcel data2 = Parcel.obtain(); 2316 try { 2317 procs.get(i).transact(IBinder.SYSPROPS_TRANSACTION, data2, null, 0); 2318 } catch (RemoteException e) { 2319 } 2320 data2.recycle(); 2321 } 2322 } 2323 try { 2324 return super.onTransact(code, data, reply, flags); 2325 } catch (RuntimeException e) { 2326 // The activity manager only throws security exceptions, so let's 2327 // log all others. 2328 if (!(e instanceof SecurityException)) { 2329 Slog.wtf(TAG, "Activity Manager Crash", e); 2330 } 2331 throw e; 2332 } 2333 } 2334 2335 void updateCpuStats() { 2336 final long now = SystemClock.uptimeMillis(); 2337 if (mLastCpuTime.get() >= now - MONITOR_CPU_MIN_TIME) { 2338 return; 2339 } 2340 if (mProcessCpuMutexFree.compareAndSet(true, false)) { 2341 synchronized (mProcessCpuThread) { 2342 mProcessCpuThread.notify(); 2343 } 2344 } 2345 } 2346 2347 void updateCpuStatsNow() { 2348 synchronized (mProcessCpuThread) { 2349 mProcessCpuMutexFree.set(false); 2350 final long now = SystemClock.uptimeMillis(); 2351 boolean haveNewCpuStats = false; 2352 2353 if (MONITOR_CPU_USAGE && 2354 mLastCpuTime.get() < (now-MONITOR_CPU_MIN_TIME)) { 2355 mLastCpuTime.set(now); 2356 haveNewCpuStats = true; 2357 mProcessCpuTracker.update(); 2358 //Slog.i(TAG, mProcessCpu.printCurrentState()); 2359 //Slog.i(TAG, "Total CPU usage: " 2360 // + mProcessCpu.getTotalCpuPercent() + "%"); 2361 2362 // Slog the cpu usage if the property is set. 2363 if ("true".equals(SystemProperties.get("events.cpu"))) { 2364 int user = mProcessCpuTracker.getLastUserTime(); 2365 int system = mProcessCpuTracker.getLastSystemTime(); 2366 int iowait = mProcessCpuTracker.getLastIoWaitTime(); 2367 int irq = mProcessCpuTracker.getLastIrqTime(); 2368 int softIrq = mProcessCpuTracker.getLastSoftIrqTime(); 2369 int idle = mProcessCpuTracker.getLastIdleTime(); 2370 2371 int total = user + system + iowait + irq + softIrq + idle; 2372 if (total == 0) total = 1; 2373 2374 EventLog.writeEvent(EventLogTags.CPU, 2375 ((user+system+iowait+irq+softIrq) * 100) / total, 2376 (user * 100) / total, 2377 (system * 100) / total, 2378 (iowait * 100) / total, 2379 (irq * 100) / total, 2380 (softIrq * 100) / total); 2381 } 2382 } 2383 2384 long[] cpuSpeedTimes = mProcessCpuTracker.getLastCpuSpeedTimes(); 2385 final BatteryStatsImpl bstats = mBatteryStatsService.getActiveStatistics(); 2386 synchronized(bstats) { 2387 synchronized(mPidsSelfLocked) { 2388 if (haveNewCpuStats) { 2389 if (mOnBattery) { 2390 int perc = bstats.startAddingCpuLocked(); 2391 int totalUTime = 0; 2392 int totalSTime = 0; 2393 final int N = mProcessCpuTracker.countStats(); 2394 for (int i=0; i<N; i++) { 2395 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 2396 if (!st.working) { 2397 continue; 2398 } 2399 ProcessRecord pr = mPidsSelfLocked.get(st.pid); 2400 int otherUTime = (st.rel_utime*perc)/100; 2401 int otherSTime = (st.rel_stime*perc)/100; 2402 totalUTime += otherUTime; 2403 totalSTime += otherSTime; 2404 if (pr != null) { 2405 BatteryStatsImpl.Uid.Proc ps = pr.curProcBatteryStats; 2406 if (ps == null || !ps.isActive()) { 2407 pr.curProcBatteryStats = ps = bstats.getProcessStatsLocked( 2408 pr.info.uid, pr.processName); 2409 } 2410 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2411 st.rel_stime-otherSTime); 2412 ps.addSpeedStepTimes(cpuSpeedTimes); 2413 pr.curCpuTime += (st.rel_utime+st.rel_stime) * 10; 2414 } else { 2415 BatteryStatsImpl.Uid.Proc ps = st.batteryStats; 2416 if (ps == null || !ps.isActive()) { 2417 st.batteryStats = ps = bstats.getProcessStatsLocked( 2418 bstats.mapUid(st.uid), st.name); 2419 } 2420 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2421 st.rel_stime-otherSTime); 2422 ps.addSpeedStepTimes(cpuSpeedTimes); 2423 } 2424 } 2425 bstats.finishAddingCpuLocked(perc, totalUTime, 2426 totalSTime, cpuSpeedTimes); 2427 } 2428 } 2429 } 2430 2431 if (mLastWriteTime < (now-BATTERY_STATS_TIME)) { 2432 mLastWriteTime = now; 2433 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2434 } 2435 } 2436 } 2437 } 2438 2439 @Override 2440 public void batteryNeedsCpuUpdate() { 2441 updateCpuStatsNow(); 2442 } 2443 2444 @Override 2445 public void batteryPowerChanged(boolean onBattery) { 2446 // When plugging in, update the CPU stats first before changing 2447 // the plug state. 2448 updateCpuStatsNow(); 2449 synchronized (this) { 2450 synchronized(mPidsSelfLocked) { 2451 mOnBattery = DEBUG_POWER ? true : onBattery; 2452 } 2453 } 2454 } 2455 2456 /** 2457 * Initialize the application bind args. These are passed to each 2458 * process when the bindApplication() IPC is sent to the process. They're 2459 * lazily setup to make sure the services are running when they're asked for. 2460 */ 2461 private HashMap<String, IBinder> getCommonServicesLocked() { 2462 if (mAppBindArgs == null) { 2463 mAppBindArgs = new HashMap<String, IBinder>(); 2464 2465 // Setup the application init args 2466 mAppBindArgs.put("package", ServiceManager.getService("package")); 2467 mAppBindArgs.put("window", ServiceManager.getService("window")); 2468 mAppBindArgs.put(Context.ALARM_SERVICE, 2469 ServiceManager.getService(Context.ALARM_SERVICE)); 2470 } 2471 return mAppBindArgs; 2472 } 2473 2474 final void setFocusedActivityLocked(ActivityRecord r) { 2475 if (mFocusedActivity != r) { 2476 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedActivityLocked: r=" + r); 2477 mFocusedActivity = r; 2478 if (r.task != null && r.task.voiceInteractor != null) { 2479 startRunningVoiceLocked(); 2480 } else { 2481 finishRunningVoiceLocked(); 2482 } 2483 mStackSupervisor.setFocusedStack(r); 2484 if (r != null) { 2485 mWindowManager.setFocusedApp(r.appToken, true); 2486 } 2487 applyUpdateLockStateLocked(r); 2488 } 2489 } 2490 2491 final void clearFocusedActivity(ActivityRecord r) { 2492 if (mFocusedActivity == r) { 2493 mFocusedActivity = null; 2494 } 2495 } 2496 2497 @Override 2498 public void setFocusedStack(int stackId) { 2499 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedStack: stackId=" + stackId); 2500 synchronized (ActivityManagerService.this) { 2501 ActivityStack stack = mStackSupervisor.getStack(stackId); 2502 if (stack != null) { 2503 ActivityRecord r = stack.topRunningActivityLocked(null); 2504 if (r != null) { 2505 setFocusedActivityLocked(r); 2506 } 2507 } 2508 } 2509 } 2510 2511 @Override 2512 public void notifyActivityDrawn(IBinder token) { 2513 if (DEBUG_VISBILITY) Slog.d(TAG, "notifyActivityDrawn: token=" + token); 2514 synchronized (this) { 2515 ActivityRecord r= mStackSupervisor.isInAnyStackLocked(token); 2516 if (r != null) { 2517 r.task.stack.notifyActivityDrawnLocked(r); 2518 } 2519 } 2520 } 2521 2522 final void applyUpdateLockStateLocked(ActivityRecord r) { 2523 // Modifications to the UpdateLock state are done on our handler, outside 2524 // the activity manager's locks. The new state is determined based on the 2525 // state *now* of the relevant activity record. The object is passed to 2526 // the handler solely for logging detail, not to be consulted/modified. 2527 final boolean nextState = r != null && r.immersive; 2528 mHandler.sendMessage( 2529 mHandler.obtainMessage(IMMERSIVE_MODE_LOCK_MSG, (nextState) ? 1 : 0, 0, r)); 2530 } 2531 2532 final void showAskCompatModeDialogLocked(ActivityRecord r) { 2533 Message msg = Message.obtain(); 2534 msg.what = SHOW_COMPAT_MODE_DIALOG_MSG; 2535 msg.obj = r.task.askedCompatMode ? null : r; 2536 mHandler.sendMessage(msg); 2537 } 2538 2539 private final int updateLruProcessInternalLocked(ProcessRecord app, long now, int index, 2540 String what, Object obj, ProcessRecord srcApp) { 2541 app.lastActivityTime = now; 2542 2543 if (app.activities.size() > 0) { 2544 // Don't want to touch dependent processes that are hosting activities. 2545 return index; 2546 } 2547 2548 int lrui = mLruProcesses.lastIndexOf(app); 2549 if (lrui < 0) { 2550 Slog.wtf(TAG, "Adding dependent process " + app + " not on LRU list: " 2551 + what + " " + obj + " from " + srcApp); 2552 return index; 2553 } 2554 2555 if (lrui >= index) { 2556 // Don't want to cause this to move dependent processes *back* in the 2557 // list as if they were less frequently used. 2558 return index; 2559 } 2560 2561 if (lrui >= mLruProcessActivityStart) { 2562 // Don't want to touch dependent processes that are hosting activities. 2563 return index; 2564 } 2565 2566 mLruProcesses.remove(lrui); 2567 if (index > 0) { 2568 index--; 2569 } 2570 if (DEBUG_LRU) Slog.d(TAG, "Moving dep from " + lrui + " to " + index 2571 + " in LRU list: " + app); 2572 mLruProcesses.add(index, app); 2573 return index; 2574 } 2575 2576 final void removeLruProcessLocked(ProcessRecord app) { 2577 int lrui = mLruProcesses.lastIndexOf(app); 2578 if (lrui >= 0) { 2579 if (lrui <= mLruProcessActivityStart) { 2580 mLruProcessActivityStart--; 2581 } 2582 if (lrui <= mLruProcessServiceStart) { 2583 mLruProcessServiceStart--; 2584 } 2585 mLruProcesses.remove(lrui); 2586 } 2587 } 2588 2589 final void updateLruProcessLocked(ProcessRecord app, boolean activityChange, 2590 ProcessRecord client) { 2591 final boolean hasActivity = app.activities.size() > 0 || app.hasClientActivities 2592 || app.treatLikeActivity; 2593 final boolean hasService = false; // not impl yet. app.services.size() > 0; 2594 if (!activityChange && hasActivity) { 2595 // The process has activities, so we are only allowing activity-based adjustments 2596 // to move it. It should be kept in the front of the list with other 2597 // processes that have activities, and we don't want those to change their 2598 // order except due to activity operations. 2599 return; 2600 } 2601 2602 mLruSeq++; 2603 final long now = SystemClock.uptimeMillis(); 2604 app.lastActivityTime = now; 2605 2606 // First a quick reject: if the app is already at the position we will 2607 // put it, then there is nothing to do. 2608 if (hasActivity) { 2609 final int N = mLruProcesses.size(); 2610 if (N > 0 && mLruProcesses.get(N-1) == app) { 2611 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top activity: " + app); 2612 return; 2613 } 2614 } else { 2615 if (mLruProcessServiceStart > 0 2616 && mLruProcesses.get(mLruProcessServiceStart-1) == app) { 2617 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top other: " + app); 2618 return; 2619 } 2620 } 2621 2622 int lrui = mLruProcesses.lastIndexOf(app); 2623 2624 if (app.persistent && lrui >= 0) { 2625 // We don't care about the position of persistent processes, as long as 2626 // they are in the list. 2627 if (DEBUG_LRU) Slog.d(TAG, "Not moving, persistent: " + app); 2628 return; 2629 } 2630 2631 /* In progress: compute new position first, so we can avoid doing work 2632 if the process is not actually going to move. Not yet working. 2633 int addIndex; 2634 int nextIndex; 2635 boolean inActivity = false, inService = false; 2636 if (hasActivity) { 2637 // Process has activities, put it at the very tipsy-top. 2638 addIndex = mLruProcesses.size(); 2639 nextIndex = mLruProcessServiceStart; 2640 inActivity = true; 2641 } else if (hasService) { 2642 // Process has services, put it at the top of the service list. 2643 addIndex = mLruProcessActivityStart; 2644 nextIndex = mLruProcessServiceStart; 2645 inActivity = true; 2646 inService = true; 2647 } else { 2648 // Process not otherwise of interest, it goes to the top of the non-service area. 2649 addIndex = mLruProcessServiceStart; 2650 if (client != null) { 2651 int clientIndex = mLruProcesses.lastIndexOf(client); 2652 if (clientIndex < 0) Slog.d(TAG, "Unknown client " + client + " when updating " 2653 + app); 2654 if (clientIndex >= 0 && addIndex > clientIndex) { 2655 addIndex = clientIndex; 2656 } 2657 } 2658 nextIndex = addIndex > 0 ? addIndex-1 : addIndex; 2659 } 2660 2661 Slog.d(TAG, "Update LRU at " + lrui + " to " + addIndex + " (act=" 2662 + mLruProcessActivityStart + "): " + app); 2663 */ 2664 2665 if (lrui >= 0) { 2666 if (lrui < mLruProcessActivityStart) { 2667 mLruProcessActivityStart--; 2668 } 2669 if (lrui < mLruProcessServiceStart) { 2670 mLruProcessServiceStart--; 2671 } 2672 /* 2673 if (addIndex > lrui) { 2674 addIndex--; 2675 } 2676 if (nextIndex > lrui) { 2677 nextIndex--; 2678 } 2679 */ 2680 mLruProcesses.remove(lrui); 2681 } 2682 2683 /* 2684 mLruProcesses.add(addIndex, app); 2685 if (inActivity) { 2686 mLruProcessActivityStart++; 2687 } 2688 if (inService) { 2689 mLruProcessActivityStart++; 2690 } 2691 */ 2692 2693 int nextIndex; 2694 if (hasActivity) { 2695 final int N = mLruProcesses.size(); 2696 if (app.activities.size() == 0 && mLruProcessActivityStart < (N-1)) { 2697 // Process doesn't have activities, but has clients with 2698 // activities... move it up, but one below the top (the top 2699 // should always have a real activity). 2700 if (DEBUG_LRU) Slog.d(TAG, "Adding to second-top of LRU activity list: " + app); 2701 mLruProcesses.add(N-1, app); 2702 // To keep it from spamming the LRU list (by making a bunch of clients), 2703 // we will push down any other entries owned by the app. 2704 final int uid = app.info.uid; 2705 for (int i=N-2; i>mLruProcessActivityStart; i--) { 2706 ProcessRecord subProc = mLruProcesses.get(i); 2707 if (subProc.info.uid == uid) { 2708 // We want to push this one down the list. If the process after 2709 // it is for the same uid, however, don't do so, because we don't 2710 // want them internally to be re-ordered. 2711 if (mLruProcesses.get(i-1).info.uid != uid) { 2712 if (DEBUG_LRU) Slog.d(TAG, "Pushing uid " + uid + " swapping at " + i 2713 + ": " + mLruProcesses.get(i) + " : " + mLruProcesses.get(i-1)); 2714 ProcessRecord tmp = mLruProcesses.get(i); 2715 mLruProcesses.set(i, mLruProcesses.get(i-1)); 2716 mLruProcesses.set(i-1, tmp); 2717 i--; 2718 } 2719 } else { 2720 // A gap, we can stop here. 2721 break; 2722 } 2723 } 2724 } else { 2725 // Process has activities, put it at the very tipsy-top. 2726 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU activity list: " + app); 2727 mLruProcesses.add(app); 2728 } 2729 nextIndex = mLruProcessServiceStart; 2730 } else if (hasService) { 2731 // Process has services, put it at the top of the service list. 2732 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU service list: " + app); 2733 mLruProcesses.add(mLruProcessActivityStart, app); 2734 nextIndex = mLruProcessServiceStart; 2735 mLruProcessActivityStart++; 2736 } else { 2737 // Process not otherwise of interest, it goes to the top of the non-service area. 2738 int index = mLruProcessServiceStart; 2739 if (client != null) { 2740 // If there is a client, don't allow the process to be moved up higher 2741 // in the list than that client. 2742 int clientIndex = mLruProcesses.lastIndexOf(client); 2743 if (DEBUG_LRU && clientIndex < 0) Slog.d(TAG, "Unknown client " + client 2744 + " when updating " + app); 2745 if (clientIndex <= lrui) { 2746 // Don't allow the client index restriction to push it down farther in the 2747 // list than it already is. 2748 clientIndex = lrui; 2749 } 2750 if (clientIndex >= 0 && index > clientIndex) { 2751 index = clientIndex; 2752 } 2753 } 2754 if (DEBUG_LRU) Slog.d(TAG, "Adding at " + index + " of LRU list: " + app); 2755 mLruProcesses.add(index, app); 2756 nextIndex = index-1; 2757 mLruProcessActivityStart++; 2758 mLruProcessServiceStart++; 2759 } 2760 2761 // If the app is currently using a content provider or service, 2762 // bump those processes as well. 2763 for (int j=app.connections.size()-1; j>=0; j--) { 2764 ConnectionRecord cr = app.connections.valueAt(j); 2765 if (cr.binding != null && !cr.serviceDead && cr.binding.service != null 2766 && cr.binding.service.app != null 2767 && cr.binding.service.app.lruSeq != mLruSeq 2768 && !cr.binding.service.app.persistent) { 2769 nextIndex = updateLruProcessInternalLocked(cr.binding.service.app, now, nextIndex, 2770 "service connection", cr, app); 2771 } 2772 } 2773 for (int j=app.conProviders.size()-1; j>=0; j--) { 2774 ContentProviderRecord cpr = app.conProviders.get(j).provider; 2775 if (cpr.proc != null && cpr.proc.lruSeq != mLruSeq && !cpr.proc.persistent) { 2776 nextIndex = updateLruProcessInternalLocked(cpr.proc, now, nextIndex, 2777 "provider reference", cpr, app); 2778 } 2779 } 2780 } 2781 2782 final ProcessRecord getProcessRecordLocked(String processName, int uid, boolean keepIfLarge) { 2783 if (uid == Process.SYSTEM_UID) { 2784 // The system gets to run in any process. If there are multiple 2785 // processes with the same uid, just pick the first (this 2786 // should never happen). 2787 SparseArray<ProcessRecord> procs = mProcessNames.getMap().get(processName); 2788 if (procs == null) return null; 2789 final int N = procs.size(); 2790 for (int i = 0; i < N; i++) { 2791 if (UserHandle.isSameUser(procs.keyAt(i), uid)) return procs.valueAt(i); 2792 } 2793 } 2794 ProcessRecord proc = mProcessNames.get(processName, uid); 2795 if (false && proc != null && !keepIfLarge 2796 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY 2797 && proc.lastCachedPss >= 4000) { 2798 // Turn this condition on to cause killing to happen regularly, for testing. 2799 if (proc.baseProcessTracker != null) { 2800 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2801 } 2802 killUnneededProcessLocked(proc, Long.toString(proc.lastCachedPss) 2803 + "k from cached"); 2804 } else if (proc != null && !keepIfLarge 2805 && mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 2806 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 2807 if (DEBUG_PSS) Slog.d(TAG, "May not keep " + proc + ": pss=" + proc.lastCachedPss); 2808 if (proc.lastCachedPss >= mProcessList.getCachedRestoreThresholdKb()) { 2809 if (proc.baseProcessTracker != null) { 2810 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2811 } 2812 killUnneededProcessLocked(proc, Long.toString(proc.lastCachedPss) 2813 + "k from cached"); 2814 } 2815 } 2816 return proc; 2817 } 2818 2819 void ensurePackageDexOpt(String packageName) { 2820 IPackageManager pm = AppGlobals.getPackageManager(); 2821 try { 2822 if (pm.performDexOptIfNeeded(packageName, null /* instruction set */)) { 2823 mDidDexOpt = true; 2824 } 2825 } catch (RemoteException e) { 2826 } 2827 } 2828 2829 boolean isNextTransitionForward() { 2830 int transit = mWindowManager.getPendingAppTransition(); 2831 return transit == AppTransition.TRANSIT_ACTIVITY_OPEN 2832 || transit == AppTransition.TRANSIT_TASK_OPEN 2833 || transit == AppTransition.TRANSIT_TASK_TO_FRONT; 2834 } 2835 2836 int startIsolatedProcess(String entryPoint, String[] entryPointArgs, 2837 String processName, String abiOverride, int uid, Runnable crashHandler) { 2838 synchronized(this) { 2839 ApplicationInfo info = new ApplicationInfo(); 2840 // In general the ApplicationInfo.uid isn't neccesarily equal to ProcessRecord.uid. 2841 // For isolated processes, the former contains the parent's uid and the latter the 2842 // actual uid of the isolated process. 2843 // In the special case introduced by this method (which is, starting an isolated 2844 // process directly from the SystemServer without an actual parent app process) the 2845 // closest thing to a parent's uid is SYSTEM_UID. 2846 // The only important thing here is to keep AI.uid != PR.uid, in order to trigger 2847 // the |isolated| logic in the ProcessRecord constructor. 2848 info.uid = Process.SYSTEM_UID; 2849 info.processName = processName; 2850 info.className = entryPoint; 2851 info.packageName = "android"; 2852 ProcessRecord proc = startProcessLocked(processName, info /* info */, 2853 false /* knownToBeDead */, 0 /* intentFlags */, "" /* hostingType */, 2854 null /* hostingName */, true /* allowWhileBooting */, true /* isolated */, 2855 uid, true /* keepIfLarge */, abiOverride, entryPoint, entryPointArgs, 2856 crashHandler); 2857 return proc != null ? proc.pid : 0; 2858 } 2859 } 2860 2861 final ProcessRecord startProcessLocked(String processName, 2862 ApplicationInfo info, boolean knownToBeDead, int intentFlags, 2863 String hostingType, ComponentName hostingName, boolean allowWhileBooting, 2864 boolean isolated, boolean keepIfLarge) { 2865 return startProcessLocked(processName, info, knownToBeDead, intentFlags, hostingType, 2866 hostingName, allowWhileBooting, isolated, 0 /* isolatedUid */, keepIfLarge, 2867 null /* ABI override */, null /* entryPoint */, null /* entryPointArgs */, 2868 null /* crashHandler */); 2869 } 2870 2871 final ProcessRecord startProcessLocked(String processName, ApplicationInfo info, 2872 boolean knownToBeDead, int intentFlags, String hostingType, ComponentName hostingName, 2873 boolean allowWhileBooting, boolean isolated, int isolatedUid, boolean keepIfLarge, 2874 String abiOverride, String entryPoint, String[] entryPointArgs, Runnable crashHandler) { 2875 ProcessRecord app; 2876 if (!isolated) { 2877 app = getProcessRecordLocked(processName, info.uid, keepIfLarge); 2878 } else { 2879 // If this is an isolated process, it can't re-use an existing process. 2880 app = null; 2881 } 2882 // We don't have to do anything more if: 2883 // (1) There is an existing application record; and 2884 // (2) The caller doesn't think it is dead, OR there is no thread 2885 // object attached to it so we know it couldn't have crashed; and 2886 // (3) There is a pid assigned to it, so it is either starting or 2887 // already running. 2888 if (DEBUG_PROCESSES) Slog.v(TAG, "startProcess: name=" + processName 2889 + " app=" + app + " knownToBeDead=" + knownToBeDead 2890 + " thread=" + (app != null ? app.thread : null) 2891 + " pid=" + (app != null ? app.pid : -1)); 2892 if (app != null && app.pid > 0) { 2893 if (!knownToBeDead || app.thread == null) { 2894 // We already have the app running, or are waiting for it to 2895 // come up (we have a pid but not yet its thread), so keep it. 2896 if (DEBUG_PROCESSES) Slog.v(TAG, "App already running: " + app); 2897 // If this is a new package in the process, add the package to the list 2898 app.addPackage(info.packageName, info.versionCode, mProcessStats); 2899 return app; 2900 } 2901 2902 // An application record is attached to a previous process, 2903 // clean it up now. 2904 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, "App died: " + app); 2905 Process.killProcessGroup(app.info.uid, app.pid); 2906 handleAppDiedLocked(app, true, true); 2907 } 2908 2909 String hostingNameStr = hostingName != null 2910 ? hostingName.flattenToShortString() : null; 2911 2912 if (!isolated) { 2913 if ((intentFlags&Intent.FLAG_FROM_BACKGROUND) != 0) { 2914 // If we are in the background, then check to see if this process 2915 // is bad. If so, we will just silently fail. 2916 if (mBadProcesses.get(info.processName, info.uid) != null) { 2917 if (DEBUG_PROCESSES) Slog.v(TAG, "Bad process: " + info.uid 2918 + "/" + info.processName); 2919 return null; 2920 } 2921 } else { 2922 // When the user is explicitly starting a process, then clear its 2923 // crash count so that we won't make it bad until they see at 2924 // least one crash dialog again, and make the process good again 2925 // if it had been bad. 2926 if (DEBUG_PROCESSES) Slog.v(TAG, "Clearing bad process: " + info.uid 2927 + "/" + info.processName); 2928 mProcessCrashTimes.remove(info.processName, info.uid); 2929 if (mBadProcesses.get(info.processName, info.uid) != null) { 2930 EventLog.writeEvent(EventLogTags.AM_PROC_GOOD, 2931 UserHandle.getUserId(info.uid), info.uid, 2932 info.processName); 2933 mBadProcesses.remove(info.processName, info.uid); 2934 if (app != null) { 2935 app.bad = false; 2936 } 2937 } 2938 } 2939 } 2940 2941 if (app == null) { 2942 app = newProcessRecordLocked(info, processName, isolated, isolatedUid); 2943 app.crashHandler = crashHandler; 2944 if (app == null) { 2945 Slog.w(TAG, "Failed making new process record for " 2946 + processName + "/" + info.uid + " isolated=" + isolated); 2947 return null; 2948 } 2949 mProcessNames.put(processName, app.uid, app); 2950 if (isolated) { 2951 mIsolatedProcesses.put(app.uid, app); 2952 } 2953 } else { 2954 // If this is a new package in the process, add the package to the list 2955 app.addPackage(info.packageName, info.versionCode, mProcessStats); 2956 } 2957 2958 // If the system is not ready yet, then hold off on starting this 2959 // process until it is. 2960 if (!mProcessesReady 2961 && !isAllowedWhileBooting(info) 2962 && !allowWhileBooting) { 2963 if (!mProcessesOnHold.contains(app)) { 2964 mProcessesOnHold.add(app); 2965 } 2966 if (DEBUG_PROCESSES) Slog.v(TAG, "System not ready, putting on hold: " + app); 2967 return app; 2968 } 2969 2970 startProcessLocked( 2971 app, hostingType, hostingNameStr, abiOverride, entryPoint, entryPointArgs); 2972 return (app.pid != 0) ? app : null; 2973 } 2974 2975 boolean isAllowedWhileBooting(ApplicationInfo ai) { 2976 return (ai.flags&ApplicationInfo.FLAG_PERSISTENT) != 0; 2977 } 2978 2979 private final void startProcessLocked(ProcessRecord app, 2980 String hostingType, String hostingNameStr) { 2981 startProcessLocked(app, hostingType, hostingNameStr, null /* abiOverride */, 2982 null /* entryPoint */, null /* entryPointArgs */); 2983 } 2984 2985 private final void startProcessLocked(ProcessRecord app, String hostingType, 2986 String hostingNameStr, String abiOverride, String entryPoint, String[] entryPointArgs) { 2987 if (app.pid > 0 && app.pid != MY_PID) { 2988 synchronized (mPidsSelfLocked) { 2989 mPidsSelfLocked.remove(app.pid); 2990 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 2991 } 2992 app.setPid(0); 2993 } 2994 2995 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 2996 "startProcessLocked removing on hold: " + app); 2997 mProcessesOnHold.remove(app); 2998 2999 updateCpuStats(); 3000 3001 try { 3002 int uid = app.uid; 3003 3004 int[] gids = null; 3005 int mountExternal = Zygote.MOUNT_EXTERNAL_NONE; 3006 if (!app.isolated) { 3007 int[] permGids = null; 3008 try { 3009 final PackageManager pm = mContext.getPackageManager(); 3010 permGids = pm.getPackageGids(app.info.packageName); 3011 3012 if (Environment.isExternalStorageEmulated()) { 3013 if (pm.checkPermission( 3014 android.Manifest.permission.ACCESS_ALL_EXTERNAL_STORAGE, 3015 app.info.packageName) == PERMISSION_GRANTED) { 3016 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER_ALL; 3017 } else { 3018 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER; 3019 } 3020 } 3021 } catch (PackageManager.NameNotFoundException e) { 3022 Slog.w(TAG, "Unable to retrieve gids", e); 3023 } 3024 3025 /* 3026 * Add shared application and profile GIDs so applications can share some 3027 * resources like shared libraries and access user-wide resources 3028 */ 3029 if (permGids == null) { 3030 gids = new int[2]; 3031 } else { 3032 gids = new int[permGids.length + 2]; 3033 System.arraycopy(permGids, 0, gids, 2, permGids.length); 3034 } 3035 gids[0] = UserHandle.getSharedAppGid(UserHandle.getAppId(uid)); 3036 gids[1] = UserHandle.getUserGid(UserHandle.getUserId(uid)); 3037 } 3038 if (mFactoryTest != FactoryTest.FACTORY_TEST_OFF) { 3039 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3040 && mTopComponent != null 3041 && app.processName.equals(mTopComponent.getPackageName())) { 3042 uid = 0; 3043 } 3044 if (mFactoryTest == FactoryTest.FACTORY_TEST_HIGH_LEVEL 3045 && (app.info.flags&ApplicationInfo.FLAG_FACTORY_TEST) != 0) { 3046 uid = 0; 3047 } 3048 } 3049 int debugFlags = 0; 3050 if ((app.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 3051 debugFlags |= Zygote.DEBUG_ENABLE_DEBUGGER; 3052 // Also turn on CheckJNI for debuggable apps. It's quite 3053 // awkward to turn on otherwise. 3054 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 3055 } 3056 // Run the app in safe mode if its manifest requests so or the 3057 // system is booted in safe mode. 3058 if ((app.info.flags & ApplicationInfo.FLAG_VM_SAFE_MODE) != 0 || 3059 mSafeMode == true) { 3060 debugFlags |= Zygote.DEBUG_ENABLE_SAFEMODE; 3061 } 3062 if ("1".equals(SystemProperties.get("debug.checkjni"))) { 3063 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 3064 } 3065 if ("1".equals(SystemProperties.get("debug.jni.logging"))) { 3066 debugFlags |= Zygote.DEBUG_ENABLE_JNI_LOGGING; 3067 } 3068 if ("1".equals(SystemProperties.get("debug.assert"))) { 3069 debugFlags |= Zygote.DEBUG_ENABLE_ASSERT; 3070 } 3071 3072 String requiredAbi = (abiOverride != null) ? abiOverride : app.info.primaryCpuAbi; 3073 if (requiredAbi == null) { 3074 requiredAbi = Build.SUPPORTED_ABIS[0]; 3075 } 3076 3077 // Start the process. It will either succeed and return a result containing 3078 // the PID of the new process, or else throw a RuntimeException. 3079 boolean isActivityProcess = (entryPoint == null); 3080 if (entryPoint == null) entryPoint = "android.app.ActivityThread"; 3081 Process.ProcessStartResult startResult = Process.start(entryPoint, 3082 app.processName, uid, uid, gids, debugFlags, mountExternal, 3083 app.info.targetSdkVersion, app.info.seinfo, requiredAbi, entryPointArgs); 3084 3085 if (app.isolated) { 3086 mBatteryStatsService.addIsolatedUid(app.uid, app.info.uid); 3087 } 3088 mBatteryStatsService.noteProcessStart(app.processName, app.info.uid); 3089 3090 EventLog.writeEvent(EventLogTags.AM_PROC_START, 3091 UserHandle.getUserId(uid), startResult.pid, uid, 3092 app.processName, hostingType, 3093 hostingNameStr != null ? hostingNameStr : ""); 3094 3095 if (app.persistent) { 3096 Watchdog.getInstance().processStarted(app.processName, startResult.pid); 3097 } 3098 3099 StringBuilder buf = mStringBuilder; 3100 buf.setLength(0); 3101 buf.append("Start proc "); 3102 buf.append(app.processName); 3103 if (!isActivityProcess) { 3104 buf.append(" ["); 3105 buf.append(entryPoint); 3106 buf.append("]"); 3107 } 3108 buf.append(" for "); 3109 buf.append(hostingType); 3110 if (hostingNameStr != null) { 3111 buf.append(" "); 3112 buf.append(hostingNameStr); 3113 } 3114 buf.append(": pid="); 3115 buf.append(startResult.pid); 3116 buf.append(" uid="); 3117 buf.append(uid); 3118 buf.append(" gids={"); 3119 if (gids != null) { 3120 for (int gi=0; gi<gids.length; gi++) { 3121 if (gi != 0) buf.append(", "); 3122 buf.append(gids[gi]); 3123 3124 } 3125 } 3126 buf.append("}"); 3127 if (requiredAbi != null) { 3128 buf.append(" abi="); 3129 buf.append(requiredAbi); 3130 } 3131 Slog.i(TAG, buf.toString()); 3132 app.setPid(startResult.pid); 3133 app.usingWrapper = startResult.usingWrapper; 3134 app.removed = false; 3135 app.killedByAm = false; 3136 synchronized (mPidsSelfLocked) { 3137 this.mPidsSelfLocked.put(startResult.pid, app); 3138 if (isActivityProcess) { 3139 Message msg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 3140 msg.obj = app; 3141 mHandler.sendMessageDelayed(msg, startResult.usingWrapper 3142 ? PROC_START_TIMEOUT_WITH_WRAPPER : PROC_START_TIMEOUT); 3143 } 3144 } 3145 } catch (RuntimeException e) { 3146 // XXX do better error recovery. 3147 app.setPid(0); 3148 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 3149 if (app.isolated) { 3150 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 3151 } 3152 Slog.e(TAG, "Failure starting process " + app.processName, e); 3153 } 3154 } 3155 3156 void updateUsageStats(ActivityRecord component, boolean resumed) { 3157 if (DEBUG_SWITCH) Slog.d(TAG, "updateUsageStats: comp=" + component + "res=" + resumed); 3158 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 3159 if (resumed) { 3160 if (mUsageStatsService != null) { 3161 mUsageStatsService.reportEvent(component.realActivity, component.userId, 3162 System.currentTimeMillis(), 3163 UsageEvents.Event.MOVE_TO_FOREGROUND); 3164 } 3165 synchronized (stats) { 3166 stats.noteActivityResumedLocked(component.app.uid); 3167 } 3168 } else { 3169 if (mUsageStatsService != null) { 3170 mUsageStatsService.reportEvent(component.realActivity, component.userId, 3171 System.currentTimeMillis(), 3172 UsageEvents.Event.MOVE_TO_BACKGROUND); 3173 } 3174 synchronized (stats) { 3175 stats.noteActivityPausedLocked(component.app.uid); 3176 } 3177 } 3178 } 3179 3180 Intent getHomeIntent() { 3181 Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null); 3182 intent.setComponent(mTopComponent); 3183 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 3184 intent.addCategory(Intent.CATEGORY_HOME); 3185 } 3186 return intent; 3187 } 3188 3189 boolean startHomeActivityLocked(int userId) { 3190 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3191 && mTopAction == null) { 3192 // We are running in factory test mode, but unable to find 3193 // the factory test app, so just sit around displaying the 3194 // error message and don't try to start anything. 3195 return false; 3196 } 3197 Intent intent = getHomeIntent(); 3198 ActivityInfo aInfo = 3199 resolveActivityInfo(intent, STOCK_PM_FLAGS, userId); 3200 if (aInfo != null) { 3201 intent.setComponent(new ComponentName( 3202 aInfo.applicationInfo.packageName, aInfo.name)); 3203 // Don't do this if the home app is currently being 3204 // instrumented. 3205 aInfo = new ActivityInfo(aInfo); 3206 aInfo.applicationInfo = getAppInfoForUser(aInfo.applicationInfo, userId); 3207 ProcessRecord app = getProcessRecordLocked(aInfo.processName, 3208 aInfo.applicationInfo.uid, true); 3209 if (app == null || app.instrumentationClass == null) { 3210 intent.setFlags(intent.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK); 3211 mStackSupervisor.startHomeActivity(intent, aInfo); 3212 } 3213 } 3214 3215 return true; 3216 } 3217 3218 private ActivityInfo resolveActivityInfo(Intent intent, int flags, int userId) { 3219 ActivityInfo ai = null; 3220 ComponentName comp = intent.getComponent(); 3221 try { 3222 if (comp != null) { 3223 ai = AppGlobals.getPackageManager().getActivityInfo(comp, flags, userId); 3224 } else { 3225 ResolveInfo info = AppGlobals.getPackageManager().resolveIntent( 3226 intent, 3227 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 3228 flags, userId); 3229 3230 if (info != null) { 3231 ai = info.activityInfo; 3232 } 3233 } 3234 } catch (RemoteException e) { 3235 // ignore 3236 } 3237 3238 return ai; 3239 } 3240 3241 /** 3242 * Starts the "new version setup screen" if appropriate. 3243 */ 3244 void startSetupActivityLocked() { 3245 // Only do this once per boot. 3246 if (mCheckedForSetup) { 3247 return; 3248 } 3249 3250 // We will show this screen if the current one is a different 3251 // version than the last one shown, and we are not running in 3252 // low-level factory test mode. 3253 final ContentResolver resolver = mContext.getContentResolver(); 3254 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL && 3255 Settings.Global.getInt(resolver, 3256 Settings.Global.DEVICE_PROVISIONED, 0) != 0) { 3257 mCheckedForSetup = true; 3258 3259 // See if we should be showing the platform update setup UI. 3260 Intent intent = new Intent(Intent.ACTION_UPGRADE_SETUP); 3261 List<ResolveInfo> ris = mContext.getPackageManager() 3262 .queryIntentActivities(intent, PackageManager.GET_META_DATA); 3263 3264 // We don't allow third party apps to replace this. 3265 ResolveInfo ri = null; 3266 for (int i=0; ris != null && i<ris.size(); i++) { 3267 if ((ris.get(i).activityInfo.applicationInfo.flags 3268 & ApplicationInfo.FLAG_SYSTEM) != 0) { 3269 ri = ris.get(i); 3270 break; 3271 } 3272 } 3273 3274 if (ri != null) { 3275 String vers = ri.activityInfo.metaData != null 3276 ? ri.activityInfo.metaData.getString(Intent.METADATA_SETUP_VERSION) 3277 : null; 3278 if (vers == null && ri.activityInfo.applicationInfo.metaData != null) { 3279 vers = ri.activityInfo.applicationInfo.metaData.getString( 3280 Intent.METADATA_SETUP_VERSION); 3281 } 3282 String lastVers = Settings.Secure.getString( 3283 resolver, Settings.Secure.LAST_SETUP_SHOWN); 3284 if (vers != null && !vers.equals(lastVers)) { 3285 intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 3286 intent.setComponent(new ComponentName( 3287 ri.activityInfo.packageName, ri.activityInfo.name)); 3288 mStackSupervisor.startActivityLocked(null, intent, null, ri.activityInfo, 3289 null, null, null, null, 0, 0, 0, null, 0, null, false, null, null); 3290 } 3291 } 3292 } 3293 } 3294 3295 CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) { 3296 return mCompatModePackages.compatibilityInfoForPackageLocked(ai); 3297 } 3298 3299 void enforceNotIsolatedCaller(String caller) { 3300 if (UserHandle.isIsolated(Binder.getCallingUid())) { 3301 throw new SecurityException("Isolated process not allowed to call " + caller); 3302 } 3303 } 3304 3305 @Override 3306 public int getFrontActivityScreenCompatMode() { 3307 enforceNotIsolatedCaller("getFrontActivityScreenCompatMode"); 3308 synchronized (this) { 3309 return mCompatModePackages.getFrontActivityScreenCompatModeLocked(); 3310 } 3311 } 3312 3313 @Override 3314 public void setFrontActivityScreenCompatMode(int mode) { 3315 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3316 "setFrontActivityScreenCompatMode"); 3317 synchronized (this) { 3318 mCompatModePackages.setFrontActivityScreenCompatModeLocked(mode); 3319 } 3320 } 3321 3322 @Override 3323 public int getPackageScreenCompatMode(String packageName) { 3324 enforceNotIsolatedCaller("getPackageScreenCompatMode"); 3325 synchronized (this) { 3326 return mCompatModePackages.getPackageScreenCompatModeLocked(packageName); 3327 } 3328 } 3329 3330 @Override 3331 public void setPackageScreenCompatMode(String packageName, int mode) { 3332 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3333 "setPackageScreenCompatMode"); 3334 synchronized (this) { 3335 mCompatModePackages.setPackageScreenCompatModeLocked(packageName, mode); 3336 } 3337 } 3338 3339 @Override 3340 public boolean getPackageAskScreenCompat(String packageName) { 3341 enforceNotIsolatedCaller("getPackageAskScreenCompat"); 3342 synchronized (this) { 3343 return mCompatModePackages.getPackageAskCompatModeLocked(packageName); 3344 } 3345 } 3346 3347 @Override 3348 public void setPackageAskScreenCompat(String packageName, boolean ask) { 3349 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3350 "setPackageAskScreenCompat"); 3351 synchronized (this) { 3352 mCompatModePackages.setPackageAskCompatModeLocked(packageName, ask); 3353 } 3354 } 3355 3356 private void dispatchProcessesChanged() { 3357 int N; 3358 synchronized (this) { 3359 N = mPendingProcessChanges.size(); 3360 if (mActiveProcessChanges.length < N) { 3361 mActiveProcessChanges = new ProcessChangeItem[N]; 3362 } 3363 mPendingProcessChanges.toArray(mActiveProcessChanges); 3364 mAvailProcessChanges.addAll(mPendingProcessChanges); 3365 mPendingProcessChanges.clear(); 3366 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "*** Delivering " + N + " process changes"); 3367 } 3368 3369 int i = mProcessObservers.beginBroadcast(); 3370 while (i > 0) { 3371 i--; 3372 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3373 if (observer != null) { 3374 try { 3375 for (int j=0; j<N; j++) { 3376 ProcessChangeItem item = mActiveProcessChanges[j]; 3377 if ((item.changes&ProcessChangeItem.CHANGE_ACTIVITIES) != 0) { 3378 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "ACTIVITIES CHANGED pid=" 3379 + item.pid + " uid=" + item.uid + ": " 3380 + item.foregroundActivities); 3381 observer.onForegroundActivitiesChanged(item.pid, item.uid, 3382 item.foregroundActivities); 3383 } 3384 if ((item.changes&ProcessChangeItem.CHANGE_PROCESS_STATE) != 0) { 3385 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "PROCSTATE CHANGED pid=" 3386 + item.pid + " uid=" + item.uid + ": " + item.processState); 3387 observer.onProcessStateChanged(item.pid, item.uid, item.processState); 3388 } 3389 } 3390 } catch (RemoteException e) { 3391 } 3392 } 3393 } 3394 mProcessObservers.finishBroadcast(); 3395 } 3396 3397 private void dispatchProcessDied(int pid, int uid) { 3398 int i = mProcessObservers.beginBroadcast(); 3399 while (i > 0) { 3400 i--; 3401 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3402 if (observer != null) { 3403 try { 3404 observer.onProcessDied(pid, uid); 3405 } catch (RemoteException e) { 3406 } 3407 } 3408 } 3409 mProcessObservers.finishBroadcast(); 3410 } 3411 3412 @Override 3413 public final int startActivity(IApplicationThread caller, String callingPackage, 3414 Intent intent, String resolvedType, IBinder resultTo, 3415 String resultWho, int requestCode, int startFlags, 3416 String profileFile, ParcelFileDescriptor profileFd, Bundle options) { 3417 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo, 3418 resultWho, requestCode, 3419 startFlags, profileFile, profileFd, options, UserHandle.getCallingUserId()); 3420 } 3421 3422 @Override 3423 public final int startActivityAsUser(IApplicationThread caller, String callingPackage, 3424 Intent intent, String resolvedType, IBinder resultTo, 3425 String resultWho, int requestCode, int startFlags, 3426 String profileFile, ParcelFileDescriptor profileFd, Bundle options, int userId) { 3427 enforceNotIsolatedCaller("startActivity"); 3428 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3429 false, ALLOW_FULL_ONLY, "startActivity", null); 3430 // TODO: Switch to user app stacks here. 3431 return mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 3432 null, null, resultTo, resultWho, requestCode, startFlags, profileFile, profileFd, 3433 null, null, options, userId, null); 3434 } 3435 3436 @Override 3437 public final WaitResult startActivityAndWait(IApplicationThread caller, String callingPackage, 3438 Intent intent, String resolvedType, IBinder resultTo, 3439 String resultWho, int requestCode, int startFlags, String profileFile, 3440 ParcelFileDescriptor profileFd, Bundle options, int userId) { 3441 enforceNotIsolatedCaller("startActivityAndWait"); 3442 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3443 false, ALLOW_FULL_ONLY, "startActivityAndWait", null); 3444 WaitResult res = new WaitResult(); 3445 // TODO: Switch to user app stacks here. 3446 mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 3447 null, null, resultTo, resultWho, requestCode, startFlags, profileFile, profileFd, 3448 res, null, options, userId, null); 3449 return res; 3450 } 3451 3452 @Override 3453 public final int startActivityWithConfig(IApplicationThread caller, String callingPackage, 3454 Intent intent, String resolvedType, IBinder resultTo, 3455 String resultWho, int requestCode, int startFlags, Configuration config, 3456 Bundle options, int userId) { 3457 enforceNotIsolatedCaller("startActivityWithConfig"); 3458 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3459 false, ALLOW_FULL_ONLY, "startActivityWithConfig", null); 3460 // TODO: Switch to user app stacks here. 3461 int ret = mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, 3462 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3463 null, null, null, config, options, userId, null); 3464 return ret; 3465 } 3466 3467 @Override 3468 public int startActivityIntentSender(IApplicationThread caller, 3469 IntentSender intent, Intent fillInIntent, String resolvedType, 3470 IBinder resultTo, String resultWho, int requestCode, 3471 int flagsMask, int flagsValues, Bundle options) { 3472 enforceNotIsolatedCaller("startActivityIntentSender"); 3473 // Refuse possible leaked file descriptors 3474 if (fillInIntent != null && fillInIntent.hasFileDescriptors()) { 3475 throw new IllegalArgumentException("File descriptors passed in Intent"); 3476 } 3477 3478 IIntentSender sender = intent.getTarget(); 3479 if (!(sender instanceof PendingIntentRecord)) { 3480 throw new IllegalArgumentException("Bad PendingIntent object"); 3481 } 3482 3483 PendingIntentRecord pir = (PendingIntentRecord)sender; 3484 3485 synchronized (this) { 3486 // If this is coming from the currently resumed activity, it is 3487 // effectively saying that app switches are allowed at this point. 3488 final ActivityStack stack = getFocusedStack(); 3489 if (stack.mResumedActivity != null && 3490 stack.mResumedActivity.info.applicationInfo.uid == Binder.getCallingUid()) { 3491 mAppSwitchesAllowedTime = 0; 3492 } 3493 } 3494 int ret = pir.sendInner(0, fillInIntent, resolvedType, null, null, 3495 resultTo, resultWho, requestCode, flagsMask, flagsValues, options, null); 3496 return ret; 3497 } 3498 3499 @Override 3500 public int startVoiceActivity(String callingPackage, int callingPid, int callingUid, 3501 Intent intent, String resolvedType, IVoiceInteractionSession session, 3502 IVoiceInteractor interactor, int startFlags, String profileFile, 3503 ParcelFileDescriptor profileFd, Bundle options, int userId) { 3504 if (checkCallingPermission(Manifest.permission.BIND_VOICE_INTERACTION) 3505 != PackageManager.PERMISSION_GRANTED) { 3506 String msg = "Permission Denial: startVoiceActivity() from pid=" 3507 + Binder.getCallingPid() 3508 + ", uid=" + Binder.getCallingUid() 3509 + " requires " + android.Manifest.permission.BIND_VOICE_INTERACTION; 3510 Slog.w(TAG, msg); 3511 throw new SecurityException(msg); 3512 } 3513 if (session == null || interactor == null) { 3514 throw new NullPointerException("null session or interactor"); 3515 } 3516 userId = handleIncomingUser(callingPid, callingUid, userId, 3517 false, ALLOW_FULL_ONLY, "startVoiceActivity", null); 3518 // TODO: Switch to user app stacks here. 3519 return mStackSupervisor.startActivityMayWait(null, callingUid, callingPackage, intent, 3520 resolvedType, session, interactor, null, null, 0, startFlags, 3521 profileFile, profileFd, null, null, options, userId, null); 3522 } 3523 3524 @Override 3525 public boolean startNextMatchingActivity(IBinder callingActivity, 3526 Intent intent, Bundle options) { 3527 // Refuse possible leaked file descriptors 3528 if (intent != null && intent.hasFileDescriptors() == true) { 3529 throw new IllegalArgumentException("File descriptors passed in Intent"); 3530 } 3531 3532 synchronized (this) { 3533 final ActivityRecord r = ActivityRecord.isInStackLocked(callingActivity); 3534 if (r == null) { 3535 ActivityOptions.abort(options); 3536 return false; 3537 } 3538 if (r.app == null || r.app.thread == null) { 3539 // The caller is not running... d'oh! 3540 ActivityOptions.abort(options); 3541 return false; 3542 } 3543 intent = new Intent(intent); 3544 // The caller is not allowed to change the data. 3545 intent.setDataAndType(r.intent.getData(), r.intent.getType()); 3546 // And we are resetting to find the next component... 3547 intent.setComponent(null); 3548 3549 final boolean debug = ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0); 3550 3551 ActivityInfo aInfo = null; 3552 try { 3553 List<ResolveInfo> resolves = 3554 AppGlobals.getPackageManager().queryIntentActivities( 3555 intent, r.resolvedType, 3556 PackageManager.MATCH_DEFAULT_ONLY | STOCK_PM_FLAGS, 3557 UserHandle.getCallingUserId()); 3558 3559 // Look for the original activity in the list... 3560 final int N = resolves != null ? resolves.size() : 0; 3561 for (int i=0; i<N; i++) { 3562 ResolveInfo rInfo = resolves.get(i); 3563 if (rInfo.activityInfo.packageName.equals(r.packageName) 3564 && rInfo.activityInfo.name.equals(r.info.name)) { 3565 // We found the current one... the next matching is 3566 // after it. 3567 i++; 3568 if (i<N) { 3569 aInfo = resolves.get(i).activityInfo; 3570 } 3571 if (debug) { 3572 Slog.v(TAG, "Next matching activity: found current " + r.packageName 3573 + "/" + r.info.name); 3574 Slog.v(TAG, "Next matching activity: next is " + aInfo.packageName 3575 + "/" + aInfo.name); 3576 } 3577 break; 3578 } 3579 } 3580 } catch (RemoteException e) { 3581 } 3582 3583 if (aInfo == null) { 3584 // Nobody who is next! 3585 ActivityOptions.abort(options); 3586 if (debug) Slog.d(TAG, "Next matching activity: nothing found"); 3587 return false; 3588 } 3589 3590 intent.setComponent(new ComponentName( 3591 aInfo.applicationInfo.packageName, aInfo.name)); 3592 intent.setFlags(intent.getFlags()&~( 3593 Intent.FLAG_ACTIVITY_FORWARD_RESULT| 3594 Intent.FLAG_ACTIVITY_CLEAR_TOP| 3595 Intent.FLAG_ACTIVITY_MULTIPLE_TASK| 3596 Intent.FLAG_ACTIVITY_NEW_TASK)); 3597 3598 // Okay now we need to start the new activity, replacing the 3599 // currently running activity. This is a little tricky because 3600 // we want to start the new one as if the current one is finished, 3601 // but not finish the current one first so that there is no flicker. 3602 // And thus... 3603 final boolean wasFinishing = r.finishing; 3604 r.finishing = true; 3605 3606 // Propagate reply information over to the new activity. 3607 final ActivityRecord resultTo = r.resultTo; 3608 final String resultWho = r.resultWho; 3609 final int requestCode = r.requestCode; 3610 r.resultTo = null; 3611 if (resultTo != null) { 3612 resultTo.removeResultsLocked(r, resultWho, requestCode); 3613 } 3614 3615 final long origId = Binder.clearCallingIdentity(); 3616 int res = mStackSupervisor.startActivityLocked(r.app.thread, intent, 3617 r.resolvedType, aInfo, null, null, resultTo != null ? resultTo.appToken : null, 3618 resultWho, requestCode, -1, r.launchedFromUid, r.launchedFromPackage, 0, 3619 options, false, null, null); 3620 Binder.restoreCallingIdentity(origId); 3621 3622 r.finishing = wasFinishing; 3623 if (res != ActivityManager.START_SUCCESS) { 3624 return false; 3625 } 3626 return true; 3627 } 3628 } 3629 3630 @Override 3631 public final int startActivityFromRecents(int taskId, Bundle options) { 3632 if (checkCallingPermission(START_TASKS_FROM_RECENTS) != PackageManager.PERMISSION_GRANTED) { 3633 String msg = "Permission Denial: startActivityFromRecents called without " + 3634 START_TASKS_FROM_RECENTS; 3635 Slog.w(TAG, msg); 3636 throw new SecurityException(msg); 3637 } 3638 final int callingUid; 3639 final String callingPackage; 3640 final Intent intent; 3641 final int userId; 3642 synchronized (this) { 3643 final TaskRecord task = recentTaskForIdLocked(taskId); 3644 if (task == null) { 3645 throw new ActivityNotFoundException("Task " + taskId + " not found."); 3646 } 3647 callingUid = task.mCallingUid; 3648 callingPackage = task.mCallingPackage; 3649 intent = task.intent; 3650 userId = task.userId; 3651 } 3652 return startActivityInPackage(callingUid, callingPackage, intent, null, null, null, 0, 0, 3653 options, userId, null); 3654 } 3655 3656 final int startActivityInPackage(int uid, String callingPackage, 3657 Intent intent, String resolvedType, IBinder resultTo, 3658 String resultWho, int requestCode, int startFlags, Bundle options, int userId, 3659 IActivityContainer container) { 3660 3661 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3662 false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 3663 3664 // TODO: Switch to user app stacks here. 3665 int ret = mStackSupervisor.startActivityMayWait(null, uid, callingPackage, intent, resolvedType, 3666 null, null, resultTo, resultWho, requestCode, startFlags, 3667 null, null, null, null, options, userId, container); 3668 return ret; 3669 } 3670 3671 @Override 3672 public final int startActivities(IApplicationThread caller, String callingPackage, 3673 Intent[] intents, String[] resolvedTypes, IBinder resultTo, Bundle options, 3674 int userId) { 3675 enforceNotIsolatedCaller("startActivities"); 3676 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3677 false, ALLOW_FULL_ONLY, "startActivity", null); 3678 // TODO: Switch to user app stacks here. 3679 int ret = mStackSupervisor.startActivities(caller, -1, callingPackage, intents, 3680 resolvedTypes, resultTo, options, userId); 3681 return ret; 3682 } 3683 3684 final int startActivitiesInPackage(int uid, String callingPackage, 3685 Intent[] intents, String[] resolvedTypes, IBinder resultTo, 3686 Bundle options, int userId) { 3687 3688 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3689 false, ALLOW_FULL_ONLY, "startActivityInPackage", null); 3690 // TODO: Switch to user app stacks here. 3691 int ret = mStackSupervisor.startActivities(null, uid, callingPackage, intents, resolvedTypes, 3692 resultTo, options, userId); 3693 return ret; 3694 } 3695 3696 //explicitly remove thd old information in mRecentTasks when removing existing user. 3697 private void removeRecentTasksForUserLocked(int userId) { 3698 if(userId <= 0) { 3699 Slog.i(TAG, "Can't remove recent task on user " + userId); 3700 return; 3701 } 3702 3703 for (int i = mRecentTasks.size() - 1; i >= 0; --i) { 3704 TaskRecord tr = mRecentTasks.get(i); 3705 if (tr.userId == userId) { 3706 if(DEBUG_TASKS) Slog.i(TAG, "remove RecentTask " + tr 3707 + " when finishing user" + userId); 3708 tr.disposeThumbnail(); 3709 mRecentTasks.remove(i); 3710 } 3711 } 3712 3713 // Remove tasks from persistent storage. 3714 mTaskPersister.wakeup(null, true); 3715 } 3716 3717 final void addRecentTaskLocked(TaskRecord task) { 3718 int N = mRecentTasks.size(); 3719 // Quick case: check if the top-most recent task is the same. 3720 if (N > 0 && mRecentTasks.get(0) == task) { 3721 return; 3722 } 3723 // Another quick case: never add voice sessions. 3724 if (task.voiceSession != null) { 3725 return; 3726 } 3727 // Remove any existing entries that are the same kind of task. 3728 final Intent intent = task.intent; 3729 final boolean document = intent != null && intent.isDocument(); 3730 final ComponentName comp = intent.getComponent(); 3731 3732 int maxRecents = task.maxRecents - 1; 3733 for (int i=0; i<N; i++) { 3734 final TaskRecord tr = mRecentTasks.get(i); 3735 if (task != tr) { 3736 if (task.userId != tr.userId) { 3737 continue; 3738 } 3739 if (i > MAX_RECENT_BITMAPS) { 3740 tr.freeLastThumbnail(); 3741 } 3742 final Intent trIntent = tr.intent; 3743 if ((task.affinity == null || !task.affinity.equals(tr.affinity)) && 3744 (intent == null || !intent.filterEquals(trIntent))) { 3745 continue; 3746 } 3747 final boolean trIsDocument = trIntent != null && trIntent.isDocument(); 3748 if (document && trIsDocument) { 3749 // These are the same document activity (not necessarily the same doc). 3750 if (maxRecents > 0) { 3751 --maxRecents; 3752 continue; 3753 } 3754 // Hit the maximum number of documents for this task. Fall through 3755 // and remove this document from recents. 3756 } else if (document || trIsDocument) { 3757 // Only one of these is a document. Not the droid we're looking for. 3758 continue; 3759 } 3760 } 3761 3762 // Either task and tr are the same or, their affinities match or their intents match 3763 // and neither of them is a document, or they are documents using the same activity 3764 // and their maxRecents has been reached. 3765 tr.disposeThumbnail(); 3766 mRecentTasks.remove(i); 3767 if (task != tr) { 3768 tr.closeRecentsChain(); 3769 } 3770 i--; 3771 N--; 3772 if (task.intent == null) { 3773 // If the new recent task we are adding is not fully 3774 // specified, then replace it with the existing recent task. 3775 task = tr; 3776 } 3777 notifyTaskPersisterLocked(tr, false); 3778 } 3779 if (N >= MAX_RECENT_TASKS) { 3780 final TaskRecord tr = mRecentTasks.remove(N - 1); 3781 tr.disposeThumbnail(); 3782 tr.closeRecentsChain(); 3783 } 3784 mRecentTasks.add(0, task); 3785 } 3786 3787 @Override 3788 public void reportActivityFullyDrawn(IBinder token) { 3789 synchronized (this) { 3790 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3791 if (r == null) { 3792 return; 3793 } 3794 r.reportFullyDrawnLocked(); 3795 } 3796 } 3797 3798 @Override 3799 public void setRequestedOrientation(IBinder token, int requestedOrientation) { 3800 synchronized (this) { 3801 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3802 if (r == null) { 3803 return; 3804 } 3805 final long origId = Binder.clearCallingIdentity(); 3806 mWindowManager.setAppOrientation(r.appToken, requestedOrientation); 3807 Configuration config = mWindowManager.updateOrientationFromAppTokens( 3808 mConfiguration, r.mayFreezeScreenLocked(r.app) ? r.appToken : null); 3809 if (config != null) { 3810 r.frozenBeforeDestroy = true; 3811 if (!updateConfigurationLocked(config, r, false, false)) { 3812 mStackSupervisor.resumeTopActivitiesLocked(); 3813 } 3814 } 3815 Binder.restoreCallingIdentity(origId); 3816 } 3817 } 3818 3819 @Override 3820 public int getRequestedOrientation(IBinder token) { 3821 synchronized (this) { 3822 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3823 if (r == null) { 3824 return ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED; 3825 } 3826 return mWindowManager.getAppOrientation(r.appToken); 3827 } 3828 } 3829 3830 /** 3831 * This is the internal entry point for handling Activity.finish(). 3832 * 3833 * @param token The Binder token referencing the Activity we want to finish. 3834 * @param resultCode Result code, if any, from this Activity. 3835 * @param resultData Result data (Intent), if any, from this Activity. 3836 * @param finishTask Whether to finish the task associated with this Activity. Only applies to 3837 * the root Activity in the task. 3838 * 3839 * @return Returns true if the activity successfully finished, or false if it is still running. 3840 */ 3841 @Override 3842 public final boolean finishActivity(IBinder token, int resultCode, Intent resultData, 3843 boolean finishTask) { 3844 // Refuse possible leaked file descriptors 3845 if (resultData != null && resultData.hasFileDescriptors() == true) { 3846 throw new IllegalArgumentException("File descriptors passed in Intent"); 3847 } 3848 3849 synchronized(this) { 3850 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3851 if (r == null) { 3852 return true; 3853 } 3854 // Keep track of the root activity of the task before we finish it 3855 TaskRecord tr = r.task; 3856 ActivityRecord rootR = tr.getRootActivity(); 3857 // Do not allow task to finish in Lock Task mode. 3858 if (tr == mStackSupervisor.mLockTaskModeTask) { 3859 if (rootR == r) { 3860 mStackSupervisor.showLockTaskToast(); 3861 return false; 3862 } 3863 } 3864 if (mController != null) { 3865 // Find the first activity that is not finishing. 3866 ActivityRecord next = r.task.stack.topRunningActivityLocked(token, 0); 3867 if (next != null) { 3868 // ask watcher if this is allowed 3869 boolean resumeOK = true; 3870 try { 3871 resumeOK = mController.activityResuming(next.packageName); 3872 } catch (RemoteException e) { 3873 mController = null; 3874 Watchdog.getInstance().setActivityController(null); 3875 } 3876 3877 if (!resumeOK) { 3878 return false; 3879 } 3880 } 3881 } 3882 final long origId = Binder.clearCallingIdentity(); 3883 try { 3884 boolean res; 3885 if (finishTask && r == rootR) { 3886 // If requested, remove the task that is associated to this activity only if it 3887 // was the root activity in the task. The result code and data is ignored because 3888 // we don't support returning them across task boundaries. 3889 res = removeTaskByIdLocked(tr.taskId, 0); 3890 } else { 3891 res = tr.stack.requestFinishActivityLocked(token, resultCode, 3892 resultData, "app-request", true); 3893 } 3894 return res; 3895 } finally { 3896 Binder.restoreCallingIdentity(origId); 3897 } 3898 } 3899 } 3900 3901 @Override 3902 public final void finishHeavyWeightApp() { 3903 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 3904 != PackageManager.PERMISSION_GRANTED) { 3905 String msg = "Permission Denial: finishHeavyWeightApp() from pid=" 3906 + Binder.getCallingPid() 3907 + ", uid=" + Binder.getCallingUid() 3908 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 3909 Slog.w(TAG, msg); 3910 throw new SecurityException(msg); 3911 } 3912 3913 synchronized(this) { 3914 if (mHeavyWeightProcess == null) { 3915 return; 3916 } 3917 3918 ArrayList<ActivityRecord> activities = new ArrayList<ActivityRecord>( 3919 mHeavyWeightProcess.activities); 3920 for (int i=0; i<activities.size(); i++) { 3921 ActivityRecord r = activities.get(i); 3922 if (!r.finishing) { 3923 r.task.stack.finishActivityLocked(r, Activity.RESULT_CANCELED, 3924 null, "finish-heavy", true); 3925 } 3926 } 3927 3928 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 3929 mHeavyWeightProcess.userId, 0)); 3930 mHeavyWeightProcess = null; 3931 } 3932 } 3933 3934 @Override 3935 public void crashApplication(int uid, int initialPid, String packageName, 3936 String message) { 3937 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 3938 != PackageManager.PERMISSION_GRANTED) { 3939 String msg = "Permission Denial: crashApplication() from pid=" 3940 + Binder.getCallingPid() 3941 + ", uid=" + Binder.getCallingUid() 3942 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 3943 Slog.w(TAG, msg); 3944 throw new SecurityException(msg); 3945 } 3946 3947 synchronized(this) { 3948 ProcessRecord proc = null; 3949 3950 // Figure out which process to kill. We don't trust that initialPid 3951 // still has any relation to current pids, so must scan through the 3952 // list. 3953 synchronized (mPidsSelfLocked) { 3954 for (int i=0; i<mPidsSelfLocked.size(); i++) { 3955 ProcessRecord p = mPidsSelfLocked.valueAt(i); 3956 if (p.uid != uid) { 3957 continue; 3958 } 3959 if (p.pid == initialPid) { 3960 proc = p; 3961 break; 3962 } 3963 if (p.pkgList.containsKey(packageName)) { 3964 proc = p; 3965 } 3966 } 3967 } 3968 3969 if (proc == null) { 3970 Slog.w(TAG, "crashApplication: nothing for uid=" + uid 3971 + " initialPid=" + initialPid 3972 + " packageName=" + packageName); 3973 return; 3974 } 3975 3976 if (proc.thread != null) { 3977 if (proc.pid == Process.myPid()) { 3978 Log.w(TAG, "crashApplication: trying to crash self!"); 3979 return; 3980 } 3981 long ident = Binder.clearCallingIdentity(); 3982 try { 3983 proc.thread.scheduleCrash(message); 3984 } catch (RemoteException e) { 3985 } 3986 Binder.restoreCallingIdentity(ident); 3987 } 3988 } 3989 } 3990 3991 @Override 3992 public final void finishSubActivity(IBinder token, String resultWho, 3993 int requestCode) { 3994 synchronized(this) { 3995 final long origId = Binder.clearCallingIdentity(); 3996 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3997 if (r != null) { 3998 r.task.stack.finishSubActivityLocked(r, resultWho, requestCode); 3999 } 4000 Binder.restoreCallingIdentity(origId); 4001 } 4002 } 4003 4004 @Override 4005 public boolean finishActivityAffinity(IBinder token) { 4006 synchronized(this) { 4007 final long origId = Binder.clearCallingIdentity(); 4008 try { 4009 ActivityRecord r = ActivityRecord.isInStackLocked(token); 4010 4011 ActivityRecord rootR = r.task.getRootActivity(); 4012 // Do not allow task to finish in Lock Task mode. 4013 if (r.task == mStackSupervisor.mLockTaskModeTask) { 4014 if (rootR == r) { 4015 mStackSupervisor.showLockTaskToast(); 4016 return false; 4017 } 4018 } 4019 boolean res = false; 4020 if (r != null) { 4021 res = r.task.stack.finishActivityAffinityLocked(r); 4022 } 4023 return res; 4024 } finally { 4025 Binder.restoreCallingIdentity(origId); 4026 } 4027 } 4028 } 4029 4030 @Override 4031 public void finishVoiceTask(IVoiceInteractionSession session) { 4032 synchronized(this) { 4033 final long origId = Binder.clearCallingIdentity(); 4034 try { 4035 mStackSupervisor.finishVoiceTask(session); 4036 } finally { 4037 Binder.restoreCallingIdentity(origId); 4038 } 4039 } 4040 4041 } 4042 4043 @Override 4044 public boolean willActivityBeVisible(IBinder token) { 4045 synchronized(this) { 4046 ActivityStack stack = ActivityRecord.getStackLocked(token); 4047 if (stack != null) { 4048 return stack.willActivityBeVisibleLocked(token); 4049 } 4050 return false; 4051 } 4052 } 4053 4054 @Override 4055 public void overridePendingTransition(IBinder token, String packageName, 4056 int enterAnim, int exitAnim) { 4057 synchronized(this) { 4058 ActivityRecord self = ActivityRecord.isInStackLocked(token); 4059 if (self == null) { 4060 return; 4061 } 4062 4063 final long origId = Binder.clearCallingIdentity(); 4064 4065 if (self.state == ActivityState.RESUMED 4066 || self.state == ActivityState.PAUSING) { 4067 mWindowManager.overridePendingAppTransition(packageName, 4068 enterAnim, exitAnim, null); 4069 } 4070 4071 Binder.restoreCallingIdentity(origId); 4072 } 4073 } 4074 4075 /** 4076 * Main function for removing an existing process from the activity manager 4077 * as a result of that process going away. Clears out all connections 4078 * to the process. 4079 */ 4080 private final void handleAppDiedLocked(ProcessRecord app, 4081 boolean restarting, boolean allowRestart) { 4082 int pid = app.pid; 4083 cleanUpApplicationRecordLocked(app, restarting, allowRestart, -1); 4084 if (!restarting) { 4085 removeLruProcessLocked(app); 4086 if (pid > 0) { 4087 ProcessList.remove(pid); 4088 } 4089 } 4090 4091 if (mProfileProc == app) { 4092 clearProfilerLocked(); 4093 } 4094 4095 // Remove this application's activities from active lists. 4096 boolean hasVisibleActivities = mStackSupervisor.handleAppDiedLocked(app); 4097 4098 app.activities.clear(); 4099 4100 if (app.instrumentationClass != null) { 4101 Slog.w(TAG, "Crash of app " + app.processName 4102 + " running instrumentation " + app.instrumentationClass); 4103 Bundle info = new Bundle(); 4104 info.putString("shortMsg", "Process crashed."); 4105 finishInstrumentationLocked(app, Activity.RESULT_CANCELED, info); 4106 } 4107 4108 if (!restarting) { 4109 if (!mStackSupervisor.resumeTopActivitiesLocked()) { 4110 // If there was nothing to resume, and we are not already 4111 // restarting this process, but there is a visible activity that 4112 // is hosted by the process... then make sure all visible 4113 // activities are running, taking care of restarting this 4114 // process. 4115 if (hasVisibleActivities) { 4116 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 4117 } 4118 } 4119 } 4120 } 4121 4122 private final int getLRURecordIndexForAppLocked(IApplicationThread thread) { 4123 IBinder threadBinder = thread.asBinder(); 4124 // Find the application record. 4125 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4126 ProcessRecord rec = mLruProcesses.get(i); 4127 if (rec.thread != null && rec.thread.asBinder() == threadBinder) { 4128 return i; 4129 } 4130 } 4131 return -1; 4132 } 4133 4134 final ProcessRecord getRecordForAppLocked( 4135 IApplicationThread thread) { 4136 if (thread == null) { 4137 return null; 4138 } 4139 4140 int appIndex = getLRURecordIndexForAppLocked(thread); 4141 return appIndex >= 0 ? mLruProcesses.get(appIndex) : null; 4142 } 4143 4144 final void doLowMemReportIfNeededLocked(ProcessRecord dyingProc) { 4145 // If there are no longer any background processes running, 4146 // and the app that died was not running instrumentation, 4147 // then tell everyone we are now low on memory. 4148 boolean haveBg = false; 4149 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4150 ProcessRecord rec = mLruProcesses.get(i); 4151 if (rec.thread != null 4152 && rec.setProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 4153 haveBg = true; 4154 break; 4155 } 4156 } 4157 4158 if (!haveBg) { 4159 boolean doReport = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 4160 if (doReport) { 4161 long now = SystemClock.uptimeMillis(); 4162 if (now < (mLastMemUsageReportTime+5*60*1000)) { 4163 doReport = false; 4164 } else { 4165 mLastMemUsageReportTime = now; 4166 } 4167 } 4168 final ArrayList<ProcessMemInfo> memInfos 4169 = doReport ? new ArrayList<ProcessMemInfo>(mLruProcesses.size()) : null; 4170 EventLog.writeEvent(EventLogTags.AM_LOW_MEMORY, mLruProcesses.size()); 4171 long now = SystemClock.uptimeMillis(); 4172 for (int i=mLruProcesses.size()-1; i>=0; i--) { 4173 ProcessRecord rec = mLruProcesses.get(i); 4174 if (rec == dyingProc || rec.thread == null) { 4175 continue; 4176 } 4177 if (doReport) { 4178 memInfos.add(new ProcessMemInfo(rec.processName, rec.pid, rec.setAdj, 4179 rec.setProcState, rec.adjType, rec.makeAdjReason())); 4180 } 4181 if ((rec.lastLowMemory+GC_MIN_INTERVAL) <= now) { 4182 // The low memory report is overriding any current 4183 // state for a GC request. Make sure to do 4184 // heavy/important/visible/foreground processes first. 4185 if (rec.setAdj <= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 4186 rec.lastRequestedGc = 0; 4187 } else { 4188 rec.lastRequestedGc = rec.lastLowMemory; 4189 } 4190 rec.reportLowMemory = true; 4191 rec.lastLowMemory = now; 4192 mProcessesToGc.remove(rec); 4193 addProcessToGcListLocked(rec); 4194 } 4195 } 4196 if (doReport) { 4197 Message msg = mHandler.obtainMessage(REPORT_MEM_USAGE_MSG, memInfos); 4198 mHandler.sendMessage(msg); 4199 } 4200 scheduleAppGcsLocked(); 4201 } 4202 } 4203 4204 final void appDiedLocked(ProcessRecord app, int pid, 4205 IApplicationThread thread) { 4206 4207 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 4208 synchronized (stats) { 4209 stats.noteProcessDiedLocked(app.info.uid, pid); 4210 } 4211 4212 Process.killProcessGroup(app.info.uid, pid); 4213 4214 // Clean up already done if the process has been re-started. 4215 if (app.pid == pid && app.thread != null && 4216 app.thread.asBinder() == thread.asBinder()) { 4217 boolean doLowMem = app.instrumentationClass == null; 4218 boolean doOomAdj = doLowMem; 4219 if (!app.killedByAm) { 4220 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4221 + ") has died."); 4222 mAllowLowerMemLevel = true; 4223 } else { 4224 // Note that we always want to do oom adj to update our state with the 4225 // new number of procs. 4226 mAllowLowerMemLevel = false; 4227 doLowMem = false; 4228 } 4229 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4230 if (DEBUG_CLEANUP) Slog.v( 4231 TAG, "Dying app: " + app + ", pid: " + pid 4232 + ", thread: " + thread.asBinder()); 4233 handleAppDiedLocked(app, false, true); 4234 4235 if (doOomAdj) { 4236 updateOomAdjLocked(); 4237 } 4238 if (doLowMem) { 4239 doLowMemReportIfNeededLocked(app); 4240 } 4241 } else if (app.pid != pid) { 4242 // A new process has already been started. 4243 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 4244 + ") has died and restarted (pid " + app.pid + ")."); 4245 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 4246 } else if (DEBUG_PROCESSES) { 4247 Slog.d(TAG, "Received spurious death notification for thread " 4248 + thread.asBinder()); 4249 } 4250 } 4251 4252 /** 4253 * If a stack trace dump file is configured, dump process stack traces. 4254 * @param clearTraces causes the dump file to be erased prior to the new 4255 * traces being written, if true; when false, the new traces will be 4256 * appended to any existing file content. 4257 * @param firstPids of dalvik VM processes to dump stack traces for first 4258 * @param lastPids of dalvik VM processes to dump stack traces for last 4259 * @param nativeProcs optional list of native process names to dump stack crawls 4260 * @return file containing stack traces, or null if no dump file is configured 4261 */ 4262 public static File dumpStackTraces(boolean clearTraces, ArrayList<Integer> firstPids, 4263 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4264 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4265 if (tracesPath == null || tracesPath.length() == 0) { 4266 return null; 4267 } 4268 4269 File tracesFile = new File(tracesPath); 4270 try { 4271 File tracesDir = tracesFile.getParentFile(); 4272 if (!tracesDir.exists()) { 4273 tracesFile.mkdirs(); 4274 if (!SELinux.restorecon(tracesDir)) { 4275 return null; 4276 } 4277 } 4278 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4279 4280 if (clearTraces && tracesFile.exists()) tracesFile.delete(); 4281 tracesFile.createNewFile(); 4282 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4283 } catch (IOException e) { 4284 Slog.w(TAG, "Unable to prepare ANR traces file: " + tracesPath, e); 4285 return null; 4286 } 4287 4288 dumpStackTraces(tracesPath, firstPids, processCpuTracker, lastPids, nativeProcs); 4289 return tracesFile; 4290 } 4291 4292 private static void dumpStackTraces(String tracesPath, ArrayList<Integer> firstPids, 4293 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4294 // Use a FileObserver to detect when traces finish writing. 4295 // The order of traces is considered important to maintain for legibility. 4296 FileObserver observer = new FileObserver(tracesPath, FileObserver.CLOSE_WRITE) { 4297 @Override 4298 public synchronized void onEvent(int event, String path) { notify(); } 4299 }; 4300 4301 try { 4302 observer.startWatching(); 4303 4304 // First collect all of the stacks of the most important pids. 4305 if (firstPids != null) { 4306 try { 4307 int num = firstPids.size(); 4308 for (int i = 0; i < num; i++) { 4309 synchronized (observer) { 4310 Process.sendSignal(firstPids.get(i), Process.SIGNAL_QUIT); 4311 observer.wait(200); // Wait for write-close, give up after 200msec 4312 } 4313 } 4314 } catch (InterruptedException e) { 4315 Log.wtf(TAG, e); 4316 } 4317 } 4318 4319 // Next collect the stacks of the native pids 4320 if (nativeProcs != null) { 4321 int[] pids = Process.getPidsForCommands(nativeProcs); 4322 if (pids != null) { 4323 for (int pid : pids) { 4324 Debug.dumpNativeBacktraceToFile(pid, tracesPath); 4325 } 4326 } 4327 } 4328 4329 // Lastly, measure CPU usage. 4330 if (processCpuTracker != null) { 4331 processCpuTracker.init(); 4332 System.gc(); 4333 processCpuTracker.update(); 4334 try { 4335 synchronized (processCpuTracker) { 4336 processCpuTracker.wait(500); // measure over 1/2 second. 4337 } 4338 } catch (InterruptedException e) { 4339 } 4340 processCpuTracker.update(); 4341 4342 // We'll take the stack crawls of just the top apps using CPU. 4343 final int N = processCpuTracker.countWorkingStats(); 4344 int numProcs = 0; 4345 for (int i=0; i<N && numProcs<5; i++) { 4346 ProcessCpuTracker.Stats stats = processCpuTracker.getWorkingStats(i); 4347 if (lastPids.indexOfKey(stats.pid) >= 0) { 4348 numProcs++; 4349 try { 4350 synchronized (observer) { 4351 Process.sendSignal(stats.pid, Process.SIGNAL_QUIT); 4352 observer.wait(200); // Wait for write-close, give up after 200msec 4353 } 4354 } catch (InterruptedException e) { 4355 Log.wtf(TAG, e); 4356 } 4357 4358 } 4359 } 4360 } 4361 } finally { 4362 observer.stopWatching(); 4363 } 4364 } 4365 4366 final void logAppTooSlow(ProcessRecord app, long startTime, String msg) { 4367 if (true || IS_USER_BUILD) { 4368 return; 4369 } 4370 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4371 if (tracesPath == null || tracesPath.length() == 0) { 4372 return; 4373 } 4374 4375 StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads(); 4376 StrictMode.allowThreadDiskWrites(); 4377 try { 4378 final File tracesFile = new File(tracesPath); 4379 final File tracesDir = tracesFile.getParentFile(); 4380 final File tracesTmp = new File(tracesDir, "__tmp__"); 4381 try { 4382 if (!tracesDir.exists()) { 4383 tracesFile.mkdirs(); 4384 if (!SELinux.restorecon(tracesDir.getPath())) { 4385 return; 4386 } 4387 } 4388 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4389 4390 if (tracesFile.exists()) { 4391 tracesTmp.delete(); 4392 tracesFile.renameTo(tracesTmp); 4393 } 4394 StringBuilder sb = new StringBuilder(); 4395 Time tobj = new Time(); 4396 tobj.set(System.currentTimeMillis()); 4397 sb.append(tobj.format("%Y-%m-%d %H:%M:%S")); 4398 sb.append(": "); 4399 TimeUtils.formatDuration(SystemClock.uptimeMillis()-startTime, sb); 4400 sb.append(" since "); 4401 sb.append(msg); 4402 FileOutputStream fos = new FileOutputStream(tracesFile); 4403 fos.write(sb.toString().getBytes()); 4404 if (app == null) { 4405 fos.write("\n*** No application process!".getBytes()); 4406 } 4407 fos.close(); 4408 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4409 } catch (IOException e) { 4410 Slog.w(TAG, "Unable to prepare slow app traces file: " + tracesPath, e); 4411 return; 4412 } 4413 4414 if (app != null) { 4415 ArrayList<Integer> firstPids = new ArrayList<Integer>(); 4416 firstPids.add(app.pid); 4417 dumpStackTraces(tracesPath, firstPids, null, null, null); 4418 } 4419 4420 File lastTracesFile = null; 4421 File curTracesFile = null; 4422 for (int i=9; i>=0; i--) { 4423 String name = String.format(Locale.US, "slow%02d.txt", i); 4424 curTracesFile = new File(tracesDir, name); 4425 if (curTracesFile.exists()) { 4426 if (lastTracesFile != null) { 4427 curTracesFile.renameTo(lastTracesFile); 4428 } else { 4429 curTracesFile.delete(); 4430 } 4431 } 4432 lastTracesFile = curTracesFile; 4433 } 4434 tracesFile.renameTo(curTracesFile); 4435 if (tracesTmp.exists()) { 4436 tracesTmp.renameTo(tracesFile); 4437 } 4438 } finally { 4439 StrictMode.setThreadPolicy(oldPolicy); 4440 } 4441 } 4442 4443 final void appNotResponding(ProcessRecord app, ActivityRecord activity, 4444 ActivityRecord parent, boolean aboveSystem, final String annotation) { 4445 ArrayList<Integer> firstPids = new ArrayList<Integer>(5); 4446 SparseArray<Boolean> lastPids = new SparseArray<Boolean>(20); 4447 4448 if (mController != null) { 4449 try { 4450 // 0 == continue, -1 = kill process immediately 4451 int res = mController.appEarlyNotResponding(app.processName, app.pid, annotation); 4452 if (res < 0 && app.pid != MY_PID) { 4453 Process.killProcess(app.pid); 4454 Process.killProcessGroup(app.info.uid, app.pid); 4455 } 4456 } catch (RemoteException e) { 4457 mController = null; 4458 Watchdog.getInstance().setActivityController(null); 4459 } 4460 } 4461 4462 long anrTime = SystemClock.uptimeMillis(); 4463 if (MONITOR_CPU_USAGE) { 4464 updateCpuStatsNow(); 4465 } 4466 4467 synchronized (this) { 4468 // PowerManager.reboot() can block for a long time, so ignore ANRs while shutting down. 4469 if (mShuttingDown) { 4470 Slog.i(TAG, "During shutdown skipping ANR: " + app + " " + annotation); 4471 return; 4472 } else if (app.notResponding) { 4473 Slog.i(TAG, "Skipping duplicate ANR: " + app + " " + annotation); 4474 return; 4475 } else if (app.crashing) { 4476 Slog.i(TAG, "Crashing app skipping ANR: " + app + " " + annotation); 4477 return; 4478 } 4479 4480 // In case we come through here for the same app before completing 4481 // this one, mark as anring now so we will bail out. 4482 app.notResponding = true; 4483 4484 // Log the ANR to the event log. 4485 EventLog.writeEvent(EventLogTags.AM_ANR, app.userId, app.pid, 4486 app.processName, app.info.flags, annotation); 4487 4488 // Dump thread traces as quickly as we can, starting with "interesting" processes. 4489 firstPids.add(app.pid); 4490 4491 int parentPid = app.pid; 4492 if (parent != null && parent.app != null && parent.app.pid > 0) parentPid = parent.app.pid; 4493 if (parentPid != app.pid) firstPids.add(parentPid); 4494 4495 if (MY_PID != app.pid && MY_PID != parentPid) firstPids.add(MY_PID); 4496 4497 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 4498 ProcessRecord r = mLruProcesses.get(i); 4499 if (r != null && r.thread != null) { 4500 int pid = r.pid; 4501 if (pid > 0 && pid != app.pid && pid != parentPid && pid != MY_PID) { 4502 if (r.persistent) { 4503 firstPids.add(pid); 4504 } else { 4505 lastPids.put(pid, Boolean.TRUE); 4506 } 4507 } 4508 } 4509 } 4510 } 4511 4512 // Log the ANR to the main log. 4513 StringBuilder info = new StringBuilder(); 4514 info.setLength(0); 4515 info.append("ANR in ").append(app.processName); 4516 if (activity != null && activity.shortComponentName != null) { 4517 info.append(" (").append(activity.shortComponentName).append(")"); 4518 } 4519 info.append("\n"); 4520 info.append("PID: ").append(app.pid).append("\n"); 4521 if (annotation != null) { 4522 info.append("Reason: ").append(annotation).append("\n"); 4523 } 4524 if (parent != null && parent != activity) { 4525 info.append("Parent: ").append(parent.shortComponentName).append("\n"); 4526 } 4527 4528 final ProcessCpuTracker processCpuTracker = new ProcessCpuTracker(true); 4529 4530 File tracesFile = dumpStackTraces(true, firstPids, processCpuTracker, lastPids, 4531 NATIVE_STACKS_OF_INTEREST); 4532 4533 String cpuInfo = null; 4534 if (MONITOR_CPU_USAGE) { 4535 updateCpuStatsNow(); 4536 synchronized (mProcessCpuThread) { 4537 cpuInfo = mProcessCpuTracker.printCurrentState(anrTime); 4538 } 4539 info.append(processCpuTracker.printCurrentLoad()); 4540 info.append(cpuInfo); 4541 } 4542 4543 info.append(processCpuTracker.printCurrentState(anrTime)); 4544 4545 Slog.e(TAG, info.toString()); 4546 if (tracesFile == null) { 4547 // There is no trace file, so dump (only) the alleged culprit's threads to the log 4548 Process.sendSignal(app.pid, Process.SIGNAL_QUIT); 4549 } 4550 4551 addErrorToDropBox("anr", app, app.processName, activity, parent, annotation, 4552 cpuInfo, tracesFile, null); 4553 4554 if (mController != null) { 4555 try { 4556 // 0 == show dialog, 1 = keep waiting, -1 = kill process immediately 4557 int res = mController.appNotResponding(app.processName, app.pid, info.toString()); 4558 if (res != 0) { 4559 if (res < 0 && app.pid != MY_PID) { 4560 Process.killProcess(app.pid); 4561 Process.killProcessGroup(app.info.uid, app.pid); 4562 } else { 4563 synchronized (this) { 4564 mServices.scheduleServiceTimeoutLocked(app); 4565 } 4566 } 4567 return; 4568 } 4569 } catch (RemoteException e) { 4570 mController = null; 4571 Watchdog.getInstance().setActivityController(null); 4572 } 4573 } 4574 4575 // Unless configured otherwise, swallow ANRs in background processes & kill the process. 4576 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 4577 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 4578 4579 synchronized (this) { 4580 if (!showBackground && !app.isInterestingToUserLocked() && app.pid != MY_PID) { 4581 killUnneededProcessLocked(app, "background ANR"); 4582 return; 4583 } 4584 4585 // Set the app's notResponding state, and look up the errorReportReceiver 4586 makeAppNotRespondingLocked(app, 4587 activity != null ? activity.shortComponentName : null, 4588 annotation != null ? "ANR " + annotation : "ANR", 4589 info.toString()); 4590 4591 // Bring up the infamous App Not Responding dialog 4592 Message msg = Message.obtain(); 4593 HashMap<String, Object> map = new HashMap<String, Object>(); 4594 msg.what = SHOW_NOT_RESPONDING_MSG; 4595 msg.obj = map; 4596 msg.arg1 = aboveSystem ? 1 : 0; 4597 map.put("app", app); 4598 if (activity != null) { 4599 map.put("activity", activity); 4600 } 4601 4602 mHandler.sendMessage(msg); 4603 } 4604 } 4605 4606 final void showLaunchWarningLocked(final ActivityRecord cur, final ActivityRecord next) { 4607 if (!mLaunchWarningShown) { 4608 mLaunchWarningShown = true; 4609 mHandler.post(new Runnable() { 4610 @Override 4611 public void run() { 4612 synchronized (ActivityManagerService.this) { 4613 final Dialog d = new LaunchWarningWindow(mContext, cur, next); 4614 d.show(); 4615 mHandler.postDelayed(new Runnable() { 4616 @Override 4617 public void run() { 4618 synchronized (ActivityManagerService.this) { 4619 d.dismiss(); 4620 mLaunchWarningShown = false; 4621 } 4622 } 4623 }, 4000); 4624 } 4625 } 4626 }); 4627 } 4628 } 4629 4630 @Override 4631 public boolean clearApplicationUserData(final String packageName, 4632 final IPackageDataObserver observer, int userId) { 4633 enforceNotIsolatedCaller("clearApplicationUserData"); 4634 int uid = Binder.getCallingUid(); 4635 int pid = Binder.getCallingPid(); 4636 userId = handleIncomingUser(pid, uid, 4637 userId, false, ALLOW_FULL_ONLY, "clearApplicationUserData", null); 4638 long callingId = Binder.clearCallingIdentity(); 4639 try { 4640 IPackageManager pm = AppGlobals.getPackageManager(); 4641 int pkgUid = -1; 4642 synchronized(this) { 4643 try { 4644 pkgUid = pm.getPackageUid(packageName, userId); 4645 } catch (RemoteException e) { 4646 } 4647 if (pkgUid == -1) { 4648 Slog.w(TAG, "Invalid packageName: " + packageName); 4649 if (observer != null) { 4650 try { 4651 observer.onRemoveCompleted(packageName, false); 4652 } catch (RemoteException e) { 4653 Slog.i(TAG, "Observer no longer exists."); 4654 } 4655 } 4656 return false; 4657 } 4658 if (uid == pkgUid || checkComponentPermission( 4659 android.Manifest.permission.CLEAR_APP_USER_DATA, 4660 pid, uid, -1, true) 4661 == PackageManager.PERMISSION_GRANTED) { 4662 forceStopPackageLocked(packageName, pkgUid, "clear data"); 4663 } else { 4664 throw new SecurityException("PID " + pid + " does not have permission " 4665 + android.Manifest.permission.CLEAR_APP_USER_DATA + " to clear data" 4666 + " of package " + packageName); 4667 } 4668 } 4669 4670 try { 4671 // Clear application user data 4672 pm.clearApplicationUserData(packageName, observer, userId); 4673 4674 // Remove all permissions granted from/to this package 4675 removeUriPermissionsForPackageLocked(packageName, userId, true); 4676 4677 Intent intent = new Intent(Intent.ACTION_PACKAGE_DATA_CLEARED, 4678 Uri.fromParts("package", packageName, null)); 4679 intent.putExtra(Intent.EXTRA_UID, pkgUid); 4680 broadcastIntentInPackage("android", Process.SYSTEM_UID, intent, 4681 null, null, 0, null, null, null, false, false, userId); 4682 } catch (RemoteException e) { 4683 } 4684 } finally { 4685 Binder.restoreCallingIdentity(callingId); 4686 } 4687 return true; 4688 } 4689 4690 @Override 4691 public void killBackgroundProcesses(final String packageName, int userId) { 4692 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 4693 != PackageManager.PERMISSION_GRANTED && 4694 checkCallingPermission(android.Manifest.permission.RESTART_PACKAGES) 4695 != PackageManager.PERMISSION_GRANTED) { 4696 String msg = "Permission Denial: killBackgroundProcesses() from pid=" 4697 + Binder.getCallingPid() 4698 + ", uid=" + Binder.getCallingUid() 4699 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 4700 Slog.w(TAG, msg); 4701 throw new SecurityException(msg); 4702 } 4703 4704 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4705 userId, true, ALLOW_FULL_ONLY, "killBackgroundProcesses", null); 4706 long callingId = Binder.clearCallingIdentity(); 4707 try { 4708 IPackageManager pm = AppGlobals.getPackageManager(); 4709 synchronized(this) { 4710 int appId = -1; 4711 try { 4712 appId = UserHandle.getAppId(pm.getPackageUid(packageName, 0)); 4713 } catch (RemoteException e) { 4714 } 4715 if (appId == -1) { 4716 Slog.w(TAG, "Invalid packageName: " + packageName); 4717 return; 4718 } 4719 killPackageProcessesLocked(packageName, appId, userId, 4720 ProcessList.SERVICE_ADJ, false, true, true, false, "kill background"); 4721 } 4722 } finally { 4723 Binder.restoreCallingIdentity(callingId); 4724 } 4725 } 4726 4727 @Override 4728 public void killAllBackgroundProcesses() { 4729 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 4730 != PackageManager.PERMISSION_GRANTED) { 4731 String msg = "Permission Denial: killAllBackgroundProcesses() from pid=" 4732 + Binder.getCallingPid() 4733 + ", uid=" + Binder.getCallingUid() 4734 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 4735 Slog.w(TAG, msg); 4736 throw new SecurityException(msg); 4737 } 4738 4739 long callingId = Binder.clearCallingIdentity(); 4740 try { 4741 synchronized(this) { 4742 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 4743 final int NP = mProcessNames.getMap().size(); 4744 for (int ip=0; ip<NP; ip++) { 4745 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 4746 final int NA = apps.size(); 4747 for (int ia=0; ia<NA; ia++) { 4748 ProcessRecord app = apps.valueAt(ia); 4749 if (app.persistent) { 4750 // we don't kill persistent processes 4751 continue; 4752 } 4753 if (app.removed) { 4754 procs.add(app); 4755 } else if (app.setAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 4756 app.removed = true; 4757 procs.add(app); 4758 } 4759 } 4760 } 4761 4762 int N = procs.size(); 4763 for (int i=0; i<N; i++) { 4764 removeProcessLocked(procs.get(i), false, true, "kill all background"); 4765 } 4766 mAllowLowerMemLevel = true; 4767 updateOomAdjLocked(); 4768 doLowMemReportIfNeededLocked(null); 4769 } 4770 } finally { 4771 Binder.restoreCallingIdentity(callingId); 4772 } 4773 } 4774 4775 @Override 4776 public void forceStopPackage(final String packageName, int userId) { 4777 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4778 != PackageManager.PERMISSION_GRANTED) { 4779 String msg = "Permission Denial: forceStopPackage() from pid=" 4780 + Binder.getCallingPid() 4781 + ", uid=" + Binder.getCallingUid() 4782 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4783 Slog.w(TAG, msg); 4784 throw new SecurityException(msg); 4785 } 4786 final int callingPid = Binder.getCallingPid(); 4787 userId = handleIncomingUser(callingPid, Binder.getCallingUid(), 4788 userId, true, ALLOW_FULL_ONLY, "forceStopPackage", null); 4789 long callingId = Binder.clearCallingIdentity(); 4790 try { 4791 IPackageManager pm = AppGlobals.getPackageManager(); 4792 synchronized(this) { 4793 int[] users = userId == UserHandle.USER_ALL 4794 ? getUsersLocked() : new int[] { userId }; 4795 for (int user : users) { 4796 int pkgUid = -1; 4797 try { 4798 pkgUid = pm.getPackageUid(packageName, user); 4799 } catch (RemoteException e) { 4800 } 4801 if (pkgUid == -1) { 4802 Slog.w(TAG, "Invalid packageName: " + packageName); 4803 continue; 4804 } 4805 try { 4806 pm.setPackageStoppedState(packageName, true, user); 4807 } catch (RemoteException e) { 4808 } catch (IllegalArgumentException e) { 4809 Slog.w(TAG, "Failed trying to unstop package " 4810 + packageName + ": " + e); 4811 } 4812 if (isUserRunningLocked(user, false)) { 4813 forceStopPackageLocked(packageName, pkgUid, "from pid " + callingPid); 4814 } 4815 } 4816 } 4817 } finally { 4818 Binder.restoreCallingIdentity(callingId); 4819 } 4820 } 4821 4822 @Override 4823 public void addPackageDependency(String packageName) { 4824 synchronized (this) { 4825 int callingPid = Binder.getCallingPid(); 4826 if (callingPid == Process.myPid()) { 4827 // Yeah, um, no. 4828 Slog.w(TAG, "Can't addPackageDependency on system process"); 4829 return; 4830 } 4831 ProcessRecord proc; 4832 synchronized (mPidsSelfLocked) { 4833 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 4834 } 4835 if (proc != null) { 4836 if (proc.pkgDeps == null) { 4837 proc.pkgDeps = new ArraySet<String>(1); 4838 } 4839 proc.pkgDeps.add(packageName); 4840 } 4841 } 4842 } 4843 4844 /* 4845 * The pkg name and app id have to be specified. 4846 */ 4847 @Override 4848 public void killApplicationWithAppId(String pkg, int appid, String reason) { 4849 if (pkg == null) { 4850 return; 4851 } 4852 // Make sure the uid is valid. 4853 if (appid < 0) { 4854 Slog.w(TAG, "Invalid appid specified for pkg : " + pkg); 4855 return; 4856 } 4857 int callerUid = Binder.getCallingUid(); 4858 // Only the system server can kill an application 4859 if (callerUid == Process.SYSTEM_UID) { 4860 // Post an aysnc message to kill the application 4861 Message msg = mHandler.obtainMessage(KILL_APPLICATION_MSG); 4862 msg.arg1 = appid; 4863 msg.arg2 = 0; 4864 Bundle bundle = new Bundle(); 4865 bundle.putString("pkg", pkg); 4866 bundle.putString("reason", reason); 4867 msg.obj = bundle; 4868 mHandler.sendMessage(msg); 4869 } else { 4870 throw new SecurityException(callerUid + " cannot kill pkg: " + 4871 pkg); 4872 } 4873 } 4874 4875 @Override 4876 public void closeSystemDialogs(String reason) { 4877 enforceNotIsolatedCaller("closeSystemDialogs"); 4878 4879 final int pid = Binder.getCallingPid(); 4880 final int uid = Binder.getCallingUid(); 4881 final long origId = Binder.clearCallingIdentity(); 4882 try { 4883 synchronized (this) { 4884 // Only allow this from foreground processes, so that background 4885 // applications can't abuse it to prevent system UI from being shown. 4886 if (uid >= Process.FIRST_APPLICATION_UID) { 4887 ProcessRecord proc; 4888 synchronized (mPidsSelfLocked) { 4889 proc = mPidsSelfLocked.get(pid); 4890 } 4891 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 4892 Slog.w(TAG, "Ignoring closeSystemDialogs " + reason 4893 + " from background process " + proc); 4894 return; 4895 } 4896 } 4897 closeSystemDialogsLocked(reason); 4898 } 4899 } finally { 4900 Binder.restoreCallingIdentity(origId); 4901 } 4902 } 4903 4904 void closeSystemDialogsLocked(String reason) { 4905 Intent intent = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS); 4906 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4907 | Intent.FLAG_RECEIVER_FOREGROUND); 4908 if (reason != null) { 4909 intent.putExtra("reason", reason); 4910 } 4911 mWindowManager.closeSystemDialogs(reason); 4912 4913 mStackSupervisor.closeSystemDialogsLocked(); 4914 4915 broadcastIntentLocked(null, null, intent, null, 4916 null, 0, null, null, null, AppOpsManager.OP_NONE, false, false, -1, 4917 Process.SYSTEM_UID, UserHandle.USER_ALL); 4918 } 4919 4920 @Override 4921 public Debug.MemoryInfo[] getProcessMemoryInfo(int[] pids) { 4922 enforceNotIsolatedCaller("getProcessMemoryInfo"); 4923 Debug.MemoryInfo[] infos = new Debug.MemoryInfo[pids.length]; 4924 for (int i=pids.length-1; i>=0; i--) { 4925 ProcessRecord proc; 4926 int oomAdj; 4927 synchronized (this) { 4928 synchronized (mPidsSelfLocked) { 4929 proc = mPidsSelfLocked.get(pids[i]); 4930 oomAdj = proc != null ? proc.setAdj : 0; 4931 } 4932 } 4933 infos[i] = new Debug.MemoryInfo(); 4934 Debug.getMemoryInfo(pids[i], infos[i]); 4935 if (proc != null) { 4936 synchronized (this) { 4937 if (proc.thread != null && proc.setAdj == oomAdj) { 4938 // Record this for posterity if the process has been stable. 4939 proc.baseProcessTracker.addPss(infos[i].getTotalPss(), 4940 infos[i].getTotalUss(), false, proc.pkgList); 4941 } 4942 } 4943 } 4944 } 4945 return infos; 4946 } 4947 4948 @Override 4949 public long[] getProcessPss(int[] pids) { 4950 enforceNotIsolatedCaller("getProcessPss"); 4951 long[] pss = new long[pids.length]; 4952 for (int i=pids.length-1; i>=0; i--) { 4953 ProcessRecord proc; 4954 int oomAdj; 4955 synchronized (this) { 4956 synchronized (mPidsSelfLocked) { 4957 proc = mPidsSelfLocked.get(pids[i]); 4958 oomAdj = proc != null ? proc.setAdj : 0; 4959 } 4960 } 4961 long[] tmpUss = new long[1]; 4962 pss[i] = Debug.getPss(pids[i], tmpUss); 4963 if (proc != null) { 4964 synchronized (this) { 4965 if (proc.thread != null && proc.setAdj == oomAdj) { 4966 // Record this for posterity if the process has been stable. 4967 proc.baseProcessTracker.addPss(pss[i], tmpUss[0], false, proc.pkgList); 4968 } 4969 } 4970 } 4971 } 4972 return pss; 4973 } 4974 4975 @Override 4976 public void killApplicationProcess(String processName, int uid) { 4977 if (processName == null) { 4978 return; 4979 } 4980 4981 int callerUid = Binder.getCallingUid(); 4982 // Only the system server can kill an application 4983 if (callerUid == Process.SYSTEM_UID) { 4984 synchronized (this) { 4985 ProcessRecord app = getProcessRecordLocked(processName, uid, true); 4986 if (app != null && app.thread != null) { 4987 try { 4988 app.thread.scheduleSuicide(); 4989 } catch (RemoteException e) { 4990 // If the other end already died, then our work here is done. 4991 } 4992 } else { 4993 Slog.w(TAG, "Process/uid not found attempting kill of " 4994 + processName + " / " + uid); 4995 } 4996 } 4997 } else { 4998 throw new SecurityException(callerUid + " cannot kill app process: " + 4999 processName); 5000 } 5001 } 5002 5003 private void forceStopPackageLocked(final String packageName, int uid, String reason) { 5004 forceStopPackageLocked(packageName, UserHandle.getAppId(uid), false, 5005 false, true, false, false, UserHandle.getUserId(uid), reason); 5006 Intent intent = new Intent(Intent.ACTION_PACKAGE_RESTARTED, 5007 Uri.fromParts("package", packageName, null)); 5008 if (!mProcessesReady) { 5009 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5010 | Intent.FLAG_RECEIVER_FOREGROUND); 5011 } 5012 intent.putExtra(Intent.EXTRA_UID, uid); 5013 intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(uid)); 5014 broadcastIntentLocked(null, null, intent, 5015 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 5016 false, false, 5017 MY_PID, Process.SYSTEM_UID, UserHandle.getUserId(uid)); 5018 } 5019 5020 private void forceStopUserLocked(int userId, String reason) { 5021 forceStopPackageLocked(null, -1, false, false, true, false, false, userId, reason); 5022 Intent intent = new Intent(Intent.ACTION_USER_STOPPED); 5023 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 5024 | Intent.FLAG_RECEIVER_FOREGROUND); 5025 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 5026 broadcastIntentLocked(null, null, intent, 5027 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 5028 false, false, 5029 MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 5030 } 5031 5032 private final boolean killPackageProcessesLocked(String packageName, int appId, 5033 int userId, int minOomAdj, boolean callerWillRestart, boolean allowRestart, 5034 boolean doit, boolean evenPersistent, String reason) { 5035 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 5036 5037 // Remove all processes this package may have touched: all with the 5038 // same UID (except for the system or root user), and all whose name 5039 // matches the package name. 5040 final int NP = mProcessNames.getMap().size(); 5041 for (int ip=0; ip<NP; ip++) { 5042 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 5043 final int NA = apps.size(); 5044 for (int ia=0; ia<NA; ia++) { 5045 ProcessRecord app = apps.valueAt(ia); 5046 if (app.persistent && !evenPersistent) { 5047 // we don't kill persistent processes 5048 continue; 5049 } 5050 if (app.removed) { 5051 if (doit) { 5052 procs.add(app); 5053 } 5054 continue; 5055 } 5056 5057 // Skip process if it doesn't meet our oom adj requirement. 5058 if (app.setAdj < minOomAdj) { 5059 continue; 5060 } 5061 5062 // If no package is specified, we call all processes under the 5063 // give user id. 5064 if (packageName == null) { 5065 if (app.userId != userId) { 5066 continue; 5067 } 5068 if (appId >= 0 && UserHandle.getAppId(app.uid) != appId) { 5069 continue; 5070 } 5071 // Package has been specified, we want to hit all processes 5072 // that match it. We need to qualify this by the processes 5073 // that are running under the specified app and user ID. 5074 } else { 5075 final boolean isDep = app.pkgDeps != null 5076 && app.pkgDeps.contains(packageName); 5077 if (!isDep && UserHandle.getAppId(app.uid) != appId) { 5078 continue; 5079 } 5080 if (userId != UserHandle.USER_ALL && app.userId != userId) { 5081 continue; 5082 } 5083 if (!app.pkgList.containsKey(packageName) && !isDep) { 5084 continue; 5085 } 5086 } 5087 5088 // Process has passed all conditions, kill it! 5089 if (!doit) { 5090 return true; 5091 } 5092 app.removed = true; 5093 procs.add(app); 5094 } 5095 } 5096 5097 int N = procs.size(); 5098 for (int i=0; i<N; i++) { 5099 removeProcessLocked(procs.get(i), callerWillRestart, allowRestart, reason); 5100 } 5101 updateOomAdjLocked(); 5102 return N > 0; 5103 } 5104 5105 private final boolean forceStopPackageLocked(String name, int appId, 5106 boolean callerWillRestart, boolean purgeCache, boolean doit, 5107 boolean evenPersistent, boolean uninstalling, int userId, String reason) { 5108 int i; 5109 int N; 5110 5111 if (userId == UserHandle.USER_ALL && name == null) { 5112 Slog.w(TAG, "Can't force stop all processes of all users, that is insane!"); 5113 } 5114 5115 if (appId < 0 && name != null) { 5116 try { 5117 appId = UserHandle.getAppId( 5118 AppGlobals.getPackageManager().getPackageUid(name, 0)); 5119 } catch (RemoteException e) { 5120 } 5121 } 5122 5123 if (doit) { 5124 if (name != null) { 5125 Slog.i(TAG, "Force stopping " + name + " appid=" + appId 5126 + " user=" + userId + ": " + reason); 5127 } else { 5128 Slog.i(TAG, "Force stopping u" + userId + ": " + reason); 5129 } 5130 5131 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 5132 for (int ip=pmap.size()-1; ip>=0; ip--) { 5133 SparseArray<Long> ba = pmap.valueAt(ip); 5134 for (i=ba.size()-1; i>=0; i--) { 5135 boolean remove = false; 5136 final int entUid = ba.keyAt(i); 5137 if (name != null) { 5138 if (userId == UserHandle.USER_ALL) { 5139 if (UserHandle.getAppId(entUid) == appId) { 5140 remove = true; 5141 } 5142 } else { 5143 if (entUid == UserHandle.getUid(userId, appId)) { 5144 remove = true; 5145 } 5146 } 5147 } else if (UserHandle.getUserId(entUid) == userId) { 5148 remove = true; 5149 } 5150 if (remove) { 5151 ba.removeAt(i); 5152 } 5153 } 5154 if (ba.size() == 0) { 5155 pmap.removeAt(ip); 5156 } 5157 } 5158 } 5159 5160 boolean didSomething = killPackageProcessesLocked(name, appId, userId, 5161 -100, callerWillRestart, true, doit, evenPersistent, 5162 name == null ? ("stop user " + userId) : ("stop " + name)); 5163 5164 if (mStackSupervisor.forceStopPackageLocked(name, doit, evenPersistent, userId)) { 5165 if (!doit) { 5166 return true; 5167 } 5168 didSomething = true; 5169 } 5170 5171 if (mServices.forceStopLocked(name, userId, evenPersistent, doit)) { 5172 if (!doit) { 5173 return true; 5174 } 5175 didSomething = true; 5176 } 5177 5178 if (name == null) { 5179 // Remove all sticky broadcasts from this user. 5180 mStickyBroadcasts.remove(userId); 5181 } 5182 5183 ArrayList<ContentProviderRecord> providers = new ArrayList<ContentProviderRecord>(); 5184 if (mProviderMap.collectForceStopProviders(name, appId, doit, evenPersistent, 5185 userId, providers)) { 5186 if (!doit) { 5187 return true; 5188 } 5189 didSomething = true; 5190 } 5191 N = providers.size(); 5192 for (i=0; i<N; i++) { 5193 removeDyingProviderLocked(null, providers.get(i), true); 5194 } 5195 5196 // Remove transient permissions granted from/to this package/user 5197 removeUriPermissionsForPackageLocked(name, userId, false); 5198 5199 if (name == null || uninstalling) { 5200 // Remove pending intents. For now we only do this when force 5201 // stopping users, because we have some problems when doing this 5202 // for packages -- app widgets are not currently cleaned up for 5203 // such packages, so they can be left with bad pending intents. 5204 if (mIntentSenderRecords.size() > 0) { 5205 Iterator<WeakReference<PendingIntentRecord>> it 5206 = mIntentSenderRecords.values().iterator(); 5207 while (it.hasNext()) { 5208 WeakReference<PendingIntentRecord> wpir = it.next(); 5209 if (wpir == null) { 5210 it.remove(); 5211 continue; 5212 } 5213 PendingIntentRecord pir = wpir.get(); 5214 if (pir == null) { 5215 it.remove(); 5216 continue; 5217 } 5218 if (name == null) { 5219 // Stopping user, remove all objects for the user. 5220 if (pir.key.userId != userId) { 5221 // Not the same user, skip it. 5222 continue; 5223 } 5224 } else { 5225 if (UserHandle.getAppId(pir.uid) != appId) { 5226 // Different app id, skip it. 5227 continue; 5228 } 5229 if (userId != UserHandle.USER_ALL && pir.key.userId != userId) { 5230 // Different user, skip it. 5231 continue; 5232 } 5233 if (!pir.key.packageName.equals(name)) { 5234 // Different package, skip it. 5235 continue; 5236 } 5237 } 5238 if (!doit) { 5239 return true; 5240 } 5241 didSomething = true; 5242 it.remove(); 5243 pir.canceled = true; 5244 if (pir.key.activity != null) { 5245 pir.key.activity.pendingResults.remove(pir.ref); 5246 } 5247 } 5248 } 5249 } 5250 5251 if (doit) { 5252 if (purgeCache && name != null) { 5253 AttributeCache ac = AttributeCache.instance(); 5254 if (ac != null) { 5255 ac.removePackage(name); 5256 } 5257 } 5258 if (mBooted) { 5259 mStackSupervisor.resumeTopActivitiesLocked(); 5260 mStackSupervisor.scheduleIdleLocked(); 5261 } 5262 } 5263 5264 return didSomething; 5265 } 5266 5267 private final boolean removeProcessLocked(ProcessRecord app, 5268 boolean callerWillRestart, boolean allowRestart, String reason) { 5269 final String name = app.processName; 5270 final int uid = app.uid; 5271 if (DEBUG_PROCESSES) Slog.d( 5272 TAG, "Force removing proc " + app.toShortString() + " (" + name 5273 + "/" + uid + ")"); 5274 5275 mProcessNames.remove(name, uid); 5276 mIsolatedProcesses.remove(app.uid); 5277 if (mHeavyWeightProcess == app) { 5278 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5279 mHeavyWeightProcess.userId, 0)); 5280 mHeavyWeightProcess = null; 5281 } 5282 boolean needRestart = false; 5283 if (app.pid > 0 && app.pid != MY_PID) { 5284 int pid = app.pid; 5285 synchronized (mPidsSelfLocked) { 5286 mPidsSelfLocked.remove(pid); 5287 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5288 } 5289 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 5290 if (app.isolated) { 5291 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5292 } 5293 killUnneededProcessLocked(app, reason); 5294 Process.killProcessGroup(app.info.uid, app.pid); 5295 handleAppDiedLocked(app, true, allowRestart); 5296 removeLruProcessLocked(app); 5297 5298 if (app.persistent && !app.isolated) { 5299 if (!callerWillRestart) { 5300 addAppLocked(app.info, false, null /* ABI override */); 5301 } else { 5302 needRestart = true; 5303 } 5304 } 5305 } else { 5306 mRemovedProcesses.add(app); 5307 } 5308 5309 return needRestart; 5310 } 5311 5312 private final void processStartTimedOutLocked(ProcessRecord app) { 5313 final int pid = app.pid; 5314 boolean gone = false; 5315 synchronized (mPidsSelfLocked) { 5316 ProcessRecord knownApp = mPidsSelfLocked.get(pid); 5317 if (knownApp != null && knownApp.thread == null) { 5318 mPidsSelfLocked.remove(pid); 5319 gone = true; 5320 } 5321 } 5322 5323 if (gone) { 5324 Slog.w(TAG, "Process " + app + " failed to attach"); 5325 EventLog.writeEvent(EventLogTags.AM_PROCESS_START_TIMEOUT, app.userId, 5326 pid, app.uid, app.processName); 5327 mProcessNames.remove(app.processName, app.uid); 5328 mIsolatedProcesses.remove(app.uid); 5329 if (mHeavyWeightProcess == app) { 5330 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5331 mHeavyWeightProcess.userId, 0)); 5332 mHeavyWeightProcess = null; 5333 } 5334 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 5335 if (app.isolated) { 5336 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5337 } 5338 // Take care of any launching providers waiting for this process. 5339 checkAppInLaunchingProvidersLocked(app, true); 5340 // Take care of any services that are waiting for the process. 5341 mServices.processStartTimedOutLocked(app); 5342 killUnneededProcessLocked(app, "start timeout"); 5343 if (mBackupTarget != null && mBackupTarget.app.pid == pid) { 5344 Slog.w(TAG, "Unattached app died before backup, skipping"); 5345 try { 5346 IBackupManager bm = IBackupManager.Stub.asInterface( 5347 ServiceManager.getService(Context.BACKUP_SERVICE)); 5348 bm.agentDisconnected(app.info.packageName); 5349 } catch (RemoteException e) { 5350 // Can't happen; the backup manager is local 5351 } 5352 } 5353 if (isPendingBroadcastProcessLocked(pid)) { 5354 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 5355 skipPendingBroadcastLocked(pid); 5356 } 5357 } else { 5358 Slog.w(TAG, "Spurious process start timeout - pid not known for " + app); 5359 } 5360 } 5361 5362 private final boolean attachApplicationLocked(IApplicationThread thread, 5363 int pid) { 5364 5365 // Find the application record that is being attached... either via 5366 // the pid if we are running in multiple processes, or just pull the 5367 // next app record if we are emulating process with anonymous threads. 5368 ProcessRecord app; 5369 if (pid != MY_PID && pid >= 0) { 5370 synchronized (mPidsSelfLocked) { 5371 app = mPidsSelfLocked.get(pid); 5372 } 5373 } else { 5374 app = null; 5375 } 5376 5377 if (app == null) { 5378 Slog.w(TAG, "No pending application record for pid " + pid 5379 + " (IApplicationThread " + thread + "); dropping process"); 5380 EventLog.writeEvent(EventLogTags.AM_DROP_PROCESS, pid); 5381 if (pid > 0 && pid != MY_PID) { 5382 Process.killProcessQuiet(pid); 5383 //TODO: Process.killProcessGroup(app.info.uid, pid); 5384 } else { 5385 try { 5386 thread.scheduleExit(); 5387 } catch (Exception e) { 5388 // Ignore exceptions. 5389 } 5390 } 5391 return false; 5392 } 5393 5394 // If this application record is still attached to a previous 5395 // process, clean it up now. 5396 if (app.thread != null) { 5397 handleAppDiedLocked(app, true, true); 5398 } 5399 5400 // Tell the process all about itself. 5401 5402 if (localLOGV) Slog.v( 5403 TAG, "Binding process pid " + pid + " to record " + app); 5404 5405 final String processName = app.processName; 5406 try { 5407 AppDeathRecipient adr = new AppDeathRecipient( 5408 app, pid, thread); 5409 thread.asBinder().linkToDeath(adr, 0); 5410 app.deathRecipient = adr; 5411 } catch (RemoteException e) { 5412 app.resetPackageList(mProcessStats); 5413 startProcessLocked(app, "link fail", processName); 5414 return false; 5415 } 5416 5417 EventLog.writeEvent(EventLogTags.AM_PROC_BOUND, app.userId, app.pid, app.processName); 5418 5419 app.makeActive(thread, mProcessStats); 5420 app.curAdj = app.setAdj = -100; 5421 app.curSchedGroup = app.setSchedGroup = Process.THREAD_GROUP_DEFAULT; 5422 app.forcingToForeground = null; 5423 updateProcessForegroundLocked(app, false, false); 5424 app.hasShownUi = false; 5425 app.debugging = false; 5426 app.cached = false; 5427 5428 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5429 5430 boolean normalMode = mProcessesReady || isAllowedWhileBooting(app.info); 5431 List<ProviderInfo> providers = normalMode ? generateApplicationProvidersLocked(app) : null; 5432 5433 if (!normalMode) { 5434 Slog.i(TAG, "Launching preboot mode app: " + app); 5435 } 5436 5437 if (localLOGV) Slog.v( 5438 TAG, "New app record " + app 5439 + " thread=" + thread.asBinder() + " pid=" + pid); 5440 try { 5441 int testMode = IApplicationThread.DEBUG_OFF; 5442 if (mDebugApp != null && mDebugApp.equals(processName)) { 5443 testMode = mWaitForDebugger 5444 ? IApplicationThread.DEBUG_WAIT 5445 : IApplicationThread.DEBUG_ON; 5446 app.debugging = true; 5447 if (mDebugTransient) { 5448 mDebugApp = mOrigDebugApp; 5449 mWaitForDebugger = mOrigWaitForDebugger; 5450 } 5451 } 5452 String profileFile = app.instrumentationProfileFile; 5453 ParcelFileDescriptor profileFd = null; 5454 boolean profileAutoStop = false; 5455 if (mProfileApp != null && mProfileApp.equals(processName)) { 5456 mProfileProc = app; 5457 profileFile = mProfileFile; 5458 profileFd = mProfileFd; 5459 profileAutoStop = mAutoStopProfiler; 5460 } 5461 boolean enableOpenGlTrace = false; 5462 if (mOpenGlTraceApp != null && mOpenGlTraceApp.equals(processName)) { 5463 enableOpenGlTrace = true; 5464 mOpenGlTraceApp = null; 5465 } 5466 5467 // If the app is being launched for restore or full backup, set it up specially 5468 boolean isRestrictedBackupMode = false; 5469 if (mBackupTarget != null && mBackupAppName.equals(processName)) { 5470 isRestrictedBackupMode = (mBackupTarget.backupMode == BackupRecord.RESTORE) 5471 || (mBackupTarget.backupMode == BackupRecord.RESTORE_FULL) 5472 || (mBackupTarget.backupMode == BackupRecord.BACKUP_FULL); 5473 } 5474 5475 ensurePackageDexOpt(app.instrumentationInfo != null 5476 ? app.instrumentationInfo.packageName 5477 : app.info.packageName); 5478 if (app.instrumentationClass != null) { 5479 ensurePackageDexOpt(app.instrumentationClass.getPackageName()); 5480 } 5481 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Binding proc " 5482 + processName + " with config " + mConfiguration); 5483 ApplicationInfo appInfo = app.instrumentationInfo != null 5484 ? app.instrumentationInfo : app.info; 5485 app.compat = compatibilityInfoForPackageLocked(appInfo); 5486 if (profileFd != null) { 5487 profileFd = profileFd.dup(); 5488 } 5489 thread.bindApplication(processName, appInfo, providers, 5490 app.instrumentationClass, profileFile, profileFd, profileAutoStop, 5491 app.instrumentationArguments, app.instrumentationWatcher, 5492 app.instrumentationUiAutomationConnection, testMode, enableOpenGlTrace, 5493 isRestrictedBackupMode || !normalMode, app.persistent, 5494 new Configuration(mConfiguration), app.compat, getCommonServicesLocked(), 5495 mCoreSettingsObserver.getCoreSettingsLocked()); 5496 updateLruProcessLocked(app, false, null); 5497 app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis(); 5498 } catch (Exception e) { 5499 // todo: Yikes! What should we do? For now we will try to 5500 // start another process, but that could easily get us in 5501 // an infinite loop of restarting processes... 5502 Slog.w(TAG, "Exception thrown during bind!", e); 5503 5504 app.resetPackageList(mProcessStats); 5505 app.unlinkDeathRecipient(); 5506 startProcessLocked(app, "bind fail", processName); 5507 return false; 5508 } 5509 5510 // Remove this record from the list of starting applications. 5511 mPersistentStartingProcesses.remove(app); 5512 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 5513 "Attach application locked removing on hold: " + app); 5514 mProcessesOnHold.remove(app); 5515 5516 boolean badApp = false; 5517 boolean didSomething = false; 5518 5519 // See if the top visible activity is waiting to run in this process... 5520 if (normalMode) { 5521 try { 5522 if (mStackSupervisor.attachApplicationLocked(app)) { 5523 didSomething = true; 5524 } 5525 } catch (Exception e) { 5526 badApp = true; 5527 } 5528 } 5529 5530 // Find any services that should be running in this process... 5531 if (!badApp) { 5532 try { 5533 didSomething |= mServices.attachApplicationLocked(app, processName); 5534 } catch (Exception e) { 5535 badApp = true; 5536 } 5537 } 5538 5539 // Check if a next-broadcast receiver is in this process... 5540 if (!badApp && isPendingBroadcastProcessLocked(pid)) { 5541 try { 5542 didSomething |= sendPendingBroadcastsLocked(app); 5543 } catch (Exception e) { 5544 // If the app died trying to launch the receiver we declare it 'bad' 5545 badApp = true; 5546 } 5547 } 5548 5549 // Check whether the next backup agent is in this process... 5550 if (!badApp && mBackupTarget != null && mBackupTarget.appInfo.uid == app.uid) { 5551 if (DEBUG_BACKUP) Slog.v(TAG, "New app is backup target, launching agent for " + app); 5552 ensurePackageDexOpt(mBackupTarget.appInfo.packageName); 5553 try { 5554 thread.scheduleCreateBackupAgent(mBackupTarget.appInfo, 5555 compatibilityInfoForPackageLocked(mBackupTarget.appInfo), 5556 mBackupTarget.backupMode); 5557 } catch (Exception e) { 5558 Slog.w(TAG, "Exception scheduling backup agent creation: "); 5559 e.printStackTrace(); 5560 } 5561 } 5562 5563 if (badApp) { 5564 // todo: Also need to kill application to deal with all 5565 // kinds of exceptions. 5566 handleAppDiedLocked(app, false, true); 5567 return false; 5568 } 5569 5570 if (!didSomething) { 5571 updateOomAdjLocked(); 5572 } 5573 5574 return true; 5575 } 5576 5577 @Override 5578 public final void attachApplication(IApplicationThread thread) { 5579 synchronized (this) { 5580 int callingPid = Binder.getCallingPid(); 5581 final long origId = Binder.clearCallingIdentity(); 5582 attachApplicationLocked(thread, callingPid); 5583 Binder.restoreCallingIdentity(origId); 5584 } 5585 } 5586 5587 @Override 5588 public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) { 5589 final long origId = Binder.clearCallingIdentity(); 5590 synchronized (this) { 5591 ActivityStack stack = ActivityRecord.getStackLocked(token); 5592 if (stack != null) { 5593 ActivityRecord r = 5594 mStackSupervisor.activityIdleInternalLocked(token, false, config); 5595 if (stopProfiling) { 5596 if ((mProfileProc == r.app) && (mProfileFd != null)) { 5597 try { 5598 mProfileFd.close(); 5599 } catch (IOException e) { 5600 } 5601 clearProfilerLocked(); 5602 } 5603 } 5604 } 5605 } 5606 Binder.restoreCallingIdentity(origId); 5607 } 5608 5609 void postEnableScreenAfterBootLocked() { 5610 mHandler.sendEmptyMessage(ENABLE_SCREEN_AFTER_BOOT_MSG); 5611 } 5612 5613 void enableScreenAfterBoot() { 5614 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN, 5615 SystemClock.uptimeMillis()); 5616 mWindowManager.enableScreenAfterBoot(); 5617 5618 synchronized (this) { 5619 updateEventDispatchingLocked(); 5620 } 5621 } 5622 5623 @Override 5624 public void showBootMessage(final CharSequence msg, final boolean always) { 5625 enforceNotIsolatedCaller("showBootMessage"); 5626 mWindowManager.showBootMessage(msg, always); 5627 } 5628 5629 @Override 5630 public void dismissKeyguardOnNextActivity() { 5631 enforceNotIsolatedCaller("dismissKeyguardOnNextActivity"); 5632 final long token = Binder.clearCallingIdentity(); 5633 try { 5634 synchronized (this) { 5635 if (DEBUG_LOCKSCREEN) logLockScreen(""); 5636 if (mLockScreenShown) { 5637 mLockScreenShown = false; 5638 comeOutOfSleepIfNeededLocked(); 5639 } 5640 mStackSupervisor.setDismissKeyguard(true); 5641 } 5642 } finally { 5643 Binder.restoreCallingIdentity(token); 5644 } 5645 } 5646 5647 final void finishBooting() { 5648 // Register receivers to handle package update events 5649 mPackageMonitor.register(mContext, Looper.getMainLooper(), false); 5650 5651 // Let system services know. 5652 mSystemServiceManager.startBootPhase(SystemService.PHASE_BOOT_COMPLETED); 5653 5654 synchronized (this) { 5655 // Ensure that any processes we had put on hold are now started 5656 // up. 5657 final int NP = mProcessesOnHold.size(); 5658 if (NP > 0) { 5659 ArrayList<ProcessRecord> procs = 5660 new ArrayList<ProcessRecord>(mProcessesOnHold); 5661 for (int ip=0; ip<NP; ip++) { 5662 if (DEBUG_PROCESSES) Slog.v(TAG, "Starting process on hold: " 5663 + procs.get(ip)); 5664 startProcessLocked(procs.get(ip), "on-hold", null); 5665 } 5666 } 5667 5668 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 5669 // Start looking for apps that are abusing wake locks. 5670 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 5671 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 5672 // Tell anyone interested that we are done booting! 5673 SystemProperties.set("sys.boot_completed", "1"); 5674 SystemProperties.set("dev.bootcomplete", "1"); 5675 for (int i=0; i<mStartedUsers.size(); i++) { 5676 UserStartedState uss = mStartedUsers.valueAt(i); 5677 if (uss.mState == UserStartedState.STATE_BOOTING) { 5678 uss.mState = UserStartedState.STATE_RUNNING; 5679 final int userId = mStartedUsers.keyAt(i); 5680 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 5681 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 5682 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 5683 broadcastIntentLocked(null, null, intent, null, 5684 new IIntentReceiver.Stub() { 5685 @Override 5686 public void performReceive(Intent intent, int resultCode, 5687 String data, Bundle extras, boolean ordered, 5688 boolean sticky, int sendingUser) { 5689 synchronized (ActivityManagerService.this) { 5690 requestPssAllProcsLocked(SystemClock.uptimeMillis(), 5691 true, false); 5692 } 5693 } 5694 }, 5695 0, null, null, 5696 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, 5697 AppOpsManager.OP_NONE, true, false, MY_PID, Process.SYSTEM_UID, 5698 userId); 5699 } 5700 } 5701 scheduleStartProfilesLocked(); 5702 } 5703 } 5704 } 5705 5706 final void ensureBootCompleted() { 5707 boolean booting; 5708 boolean enableScreen; 5709 synchronized (this) { 5710 booting = mBooting; 5711 mBooting = false; 5712 enableScreen = !mBooted; 5713 mBooted = true; 5714 } 5715 5716 if (booting) { 5717 finishBooting(); 5718 } 5719 5720 if (enableScreen) { 5721 enableScreenAfterBoot(); 5722 } 5723 } 5724 5725 @Override 5726 public final void activityResumed(IBinder token) { 5727 final long origId = Binder.clearCallingIdentity(); 5728 synchronized(this) { 5729 ActivityStack stack = ActivityRecord.getStackLocked(token); 5730 if (stack != null) { 5731 ActivityRecord.activityResumedLocked(token); 5732 } 5733 } 5734 Binder.restoreCallingIdentity(origId); 5735 } 5736 5737 @Override 5738 public final void activityPaused(IBinder token, PersistableBundle persistentState) { 5739 final long origId = Binder.clearCallingIdentity(); 5740 synchronized(this) { 5741 ActivityStack stack = ActivityRecord.getStackLocked(token); 5742 if (stack != null) { 5743 stack.activityPausedLocked(token, false, persistentState); 5744 } 5745 } 5746 Binder.restoreCallingIdentity(origId); 5747 } 5748 5749 @Override 5750 public final void activityStopped(IBinder token, Bundle icicle, 5751 PersistableBundle persistentState, CharSequence description) { 5752 if (localLOGV) Slog.v(TAG, "Activity stopped: token=" + token); 5753 5754 // Refuse possible leaked file descriptors 5755 if (icicle != null && icicle.hasFileDescriptors()) { 5756 throw new IllegalArgumentException("File descriptors passed in Bundle"); 5757 } 5758 5759 final long origId = Binder.clearCallingIdentity(); 5760 5761 synchronized (this) { 5762 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5763 if (r != null) { 5764 r.task.stack.activityStoppedLocked(r, icicle, persistentState, description); 5765 } 5766 } 5767 5768 trimApplications(); 5769 5770 Binder.restoreCallingIdentity(origId); 5771 } 5772 5773 @Override 5774 public final void activityDestroyed(IBinder token) { 5775 if (DEBUG_SWITCH) Slog.v(TAG, "ACTIVITY DESTROYED: " + token); 5776 synchronized (this) { 5777 ActivityStack stack = ActivityRecord.getStackLocked(token); 5778 if (stack != null) { 5779 stack.activityDestroyedLocked(token); 5780 } 5781 } 5782 } 5783 5784 @Override 5785 public final void mediaResourcesReleased(IBinder token) { 5786 final long origId = Binder.clearCallingIdentity(); 5787 try { 5788 synchronized (this) { 5789 ActivityStack stack = ActivityRecord.getStackLocked(token); 5790 if (stack != null) { 5791 stack.mediaResourcesReleased(token); 5792 } 5793 } 5794 } finally { 5795 Binder.restoreCallingIdentity(origId); 5796 } 5797 } 5798 5799 @Override 5800 public final void notifyLaunchTaskBehindComplete(IBinder token) { 5801 mStackSupervisor.scheduleLaunchTaskBehindComplete(token); 5802 } 5803 5804 @Override 5805 public final void notifyEnterAnimationComplete(IBinder token) { 5806 mHandler.sendMessage(mHandler.obtainMessage(ENTER_ANIMATION_COMPLETE_MSG, token)); 5807 } 5808 5809 @Override 5810 public String getCallingPackage(IBinder token) { 5811 synchronized (this) { 5812 ActivityRecord r = getCallingRecordLocked(token); 5813 return r != null ? r.info.packageName : null; 5814 } 5815 } 5816 5817 @Override 5818 public ComponentName getCallingActivity(IBinder token) { 5819 synchronized (this) { 5820 ActivityRecord r = getCallingRecordLocked(token); 5821 return r != null ? r.intent.getComponent() : null; 5822 } 5823 } 5824 5825 private ActivityRecord getCallingRecordLocked(IBinder token) { 5826 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5827 if (r == null) { 5828 return null; 5829 } 5830 return r.resultTo; 5831 } 5832 5833 @Override 5834 public ComponentName getActivityClassForToken(IBinder token) { 5835 synchronized(this) { 5836 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5837 if (r == null) { 5838 return null; 5839 } 5840 return r.intent.getComponent(); 5841 } 5842 } 5843 5844 @Override 5845 public String getPackageForToken(IBinder token) { 5846 synchronized(this) { 5847 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5848 if (r == null) { 5849 return null; 5850 } 5851 return r.packageName; 5852 } 5853 } 5854 5855 @Override 5856 public IIntentSender getIntentSender(int type, 5857 String packageName, IBinder token, String resultWho, 5858 int requestCode, Intent[] intents, String[] resolvedTypes, 5859 int flags, Bundle options, int userId) { 5860 enforceNotIsolatedCaller("getIntentSender"); 5861 // Refuse possible leaked file descriptors 5862 if (intents != null) { 5863 if (intents.length < 1) { 5864 throw new IllegalArgumentException("Intents array length must be >= 1"); 5865 } 5866 for (int i=0; i<intents.length; i++) { 5867 Intent intent = intents[i]; 5868 if (intent != null) { 5869 if (intent.hasFileDescriptors()) { 5870 throw new IllegalArgumentException("File descriptors passed in Intent"); 5871 } 5872 if (type == ActivityManager.INTENT_SENDER_BROADCAST && 5873 (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 5874 throw new IllegalArgumentException( 5875 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 5876 } 5877 intents[i] = new Intent(intent); 5878 } 5879 } 5880 if (resolvedTypes != null && resolvedTypes.length != intents.length) { 5881 throw new IllegalArgumentException( 5882 "Intent array length does not match resolvedTypes length"); 5883 } 5884 } 5885 if (options != null) { 5886 if (options.hasFileDescriptors()) { 5887 throw new IllegalArgumentException("File descriptors passed in options"); 5888 } 5889 } 5890 5891 synchronized(this) { 5892 int callingUid = Binder.getCallingUid(); 5893 int origUserId = userId; 5894 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 5895 type == ActivityManager.INTENT_SENDER_BROADCAST, 5896 ALLOW_NON_FULL, "getIntentSender", null); 5897 if (origUserId == UserHandle.USER_CURRENT) { 5898 // We don't want to evaluate this until the pending intent is 5899 // actually executed. However, we do want to always do the 5900 // security checking for it above. 5901 userId = UserHandle.USER_CURRENT; 5902 } 5903 try { 5904 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 5905 int uid = AppGlobals.getPackageManager() 5906 .getPackageUid(packageName, UserHandle.getUserId(callingUid)); 5907 if (!UserHandle.isSameApp(callingUid, uid)) { 5908 String msg = "Permission Denial: getIntentSender() from pid=" 5909 + Binder.getCallingPid() 5910 + ", uid=" + Binder.getCallingUid() 5911 + ", (need uid=" + uid + ")" 5912 + " is not allowed to send as package " + packageName; 5913 Slog.w(TAG, msg); 5914 throw new SecurityException(msg); 5915 } 5916 } 5917 5918 return getIntentSenderLocked(type, packageName, callingUid, userId, 5919 token, resultWho, requestCode, intents, resolvedTypes, flags, options); 5920 5921 } catch (RemoteException e) { 5922 throw new SecurityException(e); 5923 } 5924 } 5925 } 5926 5927 IIntentSender getIntentSenderLocked(int type, String packageName, 5928 int callingUid, int userId, IBinder token, String resultWho, 5929 int requestCode, Intent[] intents, String[] resolvedTypes, int flags, 5930 Bundle options) { 5931 if (DEBUG_MU) 5932 Slog.v(TAG_MU, "getIntentSenderLocked(): uid=" + callingUid); 5933 ActivityRecord activity = null; 5934 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 5935 activity = ActivityRecord.isInStackLocked(token); 5936 if (activity == null) { 5937 return null; 5938 } 5939 if (activity.finishing) { 5940 return null; 5941 } 5942 } 5943 5944 final boolean noCreate = (flags&PendingIntent.FLAG_NO_CREATE) != 0; 5945 final boolean cancelCurrent = (flags&PendingIntent.FLAG_CANCEL_CURRENT) != 0; 5946 final boolean updateCurrent = (flags&PendingIntent.FLAG_UPDATE_CURRENT) != 0; 5947 flags &= ~(PendingIntent.FLAG_NO_CREATE|PendingIntent.FLAG_CANCEL_CURRENT 5948 |PendingIntent.FLAG_UPDATE_CURRENT); 5949 5950 PendingIntentRecord.Key key = new PendingIntentRecord.Key( 5951 type, packageName, activity, resultWho, 5952 requestCode, intents, resolvedTypes, flags, options, userId); 5953 WeakReference<PendingIntentRecord> ref; 5954 ref = mIntentSenderRecords.get(key); 5955 PendingIntentRecord rec = ref != null ? ref.get() : null; 5956 if (rec != null) { 5957 if (!cancelCurrent) { 5958 if (updateCurrent) { 5959 if (rec.key.requestIntent != null) { 5960 rec.key.requestIntent.replaceExtras(intents != null ? 5961 intents[intents.length - 1] : null); 5962 } 5963 if (intents != null) { 5964 intents[intents.length-1] = rec.key.requestIntent; 5965 rec.key.allIntents = intents; 5966 rec.key.allResolvedTypes = resolvedTypes; 5967 } else { 5968 rec.key.allIntents = null; 5969 rec.key.allResolvedTypes = null; 5970 } 5971 } 5972 return rec; 5973 } 5974 rec.canceled = true; 5975 mIntentSenderRecords.remove(key); 5976 } 5977 if (noCreate) { 5978 return rec; 5979 } 5980 rec = new PendingIntentRecord(this, key, callingUid); 5981 mIntentSenderRecords.put(key, rec.ref); 5982 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 5983 if (activity.pendingResults == null) { 5984 activity.pendingResults 5985 = new HashSet<WeakReference<PendingIntentRecord>>(); 5986 } 5987 activity.pendingResults.add(rec.ref); 5988 } 5989 return rec; 5990 } 5991 5992 @Override 5993 public void cancelIntentSender(IIntentSender sender) { 5994 if (!(sender instanceof PendingIntentRecord)) { 5995 return; 5996 } 5997 synchronized(this) { 5998 PendingIntentRecord rec = (PendingIntentRecord)sender; 5999 try { 6000 int uid = AppGlobals.getPackageManager() 6001 .getPackageUid(rec.key.packageName, UserHandle.getCallingUserId()); 6002 if (!UserHandle.isSameApp(uid, Binder.getCallingUid())) { 6003 String msg = "Permission Denial: cancelIntentSender() from pid=" 6004 + Binder.getCallingPid() 6005 + ", uid=" + Binder.getCallingUid() 6006 + " is not allowed to cancel packges " 6007 + rec.key.packageName; 6008 Slog.w(TAG, msg); 6009 throw new SecurityException(msg); 6010 } 6011 } catch (RemoteException e) { 6012 throw new SecurityException(e); 6013 } 6014 cancelIntentSenderLocked(rec, true); 6015 } 6016 } 6017 6018 void cancelIntentSenderLocked(PendingIntentRecord rec, boolean cleanActivity) { 6019 rec.canceled = true; 6020 mIntentSenderRecords.remove(rec.key); 6021 if (cleanActivity && rec.key.activity != null) { 6022 rec.key.activity.pendingResults.remove(rec.ref); 6023 } 6024 } 6025 6026 @Override 6027 public String getPackageForIntentSender(IIntentSender pendingResult) { 6028 if (!(pendingResult instanceof PendingIntentRecord)) { 6029 return null; 6030 } 6031 try { 6032 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6033 return res.key.packageName; 6034 } catch (ClassCastException e) { 6035 } 6036 return null; 6037 } 6038 6039 @Override 6040 public int getUidForIntentSender(IIntentSender sender) { 6041 if (sender instanceof PendingIntentRecord) { 6042 try { 6043 PendingIntentRecord res = (PendingIntentRecord)sender; 6044 return res.uid; 6045 } catch (ClassCastException e) { 6046 } 6047 } 6048 return -1; 6049 } 6050 6051 @Override 6052 public boolean isIntentSenderTargetedToPackage(IIntentSender pendingResult) { 6053 if (!(pendingResult instanceof PendingIntentRecord)) { 6054 return false; 6055 } 6056 try { 6057 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6058 if (res.key.allIntents == null) { 6059 return false; 6060 } 6061 for (int i=0; i<res.key.allIntents.length; i++) { 6062 Intent intent = res.key.allIntents[i]; 6063 if (intent.getPackage() != null && intent.getComponent() != null) { 6064 return false; 6065 } 6066 } 6067 return true; 6068 } catch (ClassCastException e) { 6069 } 6070 return false; 6071 } 6072 6073 @Override 6074 public boolean isIntentSenderAnActivity(IIntentSender pendingResult) { 6075 if (!(pendingResult instanceof PendingIntentRecord)) { 6076 return false; 6077 } 6078 try { 6079 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6080 if (res.key.type == ActivityManager.INTENT_SENDER_ACTIVITY) { 6081 return true; 6082 } 6083 return false; 6084 } catch (ClassCastException e) { 6085 } 6086 return false; 6087 } 6088 6089 @Override 6090 public Intent getIntentForIntentSender(IIntentSender pendingResult) { 6091 if (!(pendingResult instanceof PendingIntentRecord)) { 6092 return null; 6093 } 6094 try { 6095 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6096 return res.key.requestIntent != null ? new Intent(res.key.requestIntent) : null; 6097 } catch (ClassCastException e) { 6098 } 6099 return null; 6100 } 6101 6102 @Override 6103 public String getTagForIntentSender(IIntentSender pendingResult, String prefix) { 6104 if (!(pendingResult instanceof PendingIntentRecord)) { 6105 return null; 6106 } 6107 try { 6108 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 6109 Intent intent = res.key.requestIntent; 6110 if (intent != null) { 6111 if (res.lastTag != null && res.lastTagPrefix == prefix && (res.lastTagPrefix == null 6112 || res.lastTagPrefix.equals(prefix))) { 6113 return res.lastTag; 6114 } 6115 res.lastTagPrefix = prefix; 6116 StringBuilder sb = new StringBuilder(128); 6117 if (prefix != null) { 6118 sb.append(prefix); 6119 } 6120 if (intent.getAction() != null) { 6121 sb.append(intent.getAction()); 6122 } else if (intent.getComponent() != null) { 6123 intent.getComponent().appendShortString(sb); 6124 } else { 6125 sb.append("?"); 6126 } 6127 return res.lastTag = sb.toString(); 6128 } 6129 } catch (ClassCastException e) { 6130 } 6131 return null; 6132 } 6133 6134 @Override 6135 public void setProcessLimit(int max) { 6136 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 6137 "setProcessLimit()"); 6138 synchronized (this) { 6139 mProcessLimit = max < 0 ? ProcessList.MAX_CACHED_APPS : max; 6140 mProcessLimitOverride = max; 6141 } 6142 trimApplications(); 6143 } 6144 6145 @Override 6146 public int getProcessLimit() { 6147 synchronized (this) { 6148 return mProcessLimitOverride; 6149 } 6150 } 6151 6152 void foregroundTokenDied(ForegroundToken token) { 6153 synchronized (ActivityManagerService.this) { 6154 synchronized (mPidsSelfLocked) { 6155 ForegroundToken cur 6156 = mForegroundProcesses.get(token.pid); 6157 if (cur != token) { 6158 return; 6159 } 6160 mForegroundProcesses.remove(token.pid); 6161 ProcessRecord pr = mPidsSelfLocked.get(token.pid); 6162 if (pr == null) { 6163 return; 6164 } 6165 pr.forcingToForeground = null; 6166 updateProcessForegroundLocked(pr, false, false); 6167 } 6168 updateOomAdjLocked(); 6169 } 6170 } 6171 6172 @Override 6173 public void setProcessForeground(IBinder token, int pid, boolean isForeground) { 6174 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 6175 "setProcessForeground()"); 6176 synchronized(this) { 6177 boolean changed = false; 6178 6179 synchronized (mPidsSelfLocked) { 6180 ProcessRecord pr = mPidsSelfLocked.get(pid); 6181 if (pr == null && isForeground) { 6182 Slog.w(TAG, "setProcessForeground called on unknown pid: " + pid); 6183 return; 6184 } 6185 ForegroundToken oldToken = mForegroundProcesses.get(pid); 6186 if (oldToken != null) { 6187 oldToken.token.unlinkToDeath(oldToken, 0); 6188 mForegroundProcesses.remove(pid); 6189 if (pr != null) { 6190 pr.forcingToForeground = null; 6191 } 6192 changed = true; 6193 } 6194 if (isForeground && token != null) { 6195 ForegroundToken newToken = new ForegroundToken() { 6196 @Override 6197 public void binderDied() { 6198 foregroundTokenDied(this); 6199 } 6200 }; 6201 newToken.pid = pid; 6202 newToken.token = token; 6203 try { 6204 token.linkToDeath(newToken, 0); 6205 mForegroundProcesses.put(pid, newToken); 6206 pr.forcingToForeground = token; 6207 changed = true; 6208 } catch (RemoteException e) { 6209 // If the process died while doing this, we will later 6210 // do the cleanup with the process death link. 6211 } 6212 } 6213 } 6214 6215 if (changed) { 6216 updateOomAdjLocked(); 6217 } 6218 } 6219 } 6220 6221 // ========================================================= 6222 // PERMISSIONS 6223 // ========================================================= 6224 6225 static class PermissionController extends IPermissionController.Stub { 6226 ActivityManagerService mActivityManagerService; 6227 PermissionController(ActivityManagerService activityManagerService) { 6228 mActivityManagerService = activityManagerService; 6229 } 6230 6231 @Override 6232 public boolean checkPermission(String permission, int pid, int uid) { 6233 return mActivityManagerService.checkPermission(permission, pid, 6234 uid) == PackageManager.PERMISSION_GRANTED; 6235 } 6236 } 6237 6238 class IntentFirewallInterface implements IntentFirewall.AMSInterface { 6239 @Override 6240 public int checkComponentPermission(String permission, int pid, int uid, 6241 int owningUid, boolean exported) { 6242 return ActivityManagerService.this.checkComponentPermission(permission, pid, uid, 6243 owningUid, exported); 6244 } 6245 6246 @Override 6247 public Object getAMSLock() { 6248 return ActivityManagerService.this; 6249 } 6250 } 6251 6252 /** 6253 * This can be called with or without the global lock held. 6254 */ 6255 int checkComponentPermission(String permission, int pid, int uid, 6256 int owningUid, boolean exported) { 6257 // We might be performing an operation on behalf of an indirect binder 6258 // invocation, e.g. via {@link #openContentUri}. Check and adjust the 6259 // client identity accordingly before proceeding. 6260 Identity tlsIdentity = sCallerIdentity.get(); 6261 if (tlsIdentity != null) { 6262 Slog.d(TAG, "checkComponentPermission() adjusting {pid,uid} to {" 6263 + tlsIdentity.pid + "," + tlsIdentity.uid + "}"); 6264 uid = tlsIdentity.uid; 6265 pid = tlsIdentity.pid; 6266 } 6267 6268 if (pid == MY_PID) { 6269 return PackageManager.PERMISSION_GRANTED; 6270 } 6271 6272 return ActivityManager.checkComponentPermission(permission, uid, 6273 owningUid, exported); 6274 } 6275 6276 /** 6277 * As the only public entry point for permissions checking, this method 6278 * can enforce the semantic that requesting a check on a null global 6279 * permission is automatically denied. (Internally a null permission 6280 * string is used when calling {@link #checkComponentPermission} in cases 6281 * when only uid-based security is needed.) 6282 * 6283 * This can be called with or without the global lock held. 6284 */ 6285 @Override 6286 public int checkPermission(String permission, int pid, int uid) { 6287 if (permission == null) { 6288 return PackageManager.PERMISSION_DENIED; 6289 } 6290 return checkComponentPermission(permission, pid, UserHandle.getAppId(uid), -1, true); 6291 } 6292 6293 /** 6294 * Binder IPC calls go through the public entry point. 6295 * This can be called with or without the global lock held. 6296 */ 6297 int checkCallingPermission(String permission) { 6298 return checkPermission(permission, 6299 Binder.getCallingPid(), 6300 UserHandle.getAppId(Binder.getCallingUid())); 6301 } 6302 6303 /** 6304 * This can be called with or without the global lock held. 6305 */ 6306 void enforceCallingPermission(String permission, String func) { 6307 if (checkCallingPermission(permission) 6308 == PackageManager.PERMISSION_GRANTED) { 6309 return; 6310 } 6311 6312 String msg = "Permission Denial: " + func + " from pid=" 6313 + Binder.getCallingPid() 6314 + ", uid=" + Binder.getCallingUid() 6315 + " requires " + permission; 6316 Slog.w(TAG, msg); 6317 throw new SecurityException(msg); 6318 } 6319 6320 /** 6321 * Determine if UID is holding permissions required to access {@link Uri} in 6322 * the given {@link ProviderInfo}. Final permission checking is always done 6323 * in {@link ContentProvider}. 6324 */ 6325 private final boolean checkHoldingPermissionsLocked( 6326 IPackageManager pm, ProviderInfo pi, GrantUri grantUri, int uid, final int modeFlags) { 6327 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6328 "checkHoldingPermissionsLocked: uri=" + grantUri + " uid=" + uid); 6329 if (UserHandle.getUserId(uid) != grantUri.sourceUserId) { 6330 if (ActivityManager.checkComponentPermission(INTERACT_ACROSS_USERS, uid, -1, true) 6331 != PERMISSION_GRANTED) { 6332 return false; 6333 } 6334 } 6335 return checkHoldingPermissionsInternalLocked(pm, pi, grantUri, uid, modeFlags, true); 6336 } 6337 6338 private final boolean checkHoldingPermissionsInternalLocked(IPackageManager pm, ProviderInfo pi, 6339 GrantUri grantUri, int uid, final int modeFlags, boolean considerUidPermissions) { 6340 if (pi.applicationInfo.uid == uid) { 6341 return true; 6342 } else if (!pi.exported) { 6343 return false; 6344 } 6345 6346 boolean readMet = (modeFlags & Intent.FLAG_GRANT_READ_URI_PERMISSION) == 0; 6347 boolean writeMet = (modeFlags & Intent.FLAG_GRANT_WRITE_URI_PERMISSION) == 0; 6348 try { 6349 // check if target holds top-level <provider> permissions 6350 if (!readMet && pi.readPermission != null && considerUidPermissions 6351 && (pm.checkUidPermission(pi.readPermission, uid) == PERMISSION_GRANTED)) { 6352 readMet = true; 6353 } 6354 if (!writeMet && pi.writePermission != null && considerUidPermissions 6355 && (pm.checkUidPermission(pi.writePermission, uid) == PERMISSION_GRANTED)) { 6356 writeMet = true; 6357 } 6358 6359 // track if unprotected read/write is allowed; any denied 6360 // <path-permission> below removes this ability 6361 boolean allowDefaultRead = pi.readPermission == null; 6362 boolean allowDefaultWrite = pi.writePermission == null; 6363 6364 // check if target holds any <path-permission> that match uri 6365 final PathPermission[] pps = pi.pathPermissions; 6366 if (pps != null) { 6367 final String path = grantUri.uri.getPath(); 6368 int i = pps.length; 6369 while (i > 0 && (!readMet || !writeMet)) { 6370 i--; 6371 PathPermission pp = pps[i]; 6372 if (pp.match(path)) { 6373 if (!readMet) { 6374 final String pprperm = pp.getReadPermission(); 6375 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking read perm for " 6376 + pprperm + " for " + pp.getPath() 6377 + ": match=" + pp.match(path) 6378 + " check=" + pm.checkUidPermission(pprperm, uid)); 6379 if (pprperm != null) { 6380 if (considerUidPermissions && pm.checkUidPermission(pprperm, uid) 6381 == PERMISSION_GRANTED) { 6382 readMet = true; 6383 } else { 6384 allowDefaultRead = false; 6385 } 6386 } 6387 } 6388 if (!writeMet) { 6389 final String ppwperm = pp.getWritePermission(); 6390 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking write perm " 6391 + ppwperm + " for " + pp.getPath() 6392 + ": match=" + pp.match(path) 6393 + " check=" + pm.checkUidPermission(ppwperm, uid)); 6394 if (ppwperm != null) { 6395 if (considerUidPermissions && pm.checkUidPermission(ppwperm, uid) 6396 == PERMISSION_GRANTED) { 6397 writeMet = true; 6398 } else { 6399 allowDefaultWrite = false; 6400 } 6401 } 6402 } 6403 } 6404 } 6405 } 6406 6407 // grant unprotected <provider> read/write, if not blocked by 6408 // <path-permission> above 6409 if (allowDefaultRead) readMet = true; 6410 if (allowDefaultWrite) writeMet = true; 6411 6412 } catch (RemoteException e) { 6413 return false; 6414 } 6415 6416 return readMet && writeMet; 6417 } 6418 6419 private ProviderInfo getProviderInfoLocked(String authority, int userHandle) { 6420 ProviderInfo pi = null; 6421 ContentProviderRecord cpr = mProviderMap.getProviderByName(authority, userHandle); 6422 if (cpr != null) { 6423 pi = cpr.info; 6424 } else { 6425 try { 6426 pi = AppGlobals.getPackageManager().resolveContentProvider( 6427 authority, PackageManager.GET_URI_PERMISSION_PATTERNS, userHandle); 6428 } catch (RemoteException ex) { 6429 } 6430 } 6431 return pi; 6432 } 6433 6434 private UriPermission findUriPermissionLocked(int targetUid, GrantUri grantUri) { 6435 final ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6436 if (targetUris != null) { 6437 return targetUris.get(grantUri); 6438 } 6439 return null; 6440 } 6441 6442 private UriPermission findOrCreateUriPermissionLocked(String sourcePkg, 6443 String targetPkg, int targetUid, GrantUri grantUri) { 6444 ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6445 if (targetUris == null) { 6446 targetUris = Maps.newArrayMap(); 6447 mGrantedUriPermissions.put(targetUid, targetUris); 6448 } 6449 6450 UriPermission perm = targetUris.get(grantUri); 6451 if (perm == null) { 6452 perm = new UriPermission(sourcePkg, targetPkg, targetUid, grantUri); 6453 targetUris.put(grantUri, perm); 6454 } 6455 6456 return perm; 6457 } 6458 6459 private final boolean checkUriPermissionLocked(GrantUri grantUri, int uid, 6460 final int modeFlags) { 6461 final boolean persistable = (modeFlags & Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION) != 0; 6462 final int minStrength = persistable ? UriPermission.STRENGTH_PERSISTABLE 6463 : UriPermission.STRENGTH_OWNED; 6464 6465 // Root gets to do everything. 6466 if (uid == 0) { 6467 return true; 6468 } 6469 6470 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 6471 if (perms == null) return false; 6472 6473 // First look for exact match 6474 final UriPermission exactPerm = perms.get(grantUri); 6475 if (exactPerm != null && exactPerm.getStrength(modeFlags) >= minStrength) { 6476 return true; 6477 } 6478 6479 // No exact match, look for prefixes 6480 final int N = perms.size(); 6481 for (int i = 0; i < N; i++) { 6482 final UriPermission perm = perms.valueAt(i); 6483 if (perm.uri.prefix && grantUri.uri.isPathPrefixMatch(perm.uri.uri) 6484 && perm.getStrength(modeFlags) >= minStrength) { 6485 return true; 6486 } 6487 } 6488 6489 return false; 6490 } 6491 6492 @Override 6493 public int checkUriPermission(Uri uri, int pid, int uid, 6494 final int modeFlags, int userId) { 6495 enforceNotIsolatedCaller("checkUriPermission"); 6496 6497 // Another redirected-binder-call permissions check as in 6498 // {@link checkComponentPermission}. 6499 Identity tlsIdentity = sCallerIdentity.get(); 6500 if (tlsIdentity != null) { 6501 uid = tlsIdentity.uid; 6502 pid = tlsIdentity.pid; 6503 } 6504 6505 // Our own process gets to do everything. 6506 if (pid == MY_PID) { 6507 return PackageManager.PERMISSION_GRANTED; 6508 } 6509 synchronized (this) { 6510 return checkUriPermissionLocked(new GrantUri(userId, uri, false), uid, modeFlags) 6511 ? PackageManager.PERMISSION_GRANTED 6512 : PackageManager.PERMISSION_DENIED; 6513 } 6514 } 6515 6516 /** 6517 * Check if the targetPkg can be granted permission to access uri by 6518 * the callingUid using the given modeFlags. Throws a security exception 6519 * if callingUid is not allowed to do this. Returns the uid of the target 6520 * if the URI permission grant should be performed; returns -1 if it is not 6521 * needed (for example targetPkg already has permission to access the URI). 6522 * If you already know the uid of the target, you can supply it in 6523 * lastTargetUid else set that to -1. 6524 */ 6525 int checkGrantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 6526 final int modeFlags, int lastTargetUid) { 6527 if (!Intent.isAccessUriMode(modeFlags)) { 6528 return -1; 6529 } 6530 6531 if (targetPkg != null) { 6532 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6533 "Checking grant " + targetPkg + " permission to " + grantUri); 6534 } 6535 6536 final IPackageManager pm = AppGlobals.getPackageManager(); 6537 6538 // If this is not a content: uri, we can't do anything with it. 6539 if (!ContentResolver.SCHEME_CONTENT.equals(grantUri.uri.getScheme())) { 6540 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6541 "Can't grant URI permission for non-content URI: " + grantUri); 6542 return -1; 6543 } 6544 6545 final String authority = grantUri.uri.getAuthority(); 6546 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6547 if (pi == null) { 6548 Slog.w(TAG, "No content provider found for permission check: " + 6549 grantUri.uri.toSafeString()); 6550 return -1; 6551 } 6552 6553 int targetUid = lastTargetUid; 6554 if (targetUid < 0 && targetPkg != null) { 6555 try { 6556 targetUid = pm.getPackageUid(targetPkg, UserHandle.getUserId(callingUid)); 6557 if (targetUid < 0) { 6558 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6559 "Can't grant URI permission no uid for: " + targetPkg); 6560 return -1; 6561 } 6562 } catch (RemoteException ex) { 6563 return -1; 6564 } 6565 } 6566 6567 if (targetUid >= 0) { 6568 // First... does the target actually need this permission? 6569 if (checkHoldingPermissionsLocked(pm, pi, grantUri, targetUid, modeFlags)) { 6570 // No need to grant the target this permission. 6571 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6572 "Target " + targetPkg + " already has full permission to " + grantUri); 6573 return -1; 6574 } 6575 } else { 6576 // First... there is no target package, so can anyone access it? 6577 boolean allowed = pi.exported; 6578 if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) { 6579 if (pi.readPermission != null) { 6580 allowed = false; 6581 } 6582 } 6583 if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) { 6584 if (pi.writePermission != null) { 6585 allowed = false; 6586 } 6587 } 6588 if (allowed) { 6589 return -1; 6590 } 6591 } 6592 6593 /* There is a special cross user grant if: 6594 * - The target is on another user. 6595 * - Apps on the current user can access the uri without any uid permissions. 6596 * In this case, we grant a uri permission, even if the ContentProvider does not normally 6597 * grant uri permissions. 6598 */ 6599 boolean specialCrossUserGrant = UserHandle.getUserId(targetUid) != grantUri.sourceUserId 6600 && checkHoldingPermissionsInternalLocked(pm, pi, grantUri, callingUid, 6601 modeFlags, false /*without considering the uid permissions*/); 6602 6603 // Second... is the provider allowing granting of URI permissions? 6604 if (!specialCrossUserGrant) { 6605 if (!pi.grantUriPermissions) { 6606 throw new SecurityException("Provider " + pi.packageName 6607 + "/" + pi.name 6608 + " does not allow granting of Uri permissions (uri " 6609 + grantUri + ")"); 6610 } 6611 if (pi.uriPermissionPatterns != null) { 6612 final int N = pi.uriPermissionPatterns.length; 6613 boolean allowed = false; 6614 for (int i=0; i<N; i++) { 6615 if (pi.uriPermissionPatterns[i] != null 6616 && pi.uriPermissionPatterns[i].match(grantUri.uri.getPath())) { 6617 allowed = true; 6618 break; 6619 } 6620 } 6621 if (!allowed) { 6622 throw new SecurityException("Provider " + pi.packageName 6623 + "/" + pi.name 6624 + " does not allow granting of permission to path of Uri " 6625 + grantUri); 6626 } 6627 } 6628 } 6629 6630 // Third... does the caller itself have permission to access 6631 // this uri? 6632 if (UserHandle.getAppId(callingUid) != Process.SYSTEM_UID) { 6633 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 6634 // Require they hold a strong enough Uri permission 6635 if (!checkUriPermissionLocked(grantUri, callingUid, modeFlags)) { 6636 throw new SecurityException("Uid " + callingUid 6637 + " does not have permission to uri " + grantUri); 6638 } 6639 } 6640 } 6641 return targetUid; 6642 } 6643 6644 @Override 6645 public int checkGrantUriPermission(int callingUid, String targetPkg, Uri uri, 6646 final int modeFlags, int userId) { 6647 enforceNotIsolatedCaller("checkGrantUriPermission"); 6648 synchronized(this) { 6649 return checkGrantUriPermissionLocked(callingUid, targetPkg, 6650 new GrantUri(userId, uri, false), modeFlags, -1); 6651 } 6652 } 6653 6654 void grantUriPermissionUncheckedLocked(int targetUid, String targetPkg, GrantUri grantUri, 6655 final int modeFlags, UriPermissionOwner owner) { 6656 if (!Intent.isAccessUriMode(modeFlags)) { 6657 return; 6658 } 6659 6660 // So here we are: the caller has the assumed permission 6661 // to the uri, and the target doesn't. Let's now give this to 6662 // the target. 6663 6664 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6665 "Granting " + targetPkg + "/" + targetUid + " permission to " + grantUri); 6666 6667 final String authority = grantUri.uri.getAuthority(); 6668 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6669 if (pi == null) { 6670 Slog.w(TAG, "No content provider found for grant: " + grantUri.toSafeString()); 6671 return; 6672 } 6673 6674 if ((modeFlags & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0) { 6675 grantUri.prefix = true; 6676 } 6677 final UriPermission perm = findOrCreateUriPermissionLocked( 6678 pi.packageName, targetPkg, targetUid, grantUri); 6679 perm.grantModes(modeFlags, owner); 6680 } 6681 6682 void grantUriPermissionLocked(int callingUid, String targetPkg, GrantUri grantUri, 6683 final int modeFlags, UriPermissionOwner owner, int targetUserId) { 6684 if (targetPkg == null) { 6685 throw new NullPointerException("targetPkg"); 6686 } 6687 int targetUid; 6688 final IPackageManager pm = AppGlobals.getPackageManager(); 6689 try { 6690 targetUid = pm.getPackageUid(targetPkg, targetUserId); 6691 } catch (RemoteException ex) { 6692 return; 6693 } 6694 6695 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, modeFlags, 6696 targetUid); 6697 if (targetUid < 0) { 6698 return; 6699 } 6700 6701 grantUriPermissionUncheckedLocked(targetUid, targetPkg, grantUri, modeFlags, 6702 owner); 6703 } 6704 6705 static class NeededUriGrants extends ArrayList<GrantUri> { 6706 final String targetPkg; 6707 final int targetUid; 6708 final int flags; 6709 6710 NeededUriGrants(String targetPkg, int targetUid, int flags) { 6711 this.targetPkg = targetPkg; 6712 this.targetUid = targetUid; 6713 this.flags = flags; 6714 } 6715 } 6716 6717 /** 6718 * Like checkGrantUriPermissionLocked, but takes an Intent. 6719 */ 6720 NeededUriGrants checkGrantUriPermissionFromIntentLocked(int callingUid, 6721 String targetPkg, Intent intent, int mode, NeededUriGrants needed, int targetUserId) { 6722 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6723 "Checking URI perm to data=" + (intent != null ? intent.getData() : null) 6724 + " clip=" + (intent != null ? intent.getClipData() : null) 6725 + " from " + intent + "; flags=0x" 6726 + Integer.toHexString(intent != null ? intent.getFlags() : 0)); 6727 6728 if (targetPkg == null) { 6729 throw new NullPointerException("targetPkg"); 6730 } 6731 6732 if (intent == null) { 6733 return null; 6734 } 6735 Uri data = intent.getData(); 6736 ClipData clip = intent.getClipData(); 6737 if (data == null && clip == null) { 6738 return null; 6739 } 6740 // Default userId for uris in the intent (if they don't specify it themselves) 6741 int contentUserHint = intent.getContentUserHint(); 6742 if (contentUserHint == UserHandle.USER_CURRENT) { 6743 contentUserHint = UserHandle.getUserId(callingUid); 6744 } 6745 final IPackageManager pm = AppGlobals.getPackageManager(); 6746 int targetUid; 6747 if (needed != null) { 6748 targetUid = needed.targetUid; 6749 } else { 6750 try { 6751 targetUid = pm.getPackageUid(targetPkg, targetUserId); 6752 } catch (RemoteException ex) { 6753 return null; 6754 } 6755 if (targetUid < 0) { 6756 if (DEBUG_URI_PERMISSION) { 6757 Slog.v(TAG, "Can't grant URI permission no uid for: " + targetPkg 6758 + " on user " + targetUserId); 6759 } 6760 return null; 6761 } 6762 } 6763 if (data != null) { 6764 GrantUri grantUri = GrantUri.resolve(contentUserHint, data); 6765 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 6766 targetUid); 6767 if (targetUid > 0) { 6768 if (needed == null) { 6769 needed = new NeededUriGrants(targetPkg, targetUid, mode); 6770 } 6771 needed.add(grantUri); 6772 } 6773 } 6774 if (clip != null) { 6775 for (int i=0; i<clip.getItemCount(); i++) { 6776 Uri uri = clip.getItemAt(i).getUri(); 6777 if (uri != null) { 6778 GrantUri grantUri = GrantUri.resolve(contentUserHint, uri); 6779 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, grantUri, mode, 6780 targetUid); 6781 if (targetUid > 0) { 6782 if (needed == null) { 6783 needed = new NeededUriGrants(targetPkg, targetUid, mode); 6784 } 6785 needed.add(grantUri); 6786 } 6787 } else { 6788 Intent clipIntent = clip.getItemAt(i).getIntent(); 6789 if (clipIntent != null) { 6790 NeededUriGrants newNeeded = checkGrantUriPermissionFromIntentLocked( 6791 callingUid, targetPkg, clipIntent, mode, needed, targetUserId); 6792 if (newNeeded != null) { 6793 needed = newNeeded; 6794 } 6795 } 6796 } 6797 } 6798 } 6799 6800 return needed; 6801 } 6802 6803 /** 6804 * Like grantUriPermissionUncheckedLocked, but takes an Intent. 6805 */ 6806 void grantUriPermissionUncheckedFromIntentLocked(NeededUriGrants needed, 6807 UriPermissionOwner owner) { 6808 if (needed != null) { 6809 for (int i=0; i<needed.size(); i++) { 6810 GrantUri grantUri = needed.get(i); 6811 grantUriPermissionUncheckedLocked(needed.targetUid, needed.targetPkg, 6812 grantUri, needed.flags, owner); 6813 } 6814 } 6815 } 6816 6817 void grantUriPermissionFromIntentLocked(int callingUid, 6818 String targetPkg, Intent intent, UriPermissionOwner owner, int targetUserId) { 6819 NeededUriGrants needed = checkGrantUriPermissionFromIntentLocked(callingUid, targetPkg, 6820 intent, intent != null ? intent.getFlags() : 0, null, targetUserId); 6821 if (needed == null) { 6822 return; 6823 } 6824 6825 grantUriPermissionUncheckedFromIntentLocked(needed, owner); 6826 } 6827 6828 @Override 6829 public void grantUriPermission(IApplicationThread caller, String targetPkg, Uri uri, 6830 final int modeFlags, int userId) { 6831 enforceNotIsolatedCaller("grantUriPermission"); 6832 GrantUri grantUri = new GrantUri(userId, uri, false); 6833 synchronized(this) { 6834 final ProcessRecord r = getRecordForAppLocked(caller); 6835 if (r == null) { 6836 throw new SecurityException("Unable to find app for caller " 6837 + caller 6838 + " when granting permission to uri " + grantUri); 6839 } 6840 if (targetPkg == null) { 6841 throw new IllegalArgumentException("null target"); 6842 } 6843 if (grantUri == null) { 6844 throw new IllegalArgumentException("null uri"); 6845 } 6846 6847 Preconditions.checkFlagsArgument(modeFlags, Intent.FLAG_GRANT_READ_URI_PERMISSION 6848 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION 6849 | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION 6850 | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION); 6851 6852 grantUriPermissionLocked(r.uid, targetPkg, grantUri, modeFlags, null, 6853 UserHandle.getUserId(r.uid)); 6854 } 6855 } 6856 6857 void removeUriPermissionIfNeededLocked(UriPermission perm) { 6858 if (perm.modeFlags == 0) { 6859 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 6860 perm.targetUid); 6861 if (perms != null) { 6862 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6863 "Removing " + perm.targetUid + " permission to " + perm.uri); 6864 6865 perms.remove(perm.uri); 6866 if (perms.isEmpty()) { 6867 mGrantedUriPermissions.remove(perm.targetUid); 6868 } 6869 } 6870 } 6871 } 6872 6873 private void revokeUriPermissionLocked(int callingUid, GrantUri grantUri, final int modeFlags) { 6874 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Revoking all granted permissions to " + grantUri); 6875 6876 final IPackageManager pm = AppGlobals.getPackageManager(); 6877 final String authority = grantUri.uri.getAuthority(); 6878 final ProviderInfo pi = getProviderInfoLocked(authority, grantUri.sourceUserId); 6879 if (pi == null) { 6880 Slog.w(TAG, "No content provider found for permission revoke: " 6881 + grantUri.toSafeString()); 6882 return; 6883 } 6884 6885 // Does the caller have this permission on the URI? 6886 if (!checkHoldingPermissionsLocked(pm, pi, grantUri, callingUid, modeFlags)) { 6887 // Right now, if you are not the original owner of the permission, 6888 // you are not allowed to revoke it. 6889 //if (!checkUriPermissionLocked(uri, callingUid, modeFlags)) { 6890 throw new SecurityException("Uid " + callingUid 6891 + " does not have permission to uri " + grantUri); 6892 //} 6893 } 6894 6895 boolean persistChanged = false; 6896 6897 // Go through all of the permissions and remove any that match. 6898 int N = mGrantedUriPermissions.size(); 6899 for (int i = 0; i < N; i++) { 6900 final int targetUid = mGrantedUriPermissions.keyAt(i); 6901 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6902 6903 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 6904 final UriPermission perm = it.next(); 6905 if (perm.uri.sourceUserId == grantUri.sourceUserId 6906 && perm.uri.uri.isPathPrefixMatch(grantUri.uri)) { 6907 if (DEBUG_URI_PERMISSION) 6908 Slog.v(TAG, 6909 "Revoking " + perm.targetUid + " permission to " + perm.uri); 6910 persistChanged |= perm.revokeModes( 6911 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 6912 if (perm.modeFlags == 0) { 6913 it.remove(); 6914 } 6915 } 6916 } 6917 6918 if (perms.isEmpty()) { 6919 mGrantedUriPermissions.remove(targetUid); 6920 N--; 6921 i--; 6922 } 6923 } 6924 6925 if (persistChanged) { 6926 schedulePersistUriGrants(); 6927 } 6928 } 6929 6930 @Override 6931 public void revokeUriPermission(IApplicationThread caller, Uri uri, final int modeFlags, 6932 int userId) { 6933 enforceNotIsolatedCaller("revokeUriPermission"); 6934 synchronized(this) { 6935 final ProcessRecord r = getRecordForAppLocked(caller); 6936 if (r == null) { 6937 throw new SecurityException("Unable to find app for caller " 6938 + caller 6939 + " when revoking permission to uri " + uri); 6940 } 6941 if (uri == null) { 6942 Slog.w(TAG, "revokeUriPermission: null uri"); 6943 return; 6944 } 6945 6946 if (!Intent.isAccessUriMode(modeFlags)) { 6947 return; 6948 } 6949 6950 final IPackageManager pm = AppGlobals.getPackageManager(); 6951 final String authority = uri.getAuthority(); 6952 final ProviderInfo pi = getProviderInfoLocked(authority, userId); 6953 if (pi == null) { 6954 Slog.w(TAG, "No content provider found for permission revoke: " 6955 + uri.toSafeString()); 6956 return; 6957 } 6958 6959 revokeUriPermissionLocked(r.uid, new GrantUri(userId, uri, false), modeFlags); 6960 } 6961 } 6962 6963 /** 6964 * Remove any {@link UriPermission} granted <em>from</em> or <em>to</em> the 6965 * given package. 6966 * 6967 * @param packageName Package name to match, or {@code null} to apply to all 6968 * packages. 6969 * @param userHandle User to match, or {@link UserHandle#USER_ALL} to apply 6970 * to all users. 6971 * @param persistable If persistable grants should be removed. 6972 */ 6973 private void removeUriPermissionsForPackageLocked( 6974 String packageName, int userHandle, boolean persistable) { 6975 if (userHandle == UserHandle.USER_ALL && packageName == null) { 6976 throw new IllegalArgumentException("Must narrow by either package or user"); 6977 } 6978 6979 boolean persistChanged = false; 6980 6981 int N = mGrantedUriPermissions.size(); 6982 for (int i = 0; i < N; i++) { 6983 final int targetUid = mGrantedUriPermissions.keyAt(i); 6984 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6985 6986 // Only inspect grants matching user 6987 if (userHandle == UserHandle.USER_ALL 6988 || userHandle == UserHandle.getUserId(targetUid)) { 6989 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 6990 final UriPermission perm = it.next(); 6991 6992 // Only inspect grants matching package 6993 if (packageName == null || perm.sourcePkg.equals(packageName) 6994 || perm.targetPkg.equals(packageName)) { 6995 persistChanged |= perm.revokeModes( 6996 persistable ? ~0 : ~Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 6997 6998 // Only remove when no modes remain; any persisted grants 6999 // will keep this alive. 7000 if (perm.modeFlags == 0) { 7001 it.remove(); 7002 } 7003 } 7004 } 7005 7006 if (perms.isEmpty()) { 7007 mGrantedUriPermissions.remove(targetUid); 7008 N--; 7009 i--; 7010 } 7011 } 7012 } 7013 7014 if (persistChanged) { 7015 schedulePersistUriGrants(); 7016 } 7017 } 7018 7019 @Override 7020 public IBinder newUriPermissionOwner(String name) { 7021 enforceNotIsolatedCaller("newUriPermissionOwner"); 7022 synchronized(this) { 7023 UriPermissionOwner owner = new UriPermissionOwner(this, name); 7024 return owner.getExternalTokenLocked(); 7025 } 7026 } 7027 7028 @Override 7029 public void grantUriPermissionFromOwner(IBinder token, int fromUid, String targetPkg, Uri uri, 7030 final int modeFlags, int sourceUserId, int targetUserId) { 7031 synchronized(this) { 7032 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 7033 if (owner == null) { 7034 throw new IllegalArgumentException("Unknown owner: " + token); 7035 } 7036 if (fromUid != Binder.getCallingUid()) { 7037 if (Binder.getCallingUid() != Process.myUid()) { 7038 // Only system code can grant URI permissions on behalf 7039 // of other users. 7040 throw new SecurityException("nice try"); 7041 } 7042 } 7043 if (targetPkg == null) { 7044 throw new IllegalArgumentException("null target"); 7045 } 7046 if (uri == null) { 7047 throw new IllegalArgumentException("null uri"); 7048 } 7049 7050 grantUriPermissionLocked(fromUid, targetPkg, new GrantUri(sourceUserId, uri, false), 7051 modeFlags, owner, targetUserId); 7052 } 7053 } 7054 7055 @Override 7056 public void revokeUriPermissionFromOwner(IBinder token, Uri uri, int mode, int userId) { 7057 synchronized(this) { 7058 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 7059 if (owner == null) { 7060 throw new IllegalArgumentException("Unknown owner: " + token); 7061 } 7062 7063 if (uri == null) { 7064 owner.removeUriPermissionsLocked(mode); 7065 } else { 7066 owner.removeUriPermissionLocked(new GrantUri(userId, uri, false), mode); 7067 } 7068 } 7069 } 7070 7071 private void schedulePersistUriGrants() { 7072 if (!mHandler.hasMessages(PERSIST_URI_GRANTS_MSG)) { 7073 mHandler.sendMessageDelayed(mHandler.obtainMessage(PERSIST_URI_GRANTS_MSG), 7074 10 * DateUtils.SECOND_IN_MILLIS); 7075 } 7076 } 7077 7078 private void writeGrantedUriPermissions() { 7079 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "writeGrantedUriPermissions()"); 7080 7081 // Snapshot permissions so we can persist without lock 7082 ArrayList<UriPermission.Snapshot> persist = Lists.newArrayList(); 7083 synchronized (this) { 7084 final int size = mGrantedUriPermissions.size(); 7085 for (int i = 0; i < size; i++) { 7086 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 7087 for (UriPermission perm : perms.values()) { 7088 if (perm.persistedModeFlags != 0) { 7089 persist.add(perm.snapshot()); 7090 } 7091 } 7092 } 7093 } 7094 7095 FileOutputStream fos = null; 7096 try { 7097 fos = mGrantFile.startWrite(); 7098 7099 XmlSerializer out = new FastXmlSerializer(); 7100 out.setOutput(fos, "utf-8"); 7101 out.startDocument(null, true); 7102 out.startTag(null, TAG_URI_GRANTS); 7103 for (UriPermission.Snapshot perm : persist) { 7104 out.startTag(null, TAG_URI_GRANT); 7105 writeIntAttribute(out, ATTR_SOURCE_USER_ID, perm.uri.sourceUserId); 7106 writeIntAttribute(out, ATTR_TARGET_USER_ID, perm.targetUserId); 7107 out.attribute(null, ATTR_SOURCE_PKG, perm.sourcePkg); 7108 out.attribute(null, ATTR_TARGET_PKG, perm.targetPkg); 7109 out.attribute(null, ATTR_URI, String.valueOf(perm.uri.uri)); 7110 writeBooleanAttribute(out, ATTR_PREFIX, perm.uri.prefix); 7111 writeIntAttribute(out, ATTR_MODE_FLAGS, perm.persistedModeFlags); 7112 writeLongAttribute(out, ATTR_CREATED_TIME, perm.persistedCreateTime); 7113 out.endTag(null, TAG_URI_GRANT); 7114 } 7115 out.endTag(null, TAG_URI_GRANTS); 7116 out.endDocument(); 7117 7118 mGrantFile.finishWrite(fos); 7119 } catch (IOException e) { 7120 if (fos != null) { 7121 mGrantFile.failWrite(fos); 7122 } 7123 } 7124 } 7125 7126 private void readGrantedUriPermissionsLocked() { 7127 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "readGrantedUriPermissions()"); 7128 7129 final long now = System.currentTimeMillis(); 7130 7131 FileInputStream fis = null; 7132 try { 7133 fis = mGrantFile.openRead(); 7134 final XmlPullParser in = Xml.newPullParser(); 7135 in.setInput(fis, null); 7136 7137 int type; 7138 while ((type = in.next()) != END_DOCUMENT) { 7139 final String tag = in.getName(); 7140 if (type == START_TAG) { 7141 if (TAG_URI_GRANT.equals(tag)) { 7142 final int sourceUserId; 7143 final int targetUserId; 7144 final int userHandle = readIntAttribute(in, 7145 ATTR_USER_HANDLE, UserHandle.USER_NULL); 7146 if (userHandle != UserHandle.USER_NULL) { 7147 // For backwards compatibility. 7148 sourceUserId = userHandle; 7149 targetUserId = userHandle; 7150 } else { 7151 sourceUserId = readIntAttribute(in, ATTR_SOURCE_USER_ID); 7152 targetUserId = readIntAttribute(in, ATTR_TARGET_USER_ID); 7153 } 7154 final String sourcePkg = in.getAttributeValue(null, ATTR_SOURCE_PKG); 7155 final String targetPkg = in.getAttributeValue(null, ATTR_TARGET_PKG); 7156 final Uri uri = Uri.parse(in.getAttributeValue(null, ATTR_URI)); 7157 final boolean prefix = readBooleanAttribute(in, ATTR_PREFIX); 7158 final int modeFlags = readIntAttribute(in, ATTR_MODE_FLAGS); 7159 final long createdTime = readLongAttribute(in, ATTR_CREATED_TIME, now); 7160 7161 // Sanity check that provider still belongs to source package 7162 final ProviderInfo pi = getProviderInfoLocked( 7163 uri.getAuthority(), sourceUserId); 7164 if (pi != null && sourcePkg.equals(pi.packageName)) { 7165 int targetUid = -1; 7166 try { 7167 targetUid = AppGlobals.getPackageManager() 7168 .getPackageUid(targetPkg, targetUserId); 7169 } catch (RemoteException e) { 7170 } 7171 if (targetUid != -1) { 7172 final UriPermission perm = findOrCreateUriPermissionLocked( 7173 sourcePkg, targetPkg, targetUid, 7174 new GrantUri(sourceUserId, uri, prefix)); 7175 perm.initPersistedModes(modeFlags, createdTime); 7176 } 7177 } else { 7178 Slog.w(TAG, "Persisted grant for " + uri + " had source " + sourcePkg 7179 + " but instead found " + pi); 7180 } 7181 } 7182 } 7183 } 7184 } catch (FileNotFoundException e) { 7185 // Missing grants is okay 7186 } catch (IOException e) { 7187 Log.wtf(TAG, "Failed reading Uri grants", e); 7188 } catch (XmlPullParserException e) { 7189 Log.wtf(TAG, "Failed reading Uri grants", e); 7190 } finally { 7191 IoUtils.closeQuietly(fis); 7192 } 7193 } 7194 7195 @Override 7196 public void takePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 7197 enforceNotIsolatedCaller("takePersistableUriPermission"); 7198 7199 Preconditions.checkFlagsArgument(modeFlags, 7200 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 7201 7202 synchronized (this) { 7203 final int callingUid = Binder.getCallingUid(); 7204 boolean persistChanged = false; 7205 GrantUri grantUri = new GrantUri(userId, uri, false); 7206 7207 UriPermission exactPerm = findUriPermissionLocked(callingUid, 7208 new GrantUri(userId, uri, false)); 7209 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 7210 new GrantUri(userId, uri, true)); 7211 7212 final boolean exactValid = (exactPerm != null) 7213 && ((modeFlags & exactPerm.persistableModeFlags) == modeFlags); 7214 final boolean prefixValid = (prefixPerm != null) 7215 && ((modeFlags & prefixPerm.persistableModeFlags) == modeFlags); 7216 7217 if (!(exactValid || prefixValid)) { 7218 throw new SecurityException("No persistable permission grants found for UID " 7219 + callingUid + " and Uri " + grantUri.toSafeString()); 7220 } 7221 7222 if (exactValid) { 7223 persistChanged |= exactPerm.takePersistableModes(modeFlags); 7224 } 7225 if (prefixValid) { 7226 persistChanged |= prefixPerm.takePersistableModes(modeFlags); 7227 } 7228 7229 persistChanged |= maybePrunePersistedUriGrantsLocked(callingUid); 7230 7231 if (persistChanged) { 7232 schedulePersistUriGrants(); 7233 } 7234 } 7235 } 7236 7237 @Override 7238 public void releasePersistableUriPermission(Uri uri, final int modeFlags, int userId) { 7239 enforceNotIsolatedCaller("releasePersistableUriPermission"); 7240 7241 Preconditions.checkFlagsArgument(modeFlags, 7242 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 7243 7244 synchronized (this) { 7245 final int callingUid = Binder.getCallingUid(); 7246 boolean persistChanged = false; 7247 7248 UriPermission exactPerm = findUriPermissionLocked(callingUid, 7249 new GrantUri(userId, uri, false)); 7250 UriPermission prefixPerm = findUriPermissionLocked(callingUid, 7251 new GrantUri(userId, uri, true)); 7252 if (exactPerm == null && prefixPerm == null) { 7253 throw new SecurityException("No permission grants found for UID " + callingUid 7254 + " and Uri " + uri.toSafeString()); 7255 } 7256 7257 if (exactPerm != null) { 7258 persistChanged |= exactPerm.releasePersistableModes(modeFlags); 7259 removeUriPermissionIfNeededLocked(exactPerm); 7260 } 7261 if (prefixPerm != null) { 7262 persistChanged |= prefixPerm.releasePersistableModes(modeFlags); 7263 removeUriPermissionIfNeededLocked(prefixPerm); 7264 } 7265 7266 if (persistChanged) { 7267 schedulePersistUriGrants(); 7268 } 7269 } 7270 } 7271 7272 /** 7273 * Prune any older {@link UriPermission} for the given UID until outstanding 7274 * persisted grants are below {@link #MAX_PERSISTED_URI_GRANTS}. 7275 * 7276 * @return if any mutations occured that require persisting. 7277 */ 7278 private boolean maybePrunePersistedUriGrantsLocked(int uid) { 7279 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 7280 if (perms == null) return false; 7281 if (perms.size() < MAX_PERSISTED_URI_GRANTS) return false; 7282 7283 final ArrayList<UriPermission> persisted = Lists.newArrayList(); 7284 for (UriPermission perm : perms.values()) { 7285 if (perm.persistedModeFlags != 0) { 7286 persisted.add(perm); 7287 } 7288 } 7289 7290 final int trimCount = persisted.size() - MAX_PERSISTED_URI_GRANTS; 7291 if (trimCount <= 0) return false; 7292 7293 Collections.sort(persisted, new UriPermission.PersistedTimeComparator()); 7294 for (int i = 0; i < trimCount; i++) { 7295 final UriPermission perm = persisted.get(i); 7296 7297 if (DEBUG_URI_PERMISSION) { 7298 Slog.v(TAG, "Trimming grant created at " + perm.persistedCreateTime); 7299 } 7300 7301 perm.releasePersistableModes(~0); 7302 removeUriPermissionIfNeededLocked(perm); 7303 } 7304 7305 return true; 7306 } 7307 7308 @Override 7309 public ParceledListSlice<android.content.UriPermission> getPersistedUriPermissions( 7310 String packageName, boolean incoming) { 7311 enforceNotIsolatedCaller("getPersistedUriPermissions"); 7312 Preconditions.checkNotNull(packageName, "packageName"); 7313 7314 final int callingUid = Binder.getCallingUid(); 7315 final IPackageManager pm = AppGlobals.getPackageManager(); 7316 try { 7317 final int packageUid = pm.getPackageUid(packageName, UserHandle.getUserId(callingUid)); 7318 if (packageUid != callingUid) { 7319 throw new SecurityException( 7320 "Package " + packageName + " does not belong to calling UID " + callingUid); 7321 } 7322 } catch (RemoteException e) { 7323 throw new SecurityException("Failed to verify package name ownership"); 7324 } 7325 7326 final ArrayList<android.content.UriPermission> result = Lists.newArrayList(); 7327 synchronized (this) { 7328 if (incoming) { 7329 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 7330 callingUid); 7331 if (perms == null) { 7332 Slog.w(TAG, "No permission grants found for " + packageName); 7333 } else { 7334 for (UriPermission perm : perms.values()) { 7335 if (packageName.equals(perm.targetPkg) && perm.persistedModeFlags != 0) { 7336 result.add(perm.buildPersistedPublicApiObject()); 7337 } 7338 } 7339 } 7340 } else { 7341 final int size = mGrantedUriPermissions.size(); 7342 for (int i = 0; i < size; i++) { 7343 final ArrayMap<GrantUri, UriPermission> perms = 7344 mGrantedUriPermissions.valueAt(i); 7345 for (UriPermission perm : perms.values()) { 7346 if (packageName.equals(perm.sourcePkg) && perm.persistedModeFlags != 0) { 7347 result.add(perm.buildPersistedPublicApiObject()); 7348 } 7349 } 7350 } 7351 } 7352 } 7353 return new ParceledListSlice<android.content.UriPermission>(result); 7354 } 7355 7356 @Override 7357 public void showWaitingForDebugger(IApplicationThread who, boolean waiting) { 7358 synchronized (this) { 7359 ProcessRecord app = 7360 who != null ? getRecordForAppLocked(who) : null; 7361 if (app == null) return; 7362 7363 Message msg = Message.obtain(); 7364 msg.what = WAIT_FOR_DEBUGGER_MSG; 7365 msg.obj = app; 7366 msg.arg1 = waiting ? 1 : 0; 7367 mHandler.sendMessage(msg); 7368 } 7369 } 7370 7371 @Override 7372 public void getMemoryInfo(ActivityManager.MemoryInfo outInfo) { 7373 final long homeAppMem = mProcessList.getMemLevel(ProcessList.HOME_APP_ADJ); 7374 final long cachedAppMem = mProcessList.getMemLevel(ProcessList.CACHED_APP_MIN_ADJ); 7375 outInfo.availMem = Process.getFreeMemory(); 7376 outInfo.totalMem = Process.getTotalMemory(); 7377 outInfo.threshold = homeAppMem; 7378 outInfo.lowMemory = outInfo.availMem < (homeAppMem + ((cachedAppMem-homeAppMem)/2)); 7379 outInfo.hiddenAppThreshold = cachedAppMem; 7380 outInfo.secondaryServerThreshold = mProcessList.getMemLevel( 7381 ProcessList.SERVICE_ADJ); 7382 outInfo.visibleAppThreshold = mProcessList.getMemLevel( 7383 ProcessList.VISIBLE_APP_ADJ); 7384 outInfo.foregroundAppThreshold = mProcessList.getMemLevel( 7385 ProcessList.FOREGROUND_APP_ADJ); 7386 } 7387 7388 // ========================================================= 7389 // TASK MANAGEMENT 7390 // ========================================================= 7391 7392 @Override 7393 public List<IAppTask> getAppTasks() { 7394 final PackageManager pm = mContext.getPackageManager(); 7395 int callingUid = Binder.getCallingUid(); 7396 long ident = Binder.clearCallingIdentity(); 7397 7398 // Compose the list of packages for this id to test against 7399 HashSet<String> packages = new HashSet<String>(); 7400 String[] uidPackages = pm.getPackagesForUid(callingUid); 7401 for (int i = 0; i < uidPackages.length; i++) { 7402 packages.add(uidPackages[i]); 7403 } 7404 7405 synchronized(this) { 7406 ArrayList<IAppTask> list = new ArrayList<IAppTask>(); 7407 try { 7408 if (localLOGV) Slog.v(TAG, "getAppTasks"); 7409 7410 final int N = mRecentTasks.size(); 7411 for (int i = 0; i < N; i++) { 7412 TaskRecord tr = mRecentTasks.get(i); 7413 // Skip tasks that are not created by the caller 7414 if (packages.contains(tr.getBaseIntent().getComponent().getPackageName())) { 7415 ActivityManager.RecentTaskInfo taskInfo = 7416 createRecentTaskInfoFromTaskRecord(tr); 7417 AppTaskImpl taskImpl = new AppTaskImpl(taskInfo.persistentId, callingUid); 7418 list.add(taskImpl); 7419 } 7420 } 7421 } finally { 7422 Binder.restoreCallingIdentity(ident); 7423 } 7424 return list; 7425 } 7426 } 7427 7428 @Override 7429 public List<RunningTaskInfo> getTasks(int maxNum, int flags) { 7430 final int callingUid = Binder.getCallingUid(); 7431 ArrayList<RunningTaskInfo> list = new ArrayList<RunningTaskInfo>(); 7432 7433 synchronized(this) { 7434 if (localLOGV) Slog.v( 7435 TAG, "getTasks: max=" + maxNum + ", flags=" + flags); 7436 7437 final boolean allowed = checkCallingPermission( 7438 android.Manifest.permission.GET_TASKS) 7439 == PackageManager.PERMISSION_GRANTED; 7440 if (!allowed) { 7441 Slog.w(TAG, "getTasks: caller " + callingUid 7442 + " does not hold GET_TASKS; limiting output"); 7443 } 7444 7445 // TODO: Improve with MRU list from all ActivityStacks. 7446 mStackSupervisor.getTasksLocked(maxNum, list, callingUid, allowed); 7447 } 7448 7449 return list; 7450 } 7451 7452 TaskRecord getMostRecentTask() { 7453 return mRecentTasks.get(0); 7454 } 7455 7456 /** 7457 * Creates a new RecentTaskInfo from a TaskRecord. 7458 */ 7459 private ActivityManager.RecentTaskInfo createRecentTaskInfoFromTaskRecord(TaskRecord tr) { 7460 // Update the task description to reflect any changes in the task stack 7461 tr.updateTaskDescription(); 7462 7463 // Compose the recent task info 7464 ActivityManager.RecentTaskInfo rti = new ActivityManager.RecentTaskInfo(); 7465 rti.id = tr.getTopActivity() == null ? -1 : tr.taskId; 7466 rti.persistentId = tr.taskId; 7467 rti.baseIntent = new Intent(tr.getBaseIntent()); 7468 rti.origActivity = tr.origActivity; 7469 rti.description = tr.lastDescription; 7470 rti.stackId = tr.stack != null ? tr.stack.mStackId : -1; 7471 rti.userId = tr.userId; 7472 rti.taskDescription = new ActivityManager.TaskDescription(tr.lastTaskDescription); 7473 rti.firstActiveTime = tr.firstActiveTime; 7474 rti.lastActiveTime = tr.lastActiveTime; 7475 rti.affiliatedTaskId = tr.mAffiliatedTaskId; 7476 rti.affiliatedTaskColor = tr.mAffiliatedTaskColor; 7477 return rti; 7478 } 7479 7480 @Override 7481 public List<ActivityManager.RecentTaskInfo> getRecentTasks(int maxNum, int flags, int userId) { 7482 final int callingUid = Binder.getCallingUid(); 7483 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 7484 false, ALLOW_FULL_ONLY, "getRecentTasks", null); 7485 7486 final boolean includeProfiles = (flags & ActivityManager.RECENT_INCLUDE_PROFILES) != 0; 7487 final boolean withExcluded = (flags&ActivityManager.RECENT_WITH_EXCLUDED) != 0; 7488 synchronized (this) { 7489 final boolean allowed = checkCallingPermission(android.Manifest.permission.GET_TASKS) 7490 == PackageManager.PERMISSION_GRANTED; 7491 if (!allowed) { 7492 Slog.w(TAG, "getRecentTasks: caller " + callingUid 7493 + " does not hold GET_TASKS; limiting output"); 7494 } 7495 final boolean detailed = checkCallingPermission( 7496 android.Manifest.permission.GET_DETAILED_TASKS) 7497 == PackageManager.PERMISSION_GRANTED; 7498 7499 IPackageManager pm = AppGlobals.getPackageManager(); 7500 7501 final int N = mRecentTasks.size(); 7502 ArrayList<ActivityManager.RecentTaskInfo> res 7503 = new ArrayList<ActivityManager.RecentTaskInfo>( 7504 maxNum < N ? maxNum : N); 7505 7506 final Set<Integer> includedUsers; 7507 if (includeProfiles) { 7508 includedUsers = getProfileIdsLocked(userId); 7509 } else { 7510 includedUsers = new HashSet<Integer>(); 7511 } 7512 includedUsers.add(Integer.valueOf(userId)); 7513 7514 // Regroup affiliated tasks together. 7515 for (int i = 0; i < N; ) { 7516 TaskRecord task = mRecentTasks.remove(i); 7517 if (mTmpRecents.contains(task)) { 7518 continue; 7519 } 7520 int affiliatedTaskId = task.mAffiliatedTaskId; 7521 while (true) { 7522 TaskRecord next = task.mNextAffiliate; 7523 if (next == null) { 7524 break; 7525 } 7526 if (next.mAffiliatedTaskId != affiliatedTaskId) { 7527 Slog.e(TAG, "Error in Recents: next.affiliatedTaskId=" + 7528 next.mAffiliatedTaskId + " affiliatedTaskId=" + affiliatedTaskId); 7529 task.setNextAffiliate(null); 7530 if (next.mPrevAffiliate == task) { 7531 next.setPrevAffiliate(null); 7532 } 7533 break; 7534 } 7535 if (next.mPrevAffiliate != task) { 7536 Slog.e(TAG, "Error in Recents chain prev.mNextAffiliate=" + 7537 next.mPrevAffiliate + " task=" + task); 7538 next.setPrevAffiliate(null); 7539 break; 7540 } 7541 if (!mRecentTasks.contains(next)) { 7542 Slog.e(TAG, "Error in Recents: next=" + next + " not in mRecentTasks"); 7543 task.setNextAffiliate(null); 7544 if (next.mPrevAffiliate == task) { 7545 next.setPrevAffiliate(null); 7546 } 7547 break; 7548 } 7549 task = next; 7550 } 7551 // task is now the end of the list 7552 do { 7553 mRecentTasks.remove(task); 7554 mRecentTasks.add(i++, task); 7555 mTmpRecents.add(task); 7556 } while ((task = task.mPrevAffiliate) != null); 7557 } 7558 mTmpRecents.clear(); 7559 // mRecentTasks is now in sorted, affiliated order. 7560 7561 for (int i=0; i<N && maxNum > 0; i++) { 7562 TaskRecord tr = mRecentTasks.get(i); 7563 // Only add calling user or related users recent tasks 7564 if (!includedUsers.contains(Integer.valueOf(tr.userId))) continue; 7565 7566 // Return the entry if desired by the caller. We always return 7567 // the first entry, because callers always expect this to be the 7568 // foreground app. We may filter others if the caller has 7569 // not supplied RECENT_WITH_EXCLUDED and there is some reason 7570 // we should exclude the entry. 7571 7572 if (i == 0 7573 || withExcluded 7574 || (tr.intent == null) 7575 || ((tr.intent.getFlags() & Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS) 7576 == 0)) { 7577 if (!allowed) { 7578 // If the caller doesn't have the GET_TASKS permission, then only 7579 // allow them to see a small subset of tasks -- their own and home. 7580 if (!tr.isHomeTask() && tr.creatorUid != callingUid) { 7581 continue; 7582 } 7583 } 7584 if (tr.autoRemoveRecents && tr.getTopActivity() == null) { 7585 // Don't include auto remove tasks that are finished or finishing. 7586 continue; 7587 } 7588 7589 ActivityManager.RecentTaskInfo rti = createRecentTaskInfoFromTaskRecord(tr); 7590 if (!detailed) { 7591 rti.baseIntent.replaceExtras((Bundle)null); 7592 } 7593 7594 if ((flags&ActivityManager.RECENT_IGNORE_UNAVAILABLE) != 0) { 7595 // Check whether this activity is currently available. 7596 try { 7597 if (rti.origActivity != null) { 7598 if (pm.getActivityInfo(rti.origActivity, 0, userId) 7599 == null) { 7600 continue; 7601 } 7602 } else if (rti.baseIntent != null) { 7603 if (pm.queryIntentActivities(rti.baseIntent, 7604 null, 0, userId) == null) { 7605 continue; 7606 } 7607 } 7608 } catch (RemoteException e) { 7609 // Will never happen. 7610 } 7611 } 7612 7613 res.add(rti); 7614 maxNum--; 7615 } 7616 } 7617 return res; 7618 } 7619 } 7620 7621 private TaskRecord recentTaskForIdLocked(int id) { 7622 final int N = mRecentTasks.size(); 7623 for (int i=0; i<N; i++) { 7624 TaskRecord tr = mRecentTasks.get(i); 7625 if (tr.taskId == id) { 7626 return tr; 7627 } 7628 } 7629 return null; 7630 } 7631 7632 @Override 7633 public ActivityManager.TaskThumbnail getTaskThumbnail(int id) { 7634 synchronized (this) { 7635 enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER, 7636 "getTaskThumbnail()"); 7637 TaskRecord tr = recentTaskForIdLocked(id); 7638 if (tr != null) { 7639 return tr.getTaskThumbnailLocked(); 7640 } 7641 } 7642 return null; 7643 } 7644 7645 @Override 7646 public void setTaskDescription(IBinder token, ActivityManager.TaskDescription td) { 7647 synchronized (this) { 7648 ActivityRecord r = ActivityRecord.isInStackLocked(token); 7649 if (r != null) { 7650 r.taskDescription = td; 7651 r.task.updateTaskDescription(); 7652 } 7653 } 7654 } 7655 7656 private void killUnneededProcessLocked(ProcessRecord pr, String reason) { 7657 if (!pr.killedByAm) { 7658 Slog.i(TAG, "Killing " + pr.toShortString() + " (adj " + pr.setAdj + "): " + reason); 7659 EventLog.writeEvent(EventLogTags.AM_KILL, pr.userId, pr.pid, 7660 pr.processName, pr.setAdj, reason); 7661 pr.killedByAm = true; 7662 Process.killProcessQuiet(pr.pid); 7663 Process.killProcessGroup(pr.info.uid, pr.pid); 7664 } 7665 } 7666 7667 private void cleanUpRemovedTaskLocked(TaskRecord tr, int flags) { 7668 tr.disposeThumbnail(); 7669 mRecentTasks.remove(tr); 7670 tr.closeRecentsChain(); 7671 final boolean killProcesses = (flags&ActivityManager.REMOVE_TASK_KILL_PROCESS) != 0; 7672 Intent baseIntent = new Intent( 7673 tr.intent != null ? tr.intent : tr.affinityIntent); 7674 ComponentName component = baseIntent.getComponent(); 7675 if (component == null) { 7676 Slog.w(TAG, "Now component for base intent of task: " + tr); 7677 return; 7678 } 7679 7680 // Find any running services associated with this app. 7681 mServices.cleanUpRemovedTaskLocked(tr, component, baseIntent); 7682 7683 if (killProcesses) { 7684 // Find any running processes associated with this app. 7685 final String pkg = component.getPackageName(); 7686 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 7687 ArrayMap<String, SparseArray<ProcessRecord>> pmap = mProcessNames.getMap(); 7688 for (int i=0; i<pmap.size(); i++) { 7689 SparseArray<ProcessRecord> uids = pmap.valueAt(i); 7690 for (int j=0; j<uids.size(); j++) { 7691 ProcessRecord proc = uids.valueAt(j); 7692 if (proc.userId != tr.userId) { 7693 continue; 7694 } 7695 if (!proc.pkgList.containsKey(pkg)) { 7696 continue; 7697 } 7698 procs.add(proc); 7699 } 7700 } 7701 7702 // Kill the running processes. 7703 for (int i=0; i<procs.size(); i++) { 7704 ProcessRecord pr = procs.get(i); 7705 if (pr == mHomeProcess) { 7706 // Don't kill the home process along with tasks from the same package. 7707 continue; 7708 } 7709 if (pr.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 7710 killUnneededProcessLocked(pr, "remove task"); 7711 } else { 7712 pr.waitingToKill = "remove task"; 7713 } 7714 } 7715 } 7716 } 7717 7718 /** 7719 * Removes the task with the specified task id. 7720 * 7721 * @param taskId Identifier of the task to be removed. 7722 * @param flags Additional operational flags. May be 0 or 7723 * {@link ActivityManager#REMOVE_TASK_KILL_PROCESS}. 7724 * @return Returns true if the given task was found and removed. 7725 */ 7726 private boolean removeTaskByIdLocked(int taskId, int flags) { 7727 TaskRecord tr = recentTaskForIdLocked(taskId); 7728 if (tr != null) { 7729 tr.removeTaskActivitiesLocked(); 7730 cleanUpRemovedTaskLocked(tr, flags); 7731 if (tr.isPersistable) { 7732 notifyTaskPersisterLocked(null, true); 7733 } 7734 return true; 7735 } 7736 return false; 7737 } 7738 7739 @Override 7740 public boolean removeTask(int taskId, int flags) { 7741 synchronized (this) { 7742 enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, 7743 "removeTask()"); 7744 long ident = Binder.clearCallingIdentity(); 7745 try { 7746 return removeTaskByIdLocked(taskId, flags); 7747 } finally { 7748 Binder.restoreCallingIdentity(ident); 7749 } 7750 } 7751 } 7752 7753 /** 7754 * TODO: Add mController hook 7755 */ 7756 @Override 7757 public void moveTaskToFront(int taskId, int flags, Bundle options) { 7758 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7759 "moveTaskToFront()"); 7760 7761 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToFront: moving taskId=" + taskId); 7762 synchronized(this) { 7763 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7764 Binder.getCallingUid(), "Task to front")) { 7765 ActivityOptions.abort(options); 7766 return; 7767 } 7768 final long origId = Binder.clearCallingIdentity(); 7769 try { 7770 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 7771 if (task == null) { 7772 return; 7773 } 7774 if (mStackSupervisor.isLockTaskModeViolation(task)) { 7775 mStackSupervisor.showLockTaskToast(); 7776 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode"); 7777 return; 7778 } 7779 final ActivityRecord prev = mStackSupervisor.topRunningActivityLocked(); 7780 if (prev != null && prev.isRecentsActivity()) { 7781 task.setTaskToReturnTo(ActivityRecord.RECENTS_ACTIVITY_TYPE); 7782 } 7783 mStackSupervisor.findTaskToMoveToFrontLocked(task, flags, options); 7784 } finally { 7785 Binder.restoreCallingIdentity(origId); 7786 } 7787 ActivityOptions.abort(options); 7788 } 7789 } 7790 7791 @Override 7792 public void moveTaskToBack(int taskId) { 7793 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7794 "moveTaskToBack()"); 7795 7796 synchronized(this) { 7797 TaskRecord tr = recentTaskForIdLocked(taskId); 7798 if (tr != null) { 7799 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToBack: moving task=" + tr); 7800 ActivityStack stack = tr.stack; 7801 if (stack.mResumedActivity != null && stack.mResumedActivity.task == tr) { 7802 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7803 Binder.getCallingUid(), "Task to back")) { 7804 return; 7805 } 7806 } 7807 final long origId = Binder.clearCallingIdentity(); 7808 try { 7809 stack.moveTaskToBackLocked(taskId, null); 7810 } finally { 7811 Binder.restoreCallingIdentity(origId); 7812 } 7813 } 7814 } 7815 } 7816 7817 /** 7818 * Moves an activity, and all of the other activities within the same task, to the bottom 7819 * of the history stack. The activity's order within the task is unchanged. 7820 * 7821 * @param token A reference to the activity we wish to move 7822 * @param nonRoot If false then this only works if the activity is the root 7823 * of a task; if true it will work for any activity in a task. 7824 * @return Returns true if the move completed, false if not. 7825 */ 7826 @Override 7827 public boolean moveActivityTaskToBack(IBinder token, boolean nonRoot) { 7828 enforceNotIsolatedCaller("moveActivityTaskToBack"); 7829 synchronized(this) { 7830 final long origId = Binder.clearCallingIdentity(); 7831 int taskId = ActivityRecord.getTaskForActivityLocked(token, !nonRoot); 7832 if (taskId >= 0) { 7833 return ActivityRecord.getStackLocked(token).moveTaskToBackLocked(taskId, null); 7834 } 7835 Binder.restoreCallingIdentity(origId); 7836 } 7837 return false; 7838 } 7839 7840 @Override 7841 public void moveTaskBackwards(int task) { 7842 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7843 "moveTaskBackwards()"); 7844 7845 synchronized(this) { 7846 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7847 Binder.getCallingUid(), "Task backwards")) { 7848 return; 7849 } 7850 final long origId = Binder.clearCallingIdentity(); 7851 moveTaskBackwardsLocked(task); 7852 Binder.restoreCallingIdentity(origId); 7853 } 7854 } 7855 7856 private final void moveTaskBackwardsLocked(int task) { 7857 Slog.e(TAG, "moveTaskBackwards not yet implemented!"); 7858 } 7859 7860 @Override 7861 public IBinder getHomeActivityToken() throws RemoteException { 7862 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7863 "getHomeActivityToken()"); 7864 synchronized (this) { 7865 return mStackSupervisor.getHomeActivityToken(); 7866 } 7867 } 7868 7869 @Override 7870 public IActivityContainer createActivityContainer(IBinder parentActivityToken, 7871 IActivityContainerCallback callback) throws RemoteException { 7872 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7873 "createActivityContainer()"); 7874 synchronized (this) { 7875 if (parentActivityToken == null) { 7876 throw new IllegalArgumentException("parent token must not be null"); 7877 } 7878 ActivityRecord r = ActivityRecord.forToken(parentActivityToken); 7879 if (r == null) { 7880 return null; 7881 } 7882 if (callback == null) { 7883 throw new IllegalArgumentException("callback must not be null"); 7884 } 7885 return mStackSupervisor.createActivityContainer(r, callback); 7886 } 7887 } 7888 7889 @Override 7890 public void deleteActivityContainer(IActivityContainer container) throws RemoteException { 7891 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7892 "deleteActivityContainer()"); 7893 synchronized (this) { 7894 mStackSupervisor.deleteActivityContainer(container); 7895 } 7896 } 7897 7898 @Override 7899 public IActivityContainer getEnclosingActivityContainer(IBinder activityToken) 7900 throws RemoteException { 7901 synchronized (this) { 7902 ActivityStack stack = ActivityRecord.getStackLocked(activityToken); 7903 if (stack != null) { 7904 return stack.mActivityContainer; 7905 } 7906 return null; 7907 } 7908 } 7909 7910 @Override 7911 public void moveTaskToStack(int taskId, int stackId, boolean toTop) { 7912 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7913 "moveTaskToStack()"); 7914 if (stackId == HOME_STACK_ID) { 7915 Slog.e(TAG, "moveTaskToStack: Attempt to move task " + taskId + " to home stack", 7916 new RuntimeException("here").fillInStackTrace()); 7917 } 7918 synchronized (this) { 7919 long ident = Binder.clearCallingIdentity(); 7920 try { 7921 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToStack: moving task=" + taskId + " to stackId=" 7922 + stackId + " toTop=" + toTop); 7923 mStackSupervisor.moveTaskToStack(taskId, stackId, toTop); 7924 } finally { 7925 Binder.restoreCallingIdentity(ident); 7926 } 7927 } 7928 } 7929 7930 @Override 7931 public void resizeStack(int stackBoxId, Rect bounds) { 7932 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7933 "resizeStackBox()"); 7934 long ident = Binder.clearCallingIdentity(); 7935 try { 7936 mWindowManager.resizeStack(stackBoxId, bounds); 7937 } finally { 7938 Binder.restoreCallingIdentity(ident); 7939 } 7940 } 7941 7942 @Override 7943 public List<StackInfo> getAllStackInfos() { 7944 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7945 "getAllStackInfos()"); 7946 long ident = Binder.clearCallingIdentity(); 7947 try { 7948 synchronized (this) { 7949 return mStackSupervisor.getAllStackInfosLocked(); 7950 } 7951 } finally { 7952 Binder.restoreCallingIdentity(ident); 7953 } 7954 } 7955 7956 @Override 7957 public StackInfo getStackInfo(int stackId) { 7958 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7959 "getStackInfo()"); 7960 long ident = Binder.clearCallingIdentity(); 7961 try { 7962 synchronized (this) { 7963 return mStackSupervisor.getStackInfoLocked(stackId); 7964 } 7965 } finally { 7966 Binder.restoreCallingIdentity(ident); 7967 } 7968 } 7969 7970 @Override 7971 public boolean isInHomeStack(int taskId) { 7972 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7973 "getStackInfo()"); 7974 long ident = Binder.clearCallingIdentity(); 7975 try { 7976 synchronized (this) { 7977 TaskRecord tr = recentTaskForIdLocked(taskId); 7978 return tr != null && tr.stack != null && tr.stack.isHomeStack(); 7979 } 7980 } finally { 7981 Binder.restoreCallingIdentity(ident); 7982 } 7983 } 7984 7985 @Override 7986 public int getTaskForActivity(IBinder token, boolean onlyRoot) { 7987 synchronized(this) { 7988 return ActivityRecord.getTaskForActivityLocked(token, onlyRoot); 7989 } 7990 } 7991 7992 private boolean isLockTaskAuthorized(String pkg) { 7993 final DevicePolicyManager dpm = (DevicePolicyManager) 7994 mContext.getSystemService(Context.DEVICE_POLICY_SERVICE); 7995 try { 7996 int uid = mContext.getPackageManager().getPackageUid(pkg, 7997 Binder.getCallingUserHandle().getIdentifier()); 7998 return (uid == Binder.getCallingUid()) && dpm != null && dpm.isLockTaskPermitted(pkg); 7999 } catch (NameNotFoundException e) { 8000 return false; 8001 } 8002 } 8003 8004 void startLockTaskMode(TaskRecord task) { 8005 final String pkg; 8006 synchronized (this) { 8007 pkg = task.intent.getComponent().getPackageName(); 8008 } 8009 boolean isSystemInitiated = Binder.getCallingUid() == Process.SYSTEM_UID; 8010 if (!isSystemInitiated && !isLockTaskAuthorized(pkg)) { 8011 final TaskRecord taskRecord = task; 8012 mHandler.post(new Runnable() { 8013 @Override 8014 public void run() { 8015 mLockToAppRequest.showLockTaskPrompt(taskRecord); 8016 } 8017 }); 8018 return; 8019 } 8020 long ident = Binder.clearCallingIdentity(); 8021 try { 8022 synchronized (this) { 8023 // Since we lost lock on task, make sure it is still there. 8024 task = mStackSupervisor.anyTaskForIdLocked(task.taskId); 8025 if (task != null) { 8026 if (!isSystemInitiated 8027 && ((mFocusedActivity == null) || (task != mFocusedActivity.task))) { 8028 throw new IllegalArgumentException("Invalid task, not in foreground"); 8029 } 8030 mStackSupervisor.setLockTaskModeLocked(task, !isSystemInitiated); 8031 } 8032 } 8033 } finally { 8034 Binder.restoreCallingIdentity(ident); 8035 } 8036 } 8037 8038 @Override 8039 public void startLockTaskMode(int taskId) { 8040 final TaskRecord task; 8041 long ident = Binder.clearCallingIdentity(); 8042 try { 8043 synchronized (this) { 8044 task = mStackSupervisor.anyTaskForIdLocked(taskId); 8045 } 8046 } finally { 8047 Binder.restoreCallingIdentity(ident); 8048 } 8049 if (task != null) { 8050 startLockTaskMode(task); 8051 } 8052 } 8053 8054 @Override 8055 public void startLockTaskMode(IBinder token) { 8056 final TaskRecord task; 8057 long ident = Binder.clearCallingIdentity(); 8058 try { 8059 synchronized (this) { 8060 final ActivityRecord r = ActivityRecord.forToken(token); 8061 if (r == null) { 8062 return; 8063 } 8064 task = r.task; 8065 } 8066 } finally { 8067 Binder.restoreCallingIdentity(ident); 8068 } 8069 if (task != null) { 8070 startLockTaskMode(task); 8071 } 8072 } 8073 8074 @Override 8075 public void startLockTaskModeOnCurrent() throws RemoteException { 8076 checkCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS); 8077 ActivityRecord r = null; 8078 synchronized (this) { 8079 r = mStackSupervisor.topRunningActivityLocked(); 8080 } 8081 startLockTaskMode(r.task); 8082 } 8083 8084 @Override 8085 public void stopLockTaskMode() { 8086 // Verify that the user matches the package of the intent for the TaskRecord 8087 // we are locked to or systtem. This will ensure the same caller for startLockTaskMode 8088 // and stopLockTaskMode. 8089 final int callingUid = Binder.getCallingUid(); 8090 if (callingUid != Process.SYSTEM_UID) { 8091 try { 8092 String pkg = 8093 mStackSupervisor.mLockTaskModeTask.intent.getComponent().getPackageName(); 8094 int uid = mContext.getPackageManager().getPackageUid(pkg, 8095 Binder.getCallingUserHandle().getIdentifier()); 8096 if (uid != callingUid) { 8097 throw new SecurityException("Invalid uid, expected " + uid); 8098 } 8099 } catch (NameNotFoundException e) { 8100 Log.d(TAG, "stopLockTaskMode " + e); 8101 return; 8102 } 8103 } 8104 long ident = Binder.clearCallingIdentity(); 8105 try { 8106 Log.d(TAG, "stopLockTaskMode"); 8107 // Stop lock task 8108 synchronized (this) { 8109 mStackSupervisor.setLockTaskModeLocked(null, false); 8110 } 8111 } finally { 8112 Binder.restoreCallingIdentity(ident); 8113 } 8114 } 8115 8116 @Override 8117 public void stopLockTaskModeOnCurrent() throws RemoteException { 8118 checkCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS); 8119 long ident = Binder.clearCallingIdentity(); 8120 try { 8121 stopLockTaskMode(); 8122 } finally { 8123 Binder.restoreCallingIdentity(ident); 8124 } 8125 } 8126 8127 @Override 8128 public boolean isInLockTaskMode() { 8129 synchronized (this) { 8130 return mStackSupervisor.isInLockTaskMode(); 8131 } 8132 } 8133 8134 // ========================================================= 8135 // CONTENT PROVIDERS 8136 // ========================================================= 8137 8138 private final List<ProviderInfo> generateApplicationProvidersLocked(ProcessRecord app) { 8139 List<ProviderInfo> providers = null; 8140 try { 8141 providers = AppGlobals.getPackageManager(). 8142 queryContentProviders(app.processName, app.uid, 8143 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS); 8144 } catch (RemoteException ex) { 8145 } 8146 if (DEBUG_MU) 8147 Slog.v(TAG_MU, "generateApplicationProvidersLocked, app.info.uid = " + app.uid); 8148 int userId = app.userId; 8149 if (providers != null) { 8150 int N = providers.size(); 8151 app.pubProviders.ensureCapacity(N + app.pubProviders.size()); 8152 for (int i=0; i<N; i++) { 8153 ProviderInfo cpi = 8154 (ProviderInfo)providers.get(i); 8155 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo, 8156 cpi.name, cpi.flags); 8157 if (singleton && UserHandle.getUserId(app.uid) != 0) { 8158 // This is a singleton provider, but a user besides the 8159 // default user is asking to initialize a process it runs 8160 // in... well, no, it doesn't actually run in this process, 8161 // it runs in the process of the default user. Get rid of it. 8162 providers.remove(i); 8163 N--; 8164 i--; 8165 continue; 8166 } 8167 8168 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 8169 ContentProviderRecord cpr = mProviderMap.getProviderByClass(comp, userId); 8170 if (cpr == null) { 8171 cpr = new ContentProviderRecord(this, cpi, app.info, comp, singleton); 8172 mProviderMap.putProviderByClass(comp, cpr); 8173 } 8174 if (DEBUG_MU) 8175 Slog.v(TAG_MU, "generateApplicationProvidersLocked, cpi.uid = " + cpr.uid); 8176 app.pubProviders.put(cpi.name, cpr); 8177 if (!cpi.multiprocess || !"android".equals(cpi.packageName)) { 8178 // Don't add this if it is a platform component that is marked 8179 // to run in multiple processes, because this is actually 8180 // part of the framework so doesn't make sense to track as a 8181 // separate apk in the process. 8182 app.addPackage(cpi.applicationInfo.packageName, cpi.applicationInfo.versionCode, 8183 mProcessStats); 8184 } 8185 ensurePackageDexOpt(cpi.applicationInfo.packageName); 8186 } 8187 } 8188 return providers; 8189 } 8190 8191 /** 8192 * Check if {@link ProcessRecord} has a possible chance at accessing the 8193 * given {@link ProviderInfo}. Final permission checking is always done 8194 * in {@link ContentProvider}. 8195 */ 8196 private final String checkContentProviderPermissionLocked( 8197 ProviderInfo cpi, ProcessRecord r, int userId, boolean checkUser) { 8198 final int callingPid = (r != null) ? r.pid : Binder.getCallingPid(); 8199 final int callingUid = (r != null) ? r.uid : Binder.getCallingUid(); 8200 boolean checkedGrants = false; 8201 if (checkUser) { 8202 // Looking for cross-user grants before enforcing the typical cross-users permissions 8203 int tmpTargetUserId = unsafeConvertIncomingUser(userId); 8204 if (tmpTargetUserId != UserHandle.getUserId(callingUid)) { 8205 if (checkAuthorityGrants(callingUid, cpi, tmpTargetUserId, checkUser)) { 8206 return null; 8207 } 8208 checkedGrants = true; 8209 } 8210 userId = handleIncomingUser(callingPid, callingUid, userId, 8211 false, ALLOW_NON_FULL, 8212 "checkContentProviderPermissionLocked " + cpi.authority, null); 8213 if (userId != tmpTargetUserId) { 8214 // When we actually went to determine the final targer user ID, this ended 8215 // up different than our initial check for the authority. This is because 8216 // they had asked for USER_CURRENT_OR_SELF and we ended up switching to 8217 // SELF. So we need to re-check the grants again. 8218 checkedGrants = false; 8219 } 8220 } 8221 if (checkComponentPermission(cpi.readPermission, callingPid, callingUid, 8222 cpi.applicationInfo.uid, cpi.exported) 8223 == PackageManager.PERMISSION_GRANTED) { 8224 return null; 8225 } 8226 if (checkComponentPermission(cpi.writePermission, callingPid, callingUid, 8227 cpi.applicationInfo.uid, cpi.exported) 8228 == PackageManager.PERMISSION_GRANTED) { 8229 return null; 8230 } 8231 8232 PathPermission[] pps = cpi.pathPermissions; 8233 if (pps != null) { 8234 int i = pps.length; 8235 while (i > 0) { 8236 i--; 8237 PathPermission pp = pps[i]; 8238 String pprperm = pp.getReadPermission(); 8239 if (pprperm != null && checkComponentPermission(pprperm, callingPid, callingUid, 8240 cpi.applicationInfo.uid, cpi.exported) 8241 == PackageManager.PERMISSION_GRANTED) { 8242 return null; 8243 } 8244 String ppwperm = pp.getWritePermission(); 8245 if (ppwperm != null && checkComponentPermission(ppwperm, callingPid, callingUid, 8246 cpi.applicationInfo.uid, cpi.exported) 8247 == PackageManager.PERMISSION_GRANTED) { 8248 return null; 8249 } 8250 } 8251 } 8252 if (!checkedGrants && checkAuthorityGrants(callingUid, cpi, userId, checkUser)) { 8253 return null; 8254 } 8255 8256 String msg; 8257 if (!cpi.exported) { 8258 msg = "Permission Denial: opening provider " + cpi.name 8259 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 8260 + ", uid=" + callingUid + ") that is not exported from uid " 8261 + cpi.applicationInfo.uid; 8262 } else { 8263 msg = "Permission Denial: opening provider " + cpi.name 8264 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 8265 + ", uid=" + callingUid + ") requires " 8266 + cpi.readPermission + " or " + cpi.writePermission; 8267 } 8268 Slog.w(TAG, msg); 8269 return msg; 8270 } 8271 8272 /** 8273 * Returns if the ContentProvider has granted a uri to callingUid 8274 */ 8275 boolean checkAuthorityGrants(int callingUid, ProviderInfo cpi, int userId, boolean checkUser) { 8276 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 8277 if (perms != null) { 8278 for (int i=perms.size()-1; i>=0; i--) { 8279 GrantUri grantUri = perms.keyAt(i); 8280 if (grantUri.sourceUserId == userId || !checkUser) { 8281 if (matchesProvider(grantUri.uri, cpi)) { 8282 return true; 8283 } 8284 } 8285 } 8286 } 8287 return false; 8288 } 8289 8290 /** 8291 * Returns true if the uri authority is one of the authorities specified in the provider. 8292 */ 8293 boolean matchesProvider(Uri uri, ProviderInfo cpi) { 8294 String uriAuth = uri.getAuthority(); 8295 String cpiAuth = cpi.authority; 8296 if (cpiAuth.indexOf(';') == -1) { 8297 return cpiAuth.equals(uriAuth); 8298 } 8299 String[] cpiAuths = cpiAuth.split(";"); 8300 int length = cpiAuths.length; 8301 for (int i = 0; i < length; i++) { 8302 if (cpiAuths[i].equals(uriAuth)) return true; 8303 } 8304 return false; 8305 } 8306 8307 ContentProviderConnection incProviderCountLocked(ProcessRecord r, 8308 final ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 8309 if (r != null) { 8310 for (int i=0; i<r.conProviders.size(); i++) { 8311 ContentProviderConnection conn = r.conProviders.get(i); 8312 if (conn.provider == cpr) { 8313 if (DEBUG_PROVIDER) Slog.v(TAG, 8314 "Adding provider requested by " 8315 + r.processName + " from process " 8316 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 8317 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 8318 if (stable) { 8319 conn.stableCount++; 8320 conn.numStableIncs++; 8321 } else { 8322 conn.unstableCount++; 8323 conn.numUnstableIncs++; 8324 } 8325 return conn; 8326 } 8327 } 8328 ContentProviderConnection conn = new ContentProviderConnection(cpr, r); 8329 if (stable) { 8330 conn.stableCount = 1; 8331 conn.numStableIncs = 1; 8332 } else { 8333 conn.unstableCount = 1; 8334 conn.numUnstableIncs = 1; 8335 } 8336 cpr.connections.add(conn); 8337 r.conProviders.add(conn); 8338 return conn; 8339 } 8340 cpr.addExternalProcessHandleLocked(externalProcessToken); 8341 return null; 8342 } 8343 8344 boolean decProviderCountLocked(ContentProviderConnection conn, 8345 ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 8346 if (conn != null) { 8347 cpr = conn.provider; 8348 if (DEBUG_PROVIDER) Slog.v(TAG, 8349 "Removing provider requested by " 8350 + conn.client.processName + " from process " 8351 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 8352 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 8353 if (stable) { 8354 conn.stableCount--; 8355 } else { 8356 conn.unstableCount--; 8357 } 8358 if (conn.stableCount == 0 && conn.unstableCount == 0) { 8359 cpr.connections.remove(conn); 8360 conn.client.conProviders.remove(conn); 8361 return true; 8362 } 8363 return false; 8364 } 8365 cpr.removeExternalProcessHandleLocked(externalProcessToken); 8366 return false; 8367 } 8368 8369 private final ContentProviderHolder getContentProviderImpl(IApplicationThread caller, 8370 String name, IBinder token, boolean stable, int userId) { 8371 ContentProviderRecord cpr; 8372 ContentProviderConnection conn = null; 8373 ProviderInfo cpi = null; 8374 8375 synchronized(this) { 8376 ProcessRecord r = null; 8377 if (caller != null) { 8378 r = getRecordForAppLocked(caller); 8379 if (r == null) { 8380 throw new SecurityException( 8381 "Unable to find app for caller " + caller 8382 + " (pid=" + Binder.getCallingPid() 8383 + ") when getting content provider " + name); 8384 } 8385 } 8386 8387 boolean checkCrossUser = true; 8388 8389 // First check if this content provider has been published... 8390 cpr = mProviderMap.getProviderByName(name, userId); 8391 // If that didn't work, check if it exists for user 0 and then 8392 // verify that it's a singleton provider before using it. 8393 if (cpr == null && userId != UserHandle.USER_OWNER) { 8394 cpr = mProviderMap.getProviderByName(name, UserHandle.USER_OWNER); 8395 if (cpr != null) { 8396 cpi = cpr.info; 8397 if (isSingleton(cpi.processName, cpi.applicationInfo, 8398 cpi.name, cpi.flags) 8399 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid)) { 8400 userId = UserHandle.USER_OWNER; 8401 checkCrossUser = false; 8402 } else { 8403 cpr = null; 8404 cpi = null; 8405 } 8406 } 8407 } 8408 8409 boolean providerRunning = cpr != null; 8410 if (providerRunning) { 8411 cpi = cpr.info; 8412 String msg; 8413 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, checkCrossUser)) 8414 != null) { 8415 throw new SecurityException(msg); 8416 } 8417 8418 if (r != null && cpr.canRunHere(r)) { 8419 // This provider has been published or is in the process 8420 // of being published... but it is also allowed to run 8421 // in the caller's process, so don't make a connection 8422 // and just let the caller instantiate its own instance. 8423 ContentProviderHolder holder = cpr.newHolder(null); 8424 // don't give caller the provider object, it needs 8425 // to make its own. 8426 holder.provider = null; 8427 return holder; 8428 } 8429 8430 final long origId = Binder.clearCallingIdentity(); 8431 8432 // In this case the provider instance already exists, so we can 8433 // return it right away. 8434 conn = incProviderCountLocked(r, cpr, token, stable); 8435 if (conn != null && (conn.stableCount+conn.unstableCount) == 1) { 8436 if (cpr.proc != null && r.setAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 8437 // If this is a perceptible app accessing the provider, 8438 // make sure to count it as being accessed and thus 8439 // back up on the LRU list. This is good because 8440 // content providers are often expensive to start. 8441 updateLruProcessLocked(cpr.proc, false, null); 8442 } 8443 } 8444 8445 if (cpr.proc != null) { 8446 if (false) { 8447 if (cpr.name.flattenToShortString().equals( 8448 "com.android.providers.calendar/.CalendarProvider2")) { 8449 Slog.v(TAG, "****************** KILLING " 8450 + cpr.name.flattenToShortString()); 8451 Process.killProcess(cpr.proc.pid); 8452 } 8453 } 8454 boolean success = updateOomAdjLocked(cpr.proc); 8455 if (DEBUG_PROVIDER) Slog.i(TAG, "Adjust success: " + success); 8456 // NOTE: there is still a race here where a signal could be 8457 // pending on the process even though we managed to update its 8458 // adj level. Not sure what to do about this, but at least 8459 // the race is now smaller. 8460 if (!success) { 8461 // Uh oh... it looks like the provider's process 8462 // has been killed on us. We need to wait for a new 8463 // process to be started, and make sure its death 8464 // doesn't kill our process. 8465 Slog.i(TAG, 8466 "Existing provider " + cpr.name.flattenToShortString() 8467 + " is crashing; detaching " + r); 8468 boolean lastRef = decProviderCountLocked(conn, cpr, token, stable); 8469 appDiedLocked(cpr.proc, cpr.proc.pid, cpr.proc.thread); 8470 if (!lastRef) { 8471 // This wasn't the last ref our process had on 8472 // the provider... we have now been killed, bail. 8473 return null; 8474 } 8475 providerRunning = false; 8476 conn = null; 8477 } 8478 } 8479 8480 Binder.restoreCallingIdentity(origId); 8481 } 8482 8483 boolean singleton; 8484 if (!providerRunning) { 8485 try { 8486 cpi = AppGlobals.getPackageManager(). 8487 resolveContentProvider(name, 8488 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS, userId); 8489 } catch (RemoteException ex) { 8490 } 8491 if (cpi == null) { 8492 return null; 8493 } 8494 // If the provider is a singleton AND 8495 // (it's a call within the same user || the provider is a 8496 // privileged app) 8497 // Then allow connecting to the singleton provider 8498 singleton = isSingleton(cpi.processName, cpi.applicationInfo, 8499 cpi.name, cpi.flags) 8500 && isValidSingletonCall(r.uid, cpi.applicationInfo.uid); 8501 if (singleton) { 8502 userId = UserHandle.USER_OWNER; 8503 } 8504 cpi.applicationInfo = getAppInfoForUser(cpi.applicationInfo, userId); 8505 8506 String msg; 8507 if ((msg = checkContentProviderPermissionLocked(cpi, r, userId, !singleton)) 8508 != null) { 8509 throw new SecurityException(msg); 8510 } 8511 8512 if (!mProcessesReady && !mDidUpdate && !mWaitingUpdate 8513 && !cpi.processName.equals("system")) { 8514 // If this content provider does not run in the system 8515 // process, and the system is not yet ready to run other 8516 // processes, then fail fast instead of hanging. 8517 throw new IllegalArgumentException( 8518 "Attempt to launch content provider before system ready"); 8519 } 8520 8521 // Make sure that the user who owns this provider is started. If not, 8522 // we don't want to allow it to run. 8523 if (mStartedUsers.get(userId) == null) { 8524 Slog.w(TAG, "Unable to launch app " 8525 + cpi.applicationInfo.packageName + "/" 8526 + cpi.applicationInfo.uid + " for provider " 8527 + name + ": user " + userId + " is stopped"); 8528 return null; 8529 } 8530 8531 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 8532 cpr = mProviderMap.getProviderByClass(comp, userId); 8533 final boolean firstClass = cpr == null; 8534 if (firstClass) { 8535 try { 8536 ApplicationInfo ai = 8537 AppGlobals.getPackageManager(). 8538 getApplicationInfo( 8539 cpi.applicationInfo.packageName, 8540 STOCK_PM_FLAGS, userId); 8541 if (ai == null) { 8542 Slog.w(TAG, "No package info for content provider " 8543 + cpi.name); 8544 return null; 8545 } 8546 ai = getAppInfoForUser(ai, userId); 8547 cpr = new ContentProviderRecord(this, cpi, ai, comp, singleton); 8548 } catch (RemoteException ex) { 8549 // pm is in same process, this will never happen. 8550 } 8551 } 8552 8553 if (r != null && cpr.canRunHere(r)) { 8554 // If this is a multiprocess provider, then just return its 8555 // info and allow the caller to instantiate it. Only do 8556 // this if the provider is the same user as the caller's 8557 // process, or can run as root (so can be in any process). 8558 return cpr.newHolder(null); 8559 } 8560 8561 if (DEBUG_PROVIDER) { 8562 RuntimeException e = new RuntimeException("here"); 8563 Slog.w(TAG, "LAUNCHING REMOTE PROVIDER (myuid " + (r != null ? r.uid : null) 8564 + " pruid " + cpr.appInfo.uid + "): " + cpr.info.name, e); 8565 } 8566 8567 // This is single process, and our app is now connecting to it. 8568 // See if we are already in the process of launching this 8569 // provider. 8570 final int N = mLaunchingProviders.size(); 8571 int i; 8572 for (i=0; i<N; i++) { 8573 if (mLaunchingProviders.get(i) == cpr) { 8574 break; 8575 } 8576 } 8577 8578 // If the provider is not already being launched, then get it 8579 // started. 8580 if (i >= N) { 8581 final long origId = Binder.clearCallingIdentity(); 8582 8583 try { 8584 // Content provider is now in use, its package can't be stopped. 8585 try { 8586 AppGlobals.getPackageManager().setPackageStoppedState( 8587 cpr.appInfo.packageName, false, userId); 8588 } catch (RemoteException e) { 8589 } catch (IllegalArgumentException e) { 8590 Slog.w(TAG, "Failed trying to unstop package " 8591 + cpr.appInfo.packageName + ": " + e); 8592 } 8593 8594 // Use existing process if already started 8595 ProcessRecord proc = getProcessRecordLocked( 8596 cpi.processName, cpr.appInfo.uid, false); 8597 if (proc != null && proc.thread != null) { 8598 if (DEBUG_PROVIDER) { 8599 Slog.d(TAG, "Installing in existing process " + proc); 8600 } 8601 proc.pubProviders.put(cpi.name, cpr); 8602 try { 8603 proc.thread.scheduleInstallProvider(cpi); 8604 } catch (RemoteException e) { 8605 } 8606 } else { 8607 proc = startProcessLocked(cpi.processName, 8608 cpr.appInfo, false, 0, "content provider", 8609 new ComponentName(cpi.applicationInfo.packageName, 8610 cpi.name), false, false, false); 8611 if (proc == null) { 8612 Slog.w(TAG, "Unable to launch app " 8613 + cpi.applicationInfo.packageName + "/" 8614 + cpi.applicationInfo.uid + " for provider " 8615 + name + ": process is bad"); 8616 return null; 8617 } 8618 } 8619 cpr.launchingApp = proc; 8620 mLaunchingProviders.add(cpr); 8621 } finally { 8622 Binder.restoreCallingIdentity(origId); 8623 } 8624 } 8625 8626 // Make sure the provider is published (the same provider class 8627 // may be published under multiple names). 8628 if (firstClass) { 8629 mProviderMap.putProviderByClass(comp, cpr); 8630 } 8631 8632 mProviderMap.putProviderByName(name, cpr); 8633 conn = incProviderCountLocked(r, cpr, token, stable); 8634 if (conn != null) { 8635 conn.waiting = true; 8636 } 8637 } 8638 } 8639 8640 // Wait for the provider to be published... 8641 synchronized (cpr) { 8642 while (cpr.provider == null) { 8643 if (cpr.launchingApp == null) { 8644 Slog.w(TAG, "Unable to launch app " 8645 + cpi.applicationInfo.packageName + "/" 8646 + cpi.applicationInfo.uid + " for provider " 8647 + name + ": launching app became null"); 8648 EventLog.writeEvent(EventLogTags.AM_PROVIDER_LOST_PROCESS, 8649 UserHandle.getUserId(cpi.applicationInfo.uid), 8650 cpi.applicationInfo.packageName, 8651 cpi.applicationInfo.uid, name); 8652 return null; 8653 } 8654 try { 8655 if (DEBUG_MU) { 8656 Slog.v(TAG_MU, "Waiting to start provider " + cpr + " launchingApp=" 8657 + cpr.launchingApp); 8658 } 8659 if (conn != null) { 8660 conn.waiting = true; 8661 } 8662 cpr.wait(); 8663 } catch (InterruptedException ex) { 8664 } finally { 8665 if (conn != null) { 8666 conn.waiting = false; 8667 } 8668 } 8669 } 8670 } 8671 return cpr != null ? cpr.newHolder(conn) : null; 8672 } 8673 8674 @Override 8675 public final ContentProviderHolder getContentProvider( 8676 IApplicationThread caller, String name, int userId, boolean stable) { 8677 enforceNotIsolatedCaller("getContentProvider"); 8678 if (caller == null) { 8679 String msg = "null IApplicationThread when getting content provider " 8680 + name; 8681 Slog.w(TAG, msg); 8682 throw new SecurityException(msg); 8683 } 8684 // The incoming user check is now handled in checkContentProviderPermissionLocked() to deal 8685 // with cross-user grant. 8686 return getContentProviderImpl(caller, name, null, stable, userId); 8687 } 8688 8689 public ContentProviderHolder getContentProviderExternal( 8690 String name, int userId, IBinder token) { 8691 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 8692 "Do not have permission in call getContentProviderExternal()"); 8693 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 8694 false, ALLOW_FULL_ONLY, "getContentProvider", null); 8695 return getContentProviderExternalUnchecked(name, token, userId); 8696 } 8697 8698 private ContentProviderHolder getContentProviderExternalUnchecked(String name, 8699 IBinder token, int userId) { 8700 return getContentProviderImpl(null, name, token, true, userId); 8701 } 8702 8703 /** 8704 * Drop a content provider from a ProcessRecord's bookkeeping 8705 */ 8706 public void removeContentProvider(IBinder connection, boolean stable) { 8707 enforceNotIsolatedCaller("removeContentProvider"); 8708 long ident = Binder.clearCallingIdentity(); 8709 try { 8710 synchronized (this) { 8711 ContentProviderConnection conn; 8712 try { 8713 conn = (ContentProviderConnection)connection; 8714 } catch (ClassCastException e) { 8715 String msg ="removeContentProvider: " + connection 8716 + " not a ContentProviderConnection"; 8717 Slog.w(TAG, msg); 8718 throw new IllegalArgumentException(msg); 8719 } 8720 if (conn == null) { 8721 throw new NullPointerException("connection is null"); 8722 } 8723 if (decProviderCountLocked(conn, null, null, stable)) { 8724 updateOomAdjLocked(); 8725 } 8726 } 8727 } finally { 8728 Binder.restoreCallingIdentity(ident); 8729 } 8730 } 8731 8732 public void removeContentProviderExternal(String name, IBinder token) { 8733 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 8734 "Do not have permission in call removeContentProviderExternal()"); 8735 removeContentProviderExternalUnchecked(name, token, UserHandle.getCallingUserId()); 8736 } 8737 8738 private void removeContentProviderExternalUnchecked(String name, IBinder token, int userId) { 8739 synchronized (this) { 8740 ContentProviderRecord cpr = mProviderMap.getProviderByName(name, userId); 8741 if(cpr == null) { 8742 //remove from mProvidersByClass 8743 if(localLOGV) Slog.v(TAG, name+" content provider not found in providers list"); 8744 return; 8745 } 8746 8747 //update content provider record entry info 8748 ComponentName comp = new ComponentName(cpr.info.packageName, cpr.info.name); 8749 ContentProviderRecord localCpr = mProviderMap.getProviderByClass(comp, userId); 8750 if (localCpr.hasExternalProcessHandles()) { 8751 if (localCpr.removeExternalProcessHandleLocked(token)) { 8752 updateOomAdjLocked(); 8753 } else { 8754 Slog.e(TAG, "Attmpt to remove content provider " + localCpr 8755 + " with no external reference for token: " 8756 + token + "."); 8757 } 8758 } else { 8759 Slog.e(TAG, "Attmpt to remove content provider: " + localCpr 8760 + " with no external references."); 8761 } 8762 } 8763 } 8764 8765 public final void publishContentProviders(IApplicationThread caller, 8766 List<ContentProviderHolder> providers) { 8767 if (providers == null) { 8768 return; 8769 } 8770 8771 enforceNotIsolatedCaller("publishContentProviders"); 8772 synchronized (this) { 8773 final ProcessRecord r = getRecordForAppLocked(caller); 8774 if (DEBUG_MU) 8775 Slog.v(TAG_MU, "ProcessRecord uid = " + r.uid); 8776 if (r == null) { 8777 throw new SecurityException( 8778 "Unable to find app for caller " + caller 8779 + " (pid=" + Binder.getCallingPid() 8780 + ") when publishing content providers"); 8781 } 8782 8783 final long origId = Binder.clearCallingIdentity(); 8784 8785 final int N = providers.size(); 8786 for (int i=0; i<N; i++) { 8787 ContentProviderHolder src = providers.get(i); 8788 if (src == null || src.info == null || src.provider == null) { 8789 continue; 8790 } 8791 ContentProviderRecord dst = r.pubProviders.get(src.info.name); 8792 if (DEBUG_MU) 8793 Slog.v(TAG_MU, "ContentProviderRecord uid = " + dst.uid); 8794 if (dst != null) { 8795 ComponentName comp = new ComponentName(dst.info.packageName, dst.info.name); 8796 mProviderMap.putProviderByClass(comp, dst); 8797 String names[] = dst.info.authority.split(";"); 8798 for (int j = 0; j < names.length; j++) { 8799 mProviderMap.putProviderByName(names[j], dst); 8800 } 8801 8802 int NL = mLaunchingProviders.size(); 8803 int j; 8804 for (j=0; j<NL; j++) { 8805 if (mLaunchingProviders.get(j) == dst) { 8806 mLaunchingProviders.remove(j); 8807 j--; 8808 NL--; 8809 } 8810 } 8811 synchronized (dst) { 8812 dst.provider = src.provider; 8813 dst.proc = r; 8814 dst.notifyAll(); 8815 } 8816 updateOomAdjLocked(r); 8817 } 8818 } 8819 8820 Binder.restoreCallingIdentity(origId); 8821 } 8822 } 8823 8824 public boolean refContentProvider(IBinder connection, int stable, int unstable) { 8825 ContentProviderConnection conn; 8826 try { 8827 conn = (ContentProviderConnection)connection; 8828 } catch (ClassCastException e) { 8829 String msg ="refContentProvider: " + connection 8830 + " not a ContentProviderConnection"; 8831 Slog.w(TAG, msg); 8832 throw new IllegalArgumentException(msg); 8833 } 8834 if (conn == null) { 8835 throw new NullPointerException("connection is null"); 8836 } 8837 8838 synchronized (this) { 8839 if (stable > 0) { 8840 conn.numStableIncs += stable; 8841 } 8842 stable = conn.stableCount + stable; 8843 if (stable < 0) { 8844 throw new IllegalStateException("stableCount < 0: " + stable); 8845 } 8846 8847 if (unstable > 0) { 8848 conn.numUnstableIncs += unstable; 8849 } 8850 unstable = conn.unstableCount + unstable; 8851 if (unstable < 0) { 8852 throw new IllegalStateException("unstableCount < 0: " + unstable); 8853 } 8854 8855 if ((stable+unstable) <= 0) { 8856 throw new IllegalStateException("ref counts can't go to zero here: stable=" 8857 + stable + " unstable=" + unstable); 8858 } 8859 conn.stableCount = stable; 8860 conn.unstableCount = unstable; 8861 return !conn.dead; 8862 } 8863 } 8864 8865 public void unstableProviderDied(IBinder connection) { 8866 ContentProviderConnection conn; 8867 try { 8868 conn = (ContentProviderConnection)connection; 8869 } catch (ClassCastException e) { 8870 String msg ="refContentProvider: " + connection 8871 + " not a ContentProviderConnection"; 8872 Slog.w(TAG, msg); 8873 throw new IllegalArgumentException(msg); 8874 } 8875 if (conn == null) { 8876 throw new NullPointerException("connection is null"); 8877 } 8878 8879 // Safely retrieve the content provider associated with the connection. 8880 IContentProvider provider; 8881 synchronized (this) { 8882 provider = conn.provider.provider; 8883 } 8884 8885 if (provider == null) { 8886 // Um, yeah, we're way ahead of you. 8887 return; 8888 } 8889 8890 // Make sure the caller is being honest with us. 8891 if (provider.asBinder().pingBinder()) { 8892 // Er, no, still looks good to us. 8893 synchronized (this) { 8894 Slog.w(TAG, "unstableProviderDied: caller " + Binder.getCallingUid() 8895 + " says " + conn + " died, but we don't agree"); 8896 return; 8897 } 8898 } 8899 8900 // Well look at that! It's dead! 8901 synchronized (this) { 8902 if (conn.provider.provider != provider) { 8903 // But something changed... good enough. 8904 return; 8905 } 8906 8907 ProcessRecord proc = conn.provider.proc; 8908 if (proc == null || proc.thread == null) { 8909 // Seems like the process is already cleaned up. 8910 return; 8911 } 8912 8913 // As far as we're concerned, this is just like receiving a 8914 // death notification... just a bit prematurely. 8915 Slog.i(TAG, "Process " + proc.processName + " (pid " + proc.pid 8916 + ") early provider death"); 8917 final long ident = Binder.clearCallingIdentity(); 8918 try { 8919 appDiedLocked(proc, proc.pid, proc.thread); 8920 } finally { 8921 Binder.restoreCallingIdentity(ident); 8922 } 8923 } 8924 } 8925 8926 @Override 8927 public void appNotRespondingViaProvider(IBinder connection) { 8928 enforceCallingPermission( 8929 android.Manifest.permission.REMOVE_TASKS, "appNotRespondingViaProvider()"); 8930 8931 final ContentProviderConnection conn = (ContentProviderConnection) connection; 8932 if (conn == null) { 8933 Slog.w(TAG, "ContentProviderConnection is null"); 8934 return; 8935 } 8936 8937 final ProcessRecord host = conn.provider.proc; 8938 if (host == null) { 8939 Slog.w(TAG, "Failed to find hosting ProcessRecord"); 8940 return; 8941 } 8942 8943 final long token = Binder.clearCallingIdentity(); 8944 try { 8945 appNotResponding(host, null, null, false, "ContentProvider not responding"); 8946 } finally { 8947 Binder.restoreCallingIdentity(token); 8948 } 8949 } 8950 8951 public final void installSystemProviders() { 8952 List<ProviderInfo> providers; 8953 synchronized (this) { 8954 ProcessRecord app = mProcessNames.get("system", Process.SYSTEM_UID); 8955 providers = generateApplicationProvidersLocked(app); 8956 if (providers != null) { 8957 for (int i=providers.size()-1; i>=0; i--) { 8958 ProviderInfo pi = (ProviderInfo)providers.get(i); 8959 if ((pi.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) == 0) { 8960 Slog.w(TAG, "Not installing system proc provider " + pi.name 8961 + ": not system .apk"); 8962 providers.remove(i); 8963 } 8964 } 8965 } 8966 } 8967 if (providers != null) { 8968 mSystemThread.installSystemProviders(providers); 8969 } 8970 8971 mCoreSettingsObserver = new CoreSettingsObserver(this); 8972 8973 //mUsageStatsService.monitorPackages(); 8974 } 8975 8976 /** 8977 * Allows apps to retrieve the MIME type of a URI. 8978 * If an app is in the same user as the ContentProvider, or if it is allowed to interact across 8979 * users, then it does not need permission to access the ContentProvider. 8980 * Either, it needs cross-user uri grants. 8981 * 8982 * CTS tests for this functionality can be run with "runtest cts-appsecurity". 8983 * 8984 * Test cases are at cts/tests/appsecurity-tests/test-apps/UsePermissionDiffCert/ 8985 * src/com/android/cts/usespermissiondiffcertapp/AccessPermissionWithDiffSigTest.java 8986 */ 8987 public String getProviderMimeType(Uri uri, int userId) { 8988 enforceNotIsolatedCaller("getProviderMimeType"); 8989 final String name = uri.getAuthority(); 8990 int callingUid = Binder.getCallingUid(); 8991 int callingPid = Binder.getCallingPid(); 8992 long ident = 0; 8993 boolean clearedIdentity = false; 8994 userId = unsafeConvertIncomingUser(userId); 8995 if (UserHandle.getUserId(callingUid) != userId) { 8996 if (checkComponentPermission(INTERACT_ACROSS_USERS, callingPid, 8997 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED 8998 || checkComponentPermission(INTERACT_ACROSS_USERS_FULL, callingPid, 8999 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED) { 9000 clearedIdentity = true; 9001 ident = Binder.clearCallingIdentity(); 9002 } 9003 } 9004 ContentProviderHolder holder = null; 9005 try { 9006 holder = getContentProviderExternalUnchecked(name, null, userId); 9007 if (holder != null) { 9008 return holder.provider.getType(uri); 9009 } 9010 } catch (RemoteException e) { 9011 Log.w(TAG, "Content provider dead retrieving " + uri, e); 9012 return null; 9013 } finally { 9014 // We need to clear the identity to call removeContentProviderExternalUnchecked 9015 if (!clearedIdentity) { 9016 ident = Binder.clearCallingIdentity(); 9017 } 9018 try { 9019 if (holder != null) { 9020 removeContentProviderExternalUnchecked(name, null, userId); 9021 } 9022 } finally { 9023 Binder.restoreCallingIdentity(ident); 9024 } 9025 } 9026 9027 return null; 9028 } 9029 9030 // ========================================================= 9031 // GLOBAL MANAGEMENT 9032 // ========================================================= 9033 9034 final ProcessRecord newProcessRecordLocked(ApplicationInfo info, String customProcess, 9035 boolean isolated, int isolatedUid) { 9036 String proc = customProcess != null ? customProcess : info.processName; 9037 BatteryStatsImpl.Uid.Proc ps = null; 9038 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 9039 int uid = info.uid; 9040 if (isolated) { 9041 if (isolatedUid == 0) { 9042 int userId = UserHandle.getUserId(uid); 9043 int stepsLeft = Process.LAST_ISOLATED_UID - Process.FIRST_ISOLATED_UID + 1; 9044 while (true) { 9045 if (mNextIsolatedProcessUid < Process.FIRST_ISOLATED_UID 9046 || mNextIsolatedProcessUid > Process.LAST_ISOLATED_UID) { 9047 mNextIsolatedProcessUid = Process.FIRST_ISOLATED_UID; 9048 } 9049 uid = UserHandle.getUid(userId, mNextIsolatedProcessUid); 9050 mNextIsolatedProcessUid++; 9051 if (mIsolatedProcesses.indexOfKey(uid) < 0) { 9052 // No process for this uid, use it. 9053 break; 9054 } 9055 stepsLeft--; 9056 if (stepsLeft <= 0) { 9057 return null; 9058 } 9059 } 9060 } else { 9061 // Special case for startIsolatedProcess (internal only), where 9062 // the uid of the isolated process is specified by the caller. 9063 uid = isolatedUid; 9064 } 9065 } 9066 return new ProcessRecord(stats, info, proc, uid); 9067 } 9068 9069 final ProcessRecord addAppLocked(ApplicationInfo info, boolean isolated, 9070 String abiOverride) { 9071 ProcessRecord app; 9072 if (!isolated) { 9073 app = getProcessRecordLocked(info.processName, info.uid, true); 9074 } else { 9075 app = null; 9076 } 9077 9078 if (app == null) { 9079 app = newProcessRecordLocked(info, null, isolated, 0); 9080 mProcessNames.put(info.processName, app.uid, app); 9081 if (isolated) { 9082 mIsolatedProcesses.put(app.uid, app); 9083 } 9084 updateLruProcessLocked(app, false, null); 9085 updateOomAdjLocked(); 9086 } 9087 9088 // This package really, really can not be stopped. 9089 try { 9090 AppGlobals.getPackageManager().setPackageStoppedState( 9091 info.packageName, false, UserHandle.getUserId(app.uid)); 9092 } catch (RemoteException e) { 9093 } catch (IllegalArgumentException e) { 9094 Slog.w(TAG, "Failed trying to unstop package " 9095 + info.packageName + ": " + e); 9096 } 9097 9098 if ((info.flags&(ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) 9099 == (ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) { 9100 app.persistent = true; 9101 app.maxAdj = ProcessList.PERSISTENT_PROC_ADJ; 9102 } 9103 if (app.thread == null && mPersistentStartingProcesses.indexOf(app) < 0) { 9104 mPersistentStartingProcesses.add(app); 9105 startProcessLocked(app, "added application", app.processName, abiOverride, 9106 null /* entryPoint */, null /* entryPointArgs */); 9107 } 9108 9109 return app; 9110 } 9111 9112 public void unhandledBack() { 9113 enforceCallingPermission(android.Manifest.permission.FORCE_BACK, 9114 "unhandledBack()"); 9115 9116 synchronized(this) { 9117 final long origId = Binder.clearCallingIdentity(); 9118 try { 9119 getFocusedStack().unhandledBackLocked(); 9120 } finally { 9121 Binder.restoreCallingIdentity(origId); 9122 } 9123 } 9124 } 9125 9126 public ParcelFileDescriptor openContentUri(Uri uri) throws RemoteException { 9127 enforceNotIsolatedCaller("openContentUri"); 9128 final int userId = UserHandle.getCallingUserId(); 9129 String name = uri.getAuthority(); 9130 ContentProviderHolder cph = getContentProviderExternalUnchecked(name, null, userId); 9131 ParcelFileDescriptor pfd = null; 9132 if (cph != null) { 9133 // We record the binder invoker's uid in thread-local storage before 9134 // going to the content provider to open the file. Later, in the code 9135 // that handles all permissions checks, we look for this uid and use 9136 // that rather than the Activity Manager's own uid. The effect is that 9137 // we do the check against the caller's permissions even though it looks 9138 // to the content provider like the Activity Manager itself is making 9139 // the request. 9140 sCallerIdentity.set(new Identity( 9141 Binder.getCallingPid(), Binder.getCallingUid())); 9142 try { 9143 pfd = cph.provider.openFile(null, uri, "r", null); 9144 } catch (FileNotFoundException e) { 9145 // do nothing; pfd will be returned null 9146 } finally { 9147 // Ensure that whatever happens, we clean up the identity state 9148 sCallerIdentity.remove(); 9149 } 9150 9151 // We've got the fd now, so we're done with the provider. 9152 removeContentProviderExternalUnchecked(name, null, userId); 9153 } else { 9154 Slog.d(TAG, "Failed to get provider for authority '" + name + "'"); 9155 } 9156 return pfd; 9157 } 9158 9159 // Actually is sleeping or shutting down or whatever else in the future 9160 // is an inactive state. 9161 public boolean isSleepingOrShuttingDown() { 9162 return mSleeping || mShuttingDown; 9163 } 9164 9165 public boolean isSleeping() { 9166 return mSleeping; 9167 } 9168 9169 void goingToSleep() { 9170 synchronized(this) { 9171 mWentToSleep = true; 9172 updateEventDispatchingLocked(); 9173 goToSleepIfNeededLocked(); 9174 } 9175 } 9176 9177 void finishRunningVoiceLocked() { 9178 if (mRunningVoice) { 9179 mRunningVoice = false; 9180 goToSleepIfNeededLocked(); 9181 } 9182 } 9183 9184 void goToSleepIfNeededLocked() { 9185 if (mWentToSleep && !mRunningVoice) { 9186 if (!mSleeping) { 9187 mSleeping = true; 9188 mStackSupervisor.goingToSleepLocked(); 9189 9190 // Initialize the wake times of all processes. 9191 checkExcessivePowerUsageLocked(false); 9192 mHandler.removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 9193 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 9194 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 9195 } 9196 } 9197 } 9198 9199 void notifyTaskPersisterLocked(TaskRecord task, boolean flush) { 9200 if (task != null && task.stack != null && task.stack.isHomeStack()) { 9201 // Never persist the home stack. 9202 return; 9203 } 9204 mTaskPersister.wakeup(task, flush); 9205 } 9206 9207 @Override 9208 public boolean shutdown(int timeout) { 9209 if (checkCallingPermission(android.Manifest.permission.SHUTDOWN) 9210 != PackageManager.PERMISSION_GRANTED) { 9211 throw new SecurityException("Requires permission " 9212 + android.Manifest.permission.SHUTDOWN); 9213 } 9214 9215 boolean timedout = false; 9216 9217 synchronized(this) { 9218 mShuttingDown = true; 9219 updateEventDispatchingLocked(); 9220 timedout = mStackSupervisor.shutdownLocked(timeout); 9221 } 9222 9223 mAppOpsService.shutdown(); 9224 if (mUsageStatsService != null) { 9225 mUsageStatsService.prepareShutdown(); 9226 } 9227 mBatteryStatsService.shutdown(); 9228 synchronized (this) { 9229 mProcessStats.shutdownLocked(); 9230 } 9231 notifyTaskPersisterLocked(null, true); 9232 9233 return timedout; 9234 } 9235 9236 public final void activitySlept(IBinder token) { 9237 if (localLOGV) Slog.v(TAG, "Activity slept: token=" + token); 9238 9239 final long origId = Binder.clearCallingIdentity(); 9240 9241 synchronized (this) { 9242 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9243 if (r != null) { 9244 mStackSupervisor.activitySleptLocked(r); 9245 } 9246 } 9247 9248 Binder.restoreCallingIdentity(origId); 9249 } 9250 9251 void logLockScreen(String msg) { 9252 if (DEBUG_LOCKSCREEN) Slog.d(TAG, Debug.getCallers(2) + ":" + msg + 9253 " mLockScreenShown=" + mLockScreenShown + " mWentToSleep=" + 9254 mWentToSleep + " mSleeping=" + mSleeping + " mDismissKeyguardOnNextActivity=" + 9255 mStackSupervisor.mDismissKeyguardOnNextActivity); 9256 } 9257 9258 private void comeOutOfSleepIfNeededLocked() { 9259 if ((!mWentToSleep && !mLockScreenShown) || mRunningVoice) { 9260 if (mSleeping) { 9261 mSleeping = false; 9262 mStackSupervisor.comeOutOfSleepIfNeededLocked(); 9263 } 9264 } 9265 } 9266 9267 void wakingUp() { 9268 synchronized(this) { 9269 mWentToSleep = false; 9270 updateEventDispatchingLocked(); 9271 comeOutOfSleepIfNeededLocked(); 9272 } 9273 } 9274 9275 void startRunningVoiceLocked() { 9276 if (!mRunningVoice) { 9277 mRunningVoice = true; 9278 comeOutOfSleepIfNeededLocked(); 9279 } 9280 } 9281 9282 private void updateEventDispatchingLocked() { 9283 mWindowManager.setEventDispatching(mBooted && !mWentToSleep && !mShuttingDown); 9284 } 9285 9286 public void setLockScreenShown(boolean shown) { 9287 if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER) 9288 != PackageManager.PERMISSION_GRANTED) { 9289 throw new SecurityException("Requires permission " 9290 + android.Manifest.permission.DEVICE_POWER); 9291 } 9292 9293 synchronized(this) { 9294 long ident = Binder.clearCallingIdentity(); 9295 try { 9296 if (DEBUG_LOCKSCREEN) logLockScreen(" shown=" + shown); 9297 mLockScreenShown = shown; 9298 comeOutOfSleepIfNeededLocked(); 9299 } finally { 9300 Binder.restoreCallingIdentity(ident); 9301 } 9302 } 9303 } 9304 9305 @Override 9306 public void stopAppSwitches() { 9307 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 9308 != PackageManager.PERMISSION_GRANTED) { 9309 throw new SecurityException("Requires permission " 9310 + android.Manifest.permission.STOP_APP_SWITCHES); 9311 } 9312 9313 synchronized(this) { 9314 mAppSwitchesAllowedTime = SystemClock.uptimeMillis() 9315 + APP_SWITCH_DELAY_TIME; 9316 mDidAppSwitch = false; 9317 mHandler.removeMessages(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 9318 Message msg = mHandler.obtainMessage(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 9319 mHandler.sendMessageDelayed(msg, APP_SWITCH_DELAY_TIME); 9320 } 9321 } 9322 9323 public void resumeAppSwitches() { 9324 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 9325 != PackageManager.PERMISSION_GRANTED) { 9326 throw new SecurityException("Requires permission " 9327 + android.Manifest.permission.STOP_APP_SWITCHES); 9328 } 9329 9330 synchronized(this) { 9331 // Note that we don't execute any pending app switches... we will 9332 // let those wait until either the timeout, or the next start 9333 // activity request. 9334 mAppSwitchesAllowedTime = 0; 9335 } 9336 } 9337 9338 boolean checkAppSwitchAllowedLocked(int callingPid, int callingUid, 9339 String name) { 9340 if (mAppSwitchesAllowedTime < SystemClock.uptimeMillis()) { 9341 return true; 9342 } 9343 9344 final int perm = checkComponentPermission( 9345 android.Manifest.permission.STOP_APP_SWITCHES, callingPid, 9346 callingUid, -1, true); 9347 if (perm == PackageManager.PERMISSION_GRANTED) { 9348 return true; 9349 } 9350 9351 Slog.w(TAG, name + " request from " + callingUid + " stopped"); 9352 return false; 9353 } 9354 9355 public void setDebugApp(String packageName, boolean waitForDebugger, 9356 boolean persistent) { 9357 enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP, 9358 "setDebugApp()"); 9359 9360 long ident = Binder.clearCallingIdentity(); 9361 try { 9362 // Note that this is not really thread safe if there are multiple 9363 // callers into it at the same time, but that's not a situation we 9364 // care about. 9365 if (persistent) { 9366 final ContentResolver resolver = mContext.getContentResolver(); 9367 Settings.Global.putString( 9368 resolver, Settings.Global.DEBUG_APP, 9369 packageName); 9370 Settings.Global.putInt( 9371 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 9372 waitForDebugger ? 1 : 0); 9373 } 9374 9375 synchronized (this) { 9376 if (!persistent) { 9377 mOrigDebugApp = mDebugApp; 9378 mOrigWaitForDebugger = mWaitForDebugger; 9379 } 9380 mDebugApp = packageName; 9381 mWaitForDebugger = waitForDebugger; 9382 mDebugTransient = !persistent; 9383 if (packageName != null) { 9384 forceStopPackageLocked(packageName, -1, false, false, true, true, 9385 false, UserHandle.USER_ALL, "set debug app"); 9386 } 9387 } 9388 } finally { 9389 Binder.restoreCallingIdentity(ident); 9390 } 9391 } 9392 9393 void setOpenGlTraceApp(ApplicationInfo app, String processName) { 9394 synchronized (this) { 9395 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 9396 if (!isDebuggable) { 9397 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 9398 throw new SecurityException("Process not debuggable: " + app.packageName); 9399 } 9400 } 9401 9402 mOpenGlTraceApp = processName; 9403 } 9404 } 9405 9406 void setProfileApp(ApplicationInfo app, String processName, String profileFile, 9407 ParcelFileDescriptor profileFd, boolean autoStopProfiler) { 9408 synchronized (this) { 9409 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 9410 if (!isDebuggable) { 9411 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 9412 throw new SecurityException("Process not debuggable: " + app.packageName); 9413 } 9414 } 9415 mProfileApp = processName; 9416 mProfileFile = profileFile; 9417 if (mProfileFd != null) { 9418 try { 9419 mProfileFd.close(); 9420 } catch (IOException e) { 9421 } 9422 mProfileFd = null; 9423 } 9424 mProfileFd = profileFd; 9425 mProfileType = 0; 9426 mAutoStopProfiler = autoStopProfiler; 9427 } 9428 } 9429 9430 @Override 9431 public void setAlwaysFinish(boolean enabled) { 9432 enforceCallingPermission(android.Manifest.permission.SET_ALWAYS_FINISH, 9433 "setAlwaysFinish()"); 9434 9435 Settings.Global.putInt( 9436 mContext.getContentResolver(), 9437 Settings.Global.ALWAYS_FINISH_ACTIVITIES, enabled ? 1 : 0); 9438 9439 synchronized (this) { 9440 mAlwaysFinishActivities = enabled; 9441 } 9442 } 9443 9444 @Override 9445 public void setActivityController(IActivityController controller) { 9446 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 9447 "setActivityController()"); 9448 synchronized (this) { 9449 mController = controller; 9450 Watchdog.getInstance().setActivityController(controller); 9451 } 9452 } 9453 9454 @Override 9455 public void setUserIsMonkey(boolean userIsMonkey) { 9456 synchronized (this) { 9457 synchronized (mPidsSelfLocked) { 9458 final int callingPid = Binder.getCallingPid(); 9459 ProcessRecord precessRecord = mPidsSelfLocked.get(callingPid); 9460 if (precessRecord == null) { 9461 throw new SecurityException("Unknown process: " + callingPid); 9462 } 9463 if (precessRecord.instrumentationUiAutomationConnection == null) { 9464 throw new SecurityException("Only an instrumentation process " 9465 + "with a UiAutomation can call setUserIsMonkey"); 9466 } 9467 } 9468 mUserIsMonkey = userIsMonkey; 9469 } 9470 } 9471 9472 @Override 9473 public boolean isUserAMonkey() { 9474 synchronized (this) { 9475 // If there is a controller also implies the user is a monkey. 9476 return (mUserIsMonkey || mController != null); 9477 } 9478 } 9479 9480 public void requestBugReport() { 9481 enforceCallingPermission(android.Manifest.permission.DUMP, "requestBugReport"); 9482 SystemProperties.set("ctl.start", "bugreport"); 9483 } 9484 9485 public static long getInputDispatchingTimeoutLocked(ActivityRecord r) { 9486 return r != null ? getInputDispatchingTimeoutLocked(r.app) : KEY_DISPATCHING_TIMEOUT; 9487 } 9488 9489 public static long getInputDispatchingTimeoutLocked(ProcessRecord r) { 9490 if (r != null && (r.instrumentationClass != null || r.usingWrapper)) { 9491 return INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT; 9492 } 9493 return KEY_DISPATCHING_TIMEOUT; 9494 } 9495 9496 @Override 9497 public long inputDispatchingTimedOut(int pid, final boolean aboveSystem, String reason) { 9498 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 9499 != PackageManager.PERMISSION_GRANTED) { 9500 throw new SecurityException("Requires permission " 9501 + android.Manifest.permission.FILTER_EVENTS); 9502 } 9503 ProcessRecord proc; 9504 long timeout; 9505 synchronized (this) { 9506 synchronized (mPidsSelfLocked) { 9507 proc = mPidsSelfLocked.get(pid); 9508 } 9509 timeout = getInputDispatchingTimeoutLocked(proc); 9510 } 9511 9512 if (!inputDispatchingTimedOut(proc, null, null, aboveSystem, reason)) { 9513 return -1; 9514 } 9515 9516 return timeout; 9517 } 9518 9519 /** 9520 * Handle input dispatching timeouts. 9521 * Returns whether input dispatching should be aborted or not. 9522 */ 9523 public boolean inputDispatchingTimedOut(final ProcessRecord proc, 9524 final ActivityRecord activity, final ActivityRecord parent, 9525 final boolean aboveSystem, String reason) { 9526 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 9527 != PackageManager.PERMISSION_GRANTED) { 9528 throw new SecurityException("Requires permission " 9529 + android.Manifest.permission.FILTER_EVENTS); 9530 } 9531 9532 final String annotation; 9533 if (reason == null) { 9534 annotation = "Input dispatching timed out"; 9535 } else { 9536 annotation = "Input dispatching timed out (" + reason + ")"; 9537 } 9538 9539 if (proc != null) { 9540 synchronized (this) { 9541 if (proc.debugging) { 9542 return false; 9543 } 9544 9545 if (mDidDexOpt) { 9546 // Give more time since we were dexopting. 9547 mDidDexOpt = false; 9548 return false; 9549 } 9550 9551 if (proc.instrumentationClass != null) { 9552 Bundle info = new Bundle(); 9553 info.putString("shortMsg", "keyDispatchingTimedOut"); 9554 info.putString("longMsg", annotation); 9555 finishInstrumentationLocked(proc, Activity.RESULT_CANCELED, info); 9556 return true; 9557 } 9558 } 9559 mHandler.post(new Runnable() { 9560 @Override 9561 public void run() { 9562 appNotResponding(proc, activity, parent, aboveSystem, annotation); 9563 } 9564 }); 9565 } 9566 9567 return true; 9568 } 9569 9570 public Bundle getAssistContextExtras(int requestType) { 9571 enforceCallingPermission(android.Manifest.permission.GET_TOP_ACTIVITY_INFO, 9572 "getAssistContextExtras()"); 9573 PendingAssistExtras pae; 9574 Bundle extras = new Bundle(); 9575 synchronized (this) { 9576 ActivityRecord activity = getFocusedStack().mResumedActivity; 9577 if (activity == null) { 9578 Slog.w(TAG, "getAssistContextExtras failed: no resumed activity"); 9579 return null; 9580 } 9581 extras.putString(Intent.EXTRA_ASSIST_PACKAGE, activity.packageName); 9582 if (activity.app == null || activity.app.thread == null) { 9583 Slog.w(TAG, "getAssistContextExtras failed: no process for " + activity); 9584 return extras; 9585 } 9586 if (activity.app.pid == Binder.getCallingPid()) { 9587 Slog.w(TAG, "getAssistContextExtras failed: request process same as " + activity); 9588 return extras; 9589 } 9590 pae = new PendingAssistExtras(activity); 9591 try { 9592 activity.app.thread.requestAssistContextExtras(activity.appToken, pae, 9593 requestType); 9594 mPendingAssistExtras.add(pae); 9595 mHandler.postDelayed(pae, PENDING_ASSIST_EXTRAS_TIMEOUT); 9596 } catch (RemoteException e) { 9597 Slog.w(TAG, "getAssistContextExtras failed: crash calling " + activity); 9598 return extras; 9599 } 9600 } 9601 synchronized (pae) { 9602 while (!pae.haveResult) { 9603 try { 9604 pae.wait(); 9605 } catch (InterruptedException e) { 9606 } 9607 } 9608 if (pae.result != null) { 9609 extras.putBundle(Intent.EXTRA_ASSIST_CONTEXT, pae.result); 9610 } 9611 } 9612 synchronized (this) { 9613 mPendingAssistExtras.remove(pae); 9614 mHandler.removeCallbacks(pae); 9615 } 9616 return extras; 9617 } 9618 9619 public void reportAssistContextExtras(IBinder token, Bundle extras) { 9620 PendingAssistExtras pae = (PendingAssistExtras)token; 9621 synchronized (pae) { 9622 pae.result = extras; 9623 pae.haveResult = true; 9624 pae.notifyAll(); 9625 } 9626 } 9627 9628 public void registerProcessObserver(IProcessObserver observer) { 9629 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 9630 "registerProcessObserver()"); 9631 synchronized (this) { 9632 mProcessObservers.register(observer); 9633 } 9634 } 9635 9636 @Override 9637 public void unregisterProcessObserver(IProcessObserver observer) { 9638 synchronized (this) { 9639 mProcessObservers.unregister(observer); 9640 } 9641 } 9642 9643 @Override 9644 public boolean convertFromTranslucent(IBinder token) { 9645 final long origId = Binder.clearCallingIdentity(); 9646 try { 9647 synchronized (this) { 9648 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9649 if (r == null) { 9650 return false; 9651 } 9652 if (r.changeWindowTranslucency(true)) { 9653 mWindowManager.setAppFullscreen(token, true); 9654 r.task.stack.releaseMediaResources(); 9655 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9656 return true; 9657 } 9658 return false; 9659 } 9660 } finally { 9661 Binder.restoreCallingIdentity(origId); 9662 } 9663 } 9664 9665 @Override 9666 public boolean convertToTranslucent(IBinder token, ActivityOptions options) { 9667 final long origId = Binder.clearCallingIdentity(); 9668 try { 9669 synchronized (this) { 9670 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9671 if (r == null) { 9672 return false; 9673 } 9674 int index = r.task.mActivities.lastIndexOf(r); 9675 if (index > 0) { 9676 ActivityRecord under = r.task.mActivities.get(index - 1); 9677 under.returningOptions = options; 9678 } 9679 if (r.changeWindowTranslucency(false)) { 9680 r.task.stack.convertToTranslucent(r); 9681 mWindowManager.setAppFullscreen(token, false); 9682 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9683 return true; 9684 } else { 9685 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9686 return false; 9687 } 9688 } 9689 } finally { 9690 Binder.restoreCallingIdentity(origId); 9691 } 9692 } 9693 9694 @Override 9695 public boolean setMediaPlaying(IBinder token, boolean playing) { 9696 final long origId = Binder.clearCallingIdentity(); 9697 try { 9698 synchronized (this) { 9699 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9700 if (r != null) { 9701 return mStackSupervisor.setMediaPlayingLocked(r, playing); 9702 } 9703 } 9704 return false; 9705 } finally { 9706 Binder.restoreCallingIdentity(origId); 9707 } 9708 } 9709 9710 @Override 9711 public boolean isBackgroundMediaPlaying(IBinder token) { 9712 final long origId = Binder.clearCallingIdentity(); 9713 try { 9714 synchronized (this) { 9715 final ActivityStack stack = ActivityRecord.getStackLocked(token); 9716 final boolean playing = stack == null ? false : stack.isMediaPlaying(); 9717 if (ActivityStackSupervisor.DEBUG_MEDIA_VISIBILITY) Slog.d(TAG, 9718 "isBackgroundMediaPlaying: stack=" + stack + " playing=" + playing); 9719 return playing; 9720 } 9721 } finally { 9722 Binder.restoreCallingIdentity(origId); 9723 } 9724 } 9725 9726 @Override 9727 public ActivityOptions getActivityOptions(IBinder token) { 9728 final long origId = Binder.clearCallingIdentity(); 9729 try { 9730 synchronized (this) { 9731 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9732 if (r != null) { 9733 final ActivityOptions activityOptions = r.pendingOptions; 9734 r.pendingOptions = null; 9735 return activityOptions; 9736 } 9737 return null; 9738 } 9739 } finally { 9740 Binder.restoreCallingIdentity(origId); 9741 } 9742 } 9743 9744 @Override 9745 public void setImmersive(IBinder token, boolean immersive) { 9746 synchronized(this) { 9747 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9748 if (r == null) { 9749 throw new IllegalArgumentException(); 9750 } 9751 r.immersive = immersive; 9752 9753 // update associated state if we're frontmost 9754 if (r == mFocusedActivity) { 9755 if (DEBUG_IMMERSIVE) { 9756 Slog.d(TAG, "Frontmost changed immersion: "+ r); 9757 } 9758 applyUpdateLockStateLocked(r); 9759 } 9760 } 9761 } 9762 9763 @Override 9764 public boolean isImmersive(IBinder token) { 9765 synchronized (this) { 9766 ActivityRecord r = ActivityRecord.isInStackLocked(token); 9767 if (r == null) { 9768 throw new IllegalArgumentException(); 9769 } 9770 return r.immersive; 9771 } 9772 } 9773 9774 public boolean isTopActivityImmersive() { 9775 enforceNotIsolatedCaller("startActivity"); 9776 synchronized (this) { 9777 ActivityRecord r = getFocusedStack().topRunningActivityLocked(null); 9778 return (r != null) ? r.immersive : false; 9779 } 9780 } 9781 9782 @Override 9783 public boolean isTopOfTask(IBinder token) { 9784 synchronized (this) { 9785 ActivityRecord r = ActivityRecord.isInStackLocked(token); 9786 if (r == null) { 9787 throw new IllegalArgumentException(); 9788 } 9789 return r.task.getTopActivity() == r; 9790 } 9791 } 9792 9793 public final void enterSafeMode() { 9794 synchronized(this) { 9795 // It only makes sense to do this before the system is ready 9796 // and started launching other packages. 9797 if (!mSystemReady) { 9798 try { 9799 AppGlobals.getPackageManager().enterSafeMode(); 9800 } catch (RemoteException e) { 9801 } 9802 } 9803 9804 mSafeMode = true; 9805 } 9806 } 9807 9808 public final void showSafeModeOverlay() { 9809 View v = LayoutInflater.from(mContext).inflate( 9810 com.android.internal.R.layout.safe_mode, null); 9811 WindowManager.LayoutParams lp = new WindowManager.LayoutParams(); 9812 lp.type = WindowManager.LayoutParams.TYPE_SECURE_SYSTEM_OVERLAY; 9813 lp.width = WindowManager.LayoutParams.WRAP_CONTENT; 9814 lp.height = WindowManager.LayoutParams.WRAP_CONTENT; 9815 lp.gravity = Gravity.BOTTOM | Gravity.START; 9816 lp.format = v.getBackground().getOpacity(); 9817 lp.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE 9818 | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE; 9819 lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; 9820 ((WindowManager)mContext.getSystemService( 9821 Context.WINDOW_SERVICE)).addView(v, lp); 9822 } 9823 9824 public void noteWakeupAlarm(IIntentSender sender, int sourceUid, String sourcePkg) { 9825 if (!(sender instanceof PendingIntentRecord)) { 9826 return; 9827 } 9828 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 9829 synchronized (stats) { 9830 if (mBatteryStatsService.isOnBattery()) { 9831 mBatteryStatsService.enforceCallingPermission(); 9832 PendingIntentRecord rec = (PendingIntentRecord)sender; 9833 int MY_UID = Binder.getCallingUid(); 9834 int uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid; 9835 BatteryStatsImpl.Uid.Pkg pkg = 9836 stats.getPackageStatsLocked(sourceUid >= 0 ? sourceUid : uid, 9837 sourcePkg != null ? sourcePkg : rec.key.packageName); 9838 pkg.incWakeupsLocked(); 9839 } 9840 } 9841 } 9842 9843 public boolean killPids(int[] pids, String pReason, boolean secure) { 9844 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9845 throw new SecurityException("killPids only available to the system"); 9846 } 9847 String reason = (pReason == null) ? "Unknown" : pReason; 9848 // XXX Note: don't acquire main activity lock here, because the window 9849 // manager calls in with its locks held. 9850 9851 boolean killed = false; 9852 synchronized (mPidsSelfLocked) { 9853 int[] types = new int[pids.length]; 9854 int worstType = 0; 9855 for (int i=0; i<pids.length; i++) { 9856 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 9857 if (proc != null) { 9858 int type = proc.setAdj; 9859 types[i] = type; 9860 if (type > worstType) { 9861 worstType = type; 9862 } 9863 } 9864 } 9865 9866 // If the worst oom_adj is somewhere in the cached proc LRU range, 9867 // then constrain it so we will kill all cached procs. 9868 if (worstType < ProcessList.CACHED_APP_MAX_ADJ 9869 && worstType > ProcessList.CACHED_APP_MIN_ADJ) { 9870 worstType = ProcessList.CACHED_APP_MIN_ADJ; 9871 } 9872 9873 // If this is not a secure call, don't let it kill processes that 9874 // are important. 9875 if (!secure && worstType < ProcessList.SERVICE_ADJ) { 9876 worstType = ProcessList.SERVICE_ADJ; 9877 } 9878 9879 Slog.w(TAG, "Killing processes " + reason + " at adjustment " + worstType); 9880 for (int i=0; i<pids.length; i++) { 9881 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 9882 if (proc == null) { 9883 continue; 9884 } 9885 int adj = proc.setAdj; 9886 if (adj >= worstType && !proc.killedByAm) { 9887 killUnneededProcessLocked(proc, reason); 9888 killed = true; 9889 } 9890 } 9891 } 9892 return killed; 9893 } 9894 9895 @Override 9896 public void killUid(int uid, String reason) { 9897 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9898 throw new SecurityException("killUid only available to the system"); 9899 } 9900 synchronized (this) { 9901 killPackageProcessesLocked(null, UserHandle.getAppId(uid), UserHandle.getUserId(uid), 9902 ProcessList.FOREGROUND_APP_ADJ-1, false, true, true, false, 9903 reason != null ? reason : "kill uid"); 9904 } 9905 } 9906 9907 @Override 9908 public boolean killProcessesBelowForeground(String reason) { 9909 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9910 throw new SecurityException("killProcessesBelowForeground() only available to system"); 9911 } 9912 9913 return killProcessesBelowAdj(ProcessList.FOREGROUND_APP_ADJ, reason); 9914 } 9915 9916 private boolean killProcessesBelowAdj(int belowAdj, String reason) { 9917 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9918 throw new SecurityException("killProcessesBelowAdj() only available to system"); 9919 } 9920 9921 boolean killed = false; 9922 synchronized (mPidsSelfLocked) { 9923 final int size = mPidsSelfLocked.size(); 9924 for (int i = 0; i < size; i++) { 9925 final int pid = mPidsSelfLocked.keyAt(i); 9926 final ProcessRecord proc = mPidsSelfLocked.valueAt(i); 9927 if (proc == null) continue; 9928 9929 final int adj = proc.setAdj; 9930 if (adj > belowAdj && !proc.killedByAm) { 9931 killUnneededProcessLocked(proc, reason); 9932 killed = true; 9933 } 9934 } 9935 } 9936 return killed; 9937 } 9938 9939 @Override 9940 public void hang(final IBinder who, boolean allowRestart) { 9941 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9942 != PackageManager.PERMISSION_GRANTED) { 9943 throw new SecurityException("Requires permission " 9944 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9945 } 9946 9947 final IBinder.DeathRecipient death = new DeathRecipient() { 9948 @Override 9949 public void binderDied() { 9950 synchronized (this) { 9951 notifyAll(); 9952 } 9953 } 9954 }; 9955 9956 try { 9957 who.linkToDeath(death, 0); 9958 } catch (RemoteException e) { 9959 Slog.w(TAG, "hang: given caller IBinder is already dead."); 9960 return; 9961 } 9962 9963 synchronized (this) { 9964 Watchdog.getInstance().setAllowRestart(allowRestart); 9965 Slog.i(TAG, "Hanging system process at request of pid " + Binder.getCallingPid()); 9966 synchronized (death) { 9967 while (who.isBinderAlive()) { 9968 try { 9969 death.wait(); 9970 } catch (InterruptedException e) { 9971 } 9972 } 9973 } 9974 Watchdog.getInstance().setAllowRestart(true); 9975 } 9976 } 9977 9978 @Override 9979 public void restart() { 9980 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9981 != PackageManager.PERMISSION_GRANTED) { 9982 throw new SecurityException("Requires permission " 9983 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9984 } 9985 9986 Log.i(TAG, "Sending shutdown broadcast..."); 9987 9988 BroadcastReceiver br = new BroadcastReceiver() { 9989 @Override public void onReceive(Context context, Intent intent) { 9990 // Now the broadcast is done, finish up the low-level shutdown. 9991 Log.i(TAG, "Shutting down activity manager..."); 9992 shutdown(10000); 9993 Log.i(TAG, "Shutdown complete, restarting!"); 9994 Process.killProcess(Process.myPid()); 9995 System.exit(10); 9996 } 9997 }; 9998 9999 // First send the high-level shut down broadcast. 10000 Intent intent = new Intent(Intent.ACTION_SHUTDOWN); 10001 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 10002 intent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 10003 /* For now we are not doing a clean shutdown, because things seem to get unhappy. 10004 mContext.sendOrderedBroadcastAsUser(intent, 10005 UserHandle.ALL, null, br, mHandler, 0, null, null); 10006 */ 10007 br.onReceive(mContext, intent); 10008 } 10009 10010 private long getLowRamTimeSinceIdle(long now) { 10011 return mLowRamTimeSinceLastIdle + (mLowRamStartTime > 0 ? (now-mLowRamStartTime) : 0); 10012 } 10013 10014 @Override 10015 public void performIdleMaintenance() { 10016 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 10017 != PackageManager.PERMISSION_GRANTED) { 10018 throw new SecurityException("Requires permission " 10019 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 10020 } 10021 10022 synchronized (this) { 10023 final long now = SystemClock.uptimeMillis(); 10024 final long timeSinceLastIdle = now - mLastIdleTime; 10025 final long lowRamSinceLastIdle = getLowRamTimeSinceIdle(now); 10026 mLastIdleTime = now; 10027 mLowRamTimeSinceLastIdle = 0; 10028 if (mLowRamStartTime != 0) { 10029 mLowRamStartTime = now; 10030 } 10031 10032 StringBuilder sb = new StringBuilder(128); 10033 sb.append("Idle maintenance over "); 10034 TimeUtils.formatDuration(timeSinceLastIdle, sb); 10035 sb.append(" low RAM for "); 10036 TimeUtils.formatDuration(lowRamSinceLastIdle, sb); 10037 Slog.i(TAG, sb.toString()); 10038 10039 // If at least 1/3 of our time since the last idle period has been spent 10040 // with RAM low, then we want to kill processes. 10041 boolean doKilling = lowRamSinceLastIdle > (timeSinceLastIdle/3); 10042 10043 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 10044 ProcessRecord proc = mLruProcesses.get(i); 10045 if (proc.notCachedSinceIdle) { 10046 if (proc.setProcState > ActivityManager.PROCESS_STATE_TOP 10047 && proc.setProcState <= ActivityManager.PROCESS_STATE_SERVICE) { 10048 if (doKilling && proc.initialIdlePss != 0 10049 && proc.lastPss > ((proc.initialIdlePss*3)/2)) { 10050 killUnneededProcessLocked(proc, "idle maint (pss " + proc.lastPss 10051 + " from " + proc.initialIdlePss + ")"); 10052 } 10053 } 10054 } else if (proc.setProcState < ActivityManager.PROCESS_STATE_HOME) { 10055 proc.notCachedSinceIdle = true; 10056 proc.initialIdlePss = 0; 10057 proc.nextPssTime = ProcessList.computeNextPssTime(proc.curProcState, true, 10058 isSleeping(), now); 10059 } 10060 } 10061 10062 mHandler.removeMessages(REQUEST_ALL_PSS_MSG); 10063 mHandler.sendEmptyMessageDelayed(REQUEST_ALL_PSS_MSG, 2*60*1000); 10064 } 10065 } 10066 10067 private void retrieveSettings() { 10068 final ContentResolver resolver = mContext.getContentResolver(); 10069 String debugApp = Settings.Global.getString( 10070 resolver, Settings.Global.DEBUG_APP); 10071 boolean waitForDebugger = Settings.Global.getInt( 10072 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 0) != 0; 10073 boolean alwaysFinishActivities = Settings.Global.getInt( 10074 resolver, Settings.Global.ALWAYS_FINISH_ACTIVITIES, 0) != 0; 10075 boolean forceRtl = Settings.Global.getInt( 10076 resolver, Settings.Global.DEVELOPMENT_FORCE_RTL, 0) != 0; 10077 // Transfer any global setting for forcing RTL layout, into a System Property 10078 SystemProperties.set(Settings.Global.DEVELOPMENT_FORCE_RTL, forceRtl ? "1":"0"); 10079 10080 Configuration configuration = new Configuration(); 10081 Settings.System.getConfiguration(resolver, configuration); 10082 if (forceRtl) { 10083 // This will take care of setting the correct layout direction flags 10084 configuration.setLayoutDirection(configuration.locale); 10085 } 10086 10087 synchronized (this) { 10088 mDebugApp = mOrigDebugApp = debugApp; 10089 mWaitForDebugger = mOrigWaitForDebugger = waitForDebugger; 10090 mAlwaysFinishActivities = alwaysFinishActivities; 10091 // This happens before any activities are started, so we can 10092 // change mConfiguration in-place. 10093 updateConfigurationLocked(configuration, null, false, true); 10094 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Initial config: " + mConfiguration); 10095 } 10096 } 10097 10098 public boolean testIsSystemReady() { 10099 // no need to synchronize(this) just to read & return the value 10100 return mSystemReady; 10101 } 10102 10103 private static File getCalledPreBootReceiversFile() { 10104 File dataDir = Environment.getDataDirectory(); 10105 File systemDir = new File(dataDir, "system"); 10106 File fname = new File(systemDir, CALLED_PRE_BOOTS_FILENAME); 10107 return fname; 10108 } 10109 10110 private static ArrayList<ComponentName> readLastDonePreBootReceivers() { 10111 ArrayList<ComponentName> lastDoneReceivers = new ArrayList<ComponentName>(); 10112 File file = getCalledPreBootReceiversFile(); 10113 FileInputStream fis = null; 10114 try { 10115 fis = new FileInputStream(file); 10116 DataInputStream dis = new DataInputStream(new BufferedInputStream(fis, 2048)); 10117 int fvers = dis.readInt(); 10118 if (fvers == LAST_PREBOOT_DELIVERED_FILE_VERSION) { 10119 String vers = dis.readUTF(); 10120 String codename = dis.readUTF(); 10121 String build = dis.readUTF(); 10122 if (android.os.Build.VERSION.RELEASE.equals(vers) 10123 && android.os.Build.VERSION.CODENAME.equals(codename) 10124 && android.os.Build.VERSION.INCREMENTAL.equals(build)) { 10125 int num = dis.readInt(); 10126 while (num > 0) { 10127 num--; 10128 String pkg = dis.readUTF(); 10129 String cls = dis.readUTF(); 10130 lastDoneReceivers.add(new ComponentName(pkg, cls)); 10131 } 10132 } 10133 } 10134 } catch (FileNotFoundException e) { 10135 } catch (IOException e) { 10136 Slog.w(TAG, "Failure reading last done pre-boot receivers", e); 10137 } finally { 10138 if (fis != null) { 10139 try { 10140 fis.close(); 10141 } catch (IOException e) { 10142 } 10143 } 10144 } 10145 return lastDoneReceivers; 10146 } 10147 10148 private static void writeLastDonePreBootReceivers(ArrayList<ComponentName> list) { 10149 File file = getCalledPreBootReceiversFile(); 10150 FileOutputStream fos = null; 10151 DataOutputStream dos = null; 10152 try { 10153 fos = new FileOutputStream(file); 10154 dos = new DataOutputStream(new BufferedOutputStream(fos, 2048)); 10155 dos.writeInt(LAST_PREBOOT_DELIVERED_FILE_VERSION); 10156 dos.writeUTF(android.os.Build.VERSION.RELEASE); 10157 dos.writeUTF(android.os.Build.VERSION.CODENAME); 10158 dos.writeUTF(android.os.Build.VERSION.INCREMENTAL); 10159 dos.writeInt(list.size()); 10160 for (int i=0; i<list.size(); i++) { 10161 dos.writeUTF(list.get(i).getPackageName()); 10162 dos.writeUTF(list.get(i).getClassName()); 10163 } 10164 } catch (IOException e) { 10165 Slog.w(TAG, "Failure writing last done pre-boot receivers", e); 10166 file.delete(); 10167 } finally { 10168 FileUtils.sync(fos); 10169 if (dos != null) { 10170 try { 10171 dos.close(); 10172 } catch (IOException e) { 10173 // TODO Auto-generated catch block 10174 e.printStackTrace(); 10175 } 10176 } 10177 } 10178 } 10179 10180 private boolean deliverPreBootCompleted(final Runnable onFinishCallback, 10181 ArrayList<ComponentName> doneReceivers, int userId) { 10182 boolean waitingUpdate = false; 10183 Intent intent = new Intent(Intent.ACTION_PRE_BOOT_COMPLETED); 10184 List<ResolveInfo> ris = null; 10185 try { 10186 ris = AppGlobals.getPackageManager().queryIntentReceivers( 10187 intent, null, 0, userId); 10188 } catch (RemoteException e) { 10189 } 10190 if (ris != null) { 10191 for (int i=ris.size()-1; i>=0; i--) { 10192 if ((ris.get(i).activityInfo.applicationInfo.flags 10193 &ApplicationInfo.FLAG_SYSTEM) == 0) { 10194 ris.remove(i); 10195 } 10196 } 10197 intent.addFlags(Intent.FLAG_RECEIVER_BOOT_UPGRADE); 10198 10199 // For User 0, load the version number. When delivering to a new user, deliver 10200 // to all receivers. 10201 if (userId == UserHandle.USER_OWNER) { 10202 ArrayList<ComponentName> lastDoneReceivers = readLastDonePreBootReceivers(); 10203 for (int i=0; i<ris.size(); i++) { 10204 ActivityInfo ai = ris.get(i).activityInfo; 10205 ComponentName comp = new ComponentName(ai.packageName, ai.name); 10206 if (lastDoneReceivers.contains(comp)) { 10207 // We already did the pre boot receiver for this app with the current 10208 // platform version, so don't do it again... 10209 ris.remove(i); 10210 i--; 10211 // ...however, do keep it as one that has been done, so we don't 10212 // forget about it when rewriting the file of last done receivers. 10213 doneReceivers.add(comp); 10214 } 10215 } 10216 } 10217 10218 // If primary user, send broadcast to all available users, else just to userId 10219 final int[] users = userId == UserHandle.USER_OWNER ? getUsersLocked() 10220 : new int[] { userId }; 10221 for (int i = 0; i < ris.size(); i++) { 10222 ActivityInfo ai = ris.get(i).activityInfo; 10223 ComponentName comp = new ComponentName(ai.packageName, ai.name); 10224 doneReceivers.add(comp); 10225 intent.setComponent(comp); 10226 for (int j=0; j<users.length; j++) { 10227 IIntentReceiver finisher = null; 10228 // On last receiver and user, set up a completion callback 10229 if (i == ris.size() - 1 && j == users.length - 1 && onFinishCallback != null) { 10230 finisher = new IIntentReceiver.Stub() { 10231 public void performReceive(Intent intent, int resultCode, 10232 String data, Bundle extras, boolean ordered, 10233 boolean sticky, int sendingUser) { 10234 // The raw IIntentReceiver interface is called 10235 // with the AM lock held, so redispatch to 10236 // execute our code without the lock. 10237 mHandler.post(onFinishCallback); 10238 } 10239 }; 10240 } 10241 Slog.i(TAG, "Sending system update to " + intent.getComponent() 10242 + " for user " + users[j]); 10243 broadcastIntentLocked(null, null, intent, null, finisher, 10244 0, null, null, null, AppOpsManager.OP_NONE, 10245 true, false, MY_PID, Process.SYSTEM_UID, 10246 users[j]); 10247 if (finisher != null) { 10248 waitingUpdate = true; 10249 } 10250 } 10251 } 10252 } 10253 10254 return waitingUpdate; 10255 } 10256 10257 public void systemReady(final Runnable goingCallback) { 10258 synchronized(this) { 10259 if (mSystemReady) { 10260 // If we're done calling all the receivers, run the next "boot phase" passed in 10261 // by the SystemServer 10262 if (goingCallback != null) { 10263 goingCallback.run(); 10264 } 10265 return; 10266 } 10267 10268 // Make sure we have the current profile info, since it is needed for 10269 // security checks. 10270 updateCurrentProfileIdsLocked(); 10271 10272 if (mRecentTasks == null) { 10273 mRecentTasks = mTaskPersister.restoreTasksLocked(); 10274 if (!mRecentTasks.isEmpty()) { 10275 mStackSupervisor.createStackForRestoredTaskHistory(mRecentTasks); 10276 } 10277 mTaskPersister.startPersisting(); 10278 } 10279 10280 // Check to see if there are any update receivers to run. 10281 if (!mDidUpdate) { 10282 if (mWaitingUpdate) { 10283 return; 10284 } 10285 final ArrayList<ComponentName> doneReceivers = new ArrayList<ComponentName>(); 10286 mWaitingUpdate = deliverPreBootCompleted(new Runnable() { 10287 public void run() { 10288 synchronized (ActivityManagerService.this) { 10289 mDidUpdate = true; 10290 } 10291 writeLastDonePreBootReceivers(doneReceivers); 10292 showBootMessage(mContext.getText( 10293 R.string.android_upgrading_complete), 10294 false); 10295 systemReady(goingCallback); 10296 } 10297 }, doneReceivers, UserHandle.USER_OWNER); 10298 10299 if (mWaitingUpdate) { 10300 return; 10301 } 10302 mDidUpdate = true; 10303 } 10304 10305 mAppOpsService.systemReady(); 10306 mSystemReady = true; 10307 } 10308 10309 ArrayList<ProcessRecord> procsToKill = null; 10310 synchronized(mPidsSelfLocked) { 10311 for (int i=mPidsSelfLocked.size()-1; i>=0; i--) { 10312 ProcessRecord proc = mPidsSelfLocked.valueAt(i); 10313 if (!isAllowedWhileBooting(proc.info)){ 10314 if (procsToKill == null) { 10315 procsToKill = new ArrayList<ProcessRecord>(); 10316 } 10317 procsToKill.add(proc); 10318 } 10319 } 10320 } 10321 10322 synchronized(this) { 10323 if (procsToKill != null) { 10324 for (int i=procsToKill.size()-1; i>=0; i--) { 10325 ProcessRecord proc = procsToKill.get(i); 10326 Slog.i(TAG, "Removing system update proc: " + proc); 10327 removeProcessLocked(proc, true, false, "system update done"); 10328 } 10329 } 10330 10331 // Now that we have cleaned up any update processes, we 10332 // are ready to start launching real processes and know that 10333 // we won't trample on them any more. 10334 mProcessesReady = true; 10335 } 10336 10337 Slog.i(TAG, "System now ready"); 10338 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_AMS_READY, 10339 SystemClock.uptimeMillis()); 10340 10341 synchronized(this) { 10342 // Make sure we have no pre-ready processes sitting around. 10343 10344 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) { 10345 ResolveInfo ri = mContext.getPackageManager() 10346 .resolveActivity(new Intent(Intent.ACTION_FACTORY_TEST), 10347 STOCK_PM_FLAGS); 10348 CharSequence errorMsg = null; 10349 if (ri != null) { 10350 ActivityInfo ai = ri.activityInfo; 10351 ApplicationInfo app = ai.applicationInfo; 10352 if ((app.flags&ApplicationInfo.FLAG_SYSTEM) != 0) { 10353 mTopAction = Intent.ACTION_FACTORY_TEST; 10354 mTopData = null; 10355 mTopComponent = new ComponentName(app.packageName, 10356 ai.name); 10357 } else { 10358 errorMsg = mContext.getResources().getText( 10359 com.android.internal.R.string.factorytest_not_system); 10360 } 10361 } else { 10362 errorMsg = mContext.getResources().getText( 10363 com.android.internal.R.string.factorytest_no_action); 10364 } 10365 if (errorMsg != null) { 10366 mTopAction = null; 10367 mTopData = null; 10368 mTopComponent = null; 10369 Message msg = Message.obtain(); 10370 msg.what = SHOW_FACTORY_ERROR_MSG; 10371 msg.getData().putCharSequence("msg", errorMsg); 10372 mHandler.sendMessage(msg); 10373 } 10374 } 10375 } 10376 10377 retrieveSettings(); 10378 10379 synchronized (this) { 10380 readGrantedUriPermissionsLocked(); 10381 } 10382 10383 if (goingCallback != null) goingCallback.run(); 10384 10385 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_RUNNING_START, 10386 Integer.toString(mCurrentUserId), mCurrentUserId); 10387 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_USER_FOREGROUND_START, 10388 Integer.toString(mCurrentUserId), mCurrentUserId); 10389 mSystemServiceManager.startUser(mCurrentUserId); 10390 10391 synchronized (this) { 10392 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 10393 try { 10394 List apps = AppGlobals.getPackageManager(). 10395 getPersistentApplications(STOCK_PM_FLAGS); 10396 if (apps != null) { 10397 int N = apps.size(); 10398 int i; 10399 for (i=0; i<N; i++) { 10400 ApplicationInfo info 10401 = (ApplicationInfo)apps.get(i); 10402 if (info != null && 10403 !info.packageName.equals("android")) { 10404 addAppLocked(info, false, null /* ABI override */); 10405 } 10406 } 10407 } 10408 } catch (RemoteException ex) { 10409 // pm is in same process, this will never happen. 10410 } 10411 } 10412 10413 // Start up initial activity. 10414 mBooting = true; 10415 10416 try { 10417 if (AppGlobals.getPackageManager().hasSystemUidErrors()) { 10418 Message msg = Message.obtain(); 10419 msg.what = SHOW_UID_ERROR_MSG; 10420 mHandler.sendMessage(msg); 10421 } 10422 } catch (RemoteException e) { 10423 } 10424 10425 long ident = Binder.clearCallingIdentity(); 10426 try { 10427 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 10428 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 10429 | Intent.FLAG_RECEIVER_FOREGROUND); 10430 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 10431 broadcastIntentLocked(null, null, intent, 10432 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 10433 false, false, MY_PID, Process.SYSTEM_UID, mCurrentUserId); 10434 intent = new Intent(Intent.ACTION_USER_STARTING); 10435 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 10436 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 10437 broadcastIntentLocked(null, null, intent, 10438 null, new IIntentReceiver.Stub() { 10439 @Override 10440 public void performReceive(Intent intent, int resultCode, String data, 10441 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 10442 throws RemoteException { 10443 } 10444 }, 0, null, null, 10445 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 10446 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 10447 } catch (Throwable t) { 10448 Slog.wtf(TAG, "Failed sending first user broadcasts", t); 10449 } finally { 10450 Binder.restoreCallingIdentity(ident); 10451 } 10452 mStackSupervisor.resumeTopActivitiesLocked(); 10453 sendUserSwitchBroadcastsLocked(-1, mCurrentUserId); 10454 } 10455 } 10456 10457 private boolean makeAppCrashingLocked(ProcessRecord app, 10458 String shortMsg, String longMsg, String stackTrace) { 10459 app.crashing = true; 10460 app.crashingReport = generateProcessError(app, 10461 ActivityManager.ProcessErrorStateInfo.CRASHED, null, shortMsg, longMsg, stackTrace); 10462 startAppProblemLocked(app); 10463 app.stopFreezingAllLocked(); 10464 return handleAppCrashLocked(app, shortMsg, longMsg, stackTrace); 10465 } 10466 10467 private void makeAppNotRespondingLocked(ProcessRecord app, 10468 String activity, String shortMsg, String longMsg) { 10469 app.notResponding = true; 10470 app.notRespondingReport = generateProcessError(app, 10471 ActivityManager.ProcessErrorStateInfo.NOT_RESPONDING, 10472 activity, shortMsg, longMsg, null); 10473 startAppProblemLocked(app); 10474 app.stopFreezingAllLocked(); 10475 } 10476 10477 /** 10478 * Generate a process error record, suitable for attachment to a ProcessRecord. 10479 * 10480 * @param app The ProcessRecord in which the error occurred. 10481 * @param condition Crashing, Application Not Responding, etc. Values are defined in 10482 * ActivityManager.AppErrorStateInfo 10483 * @param activity The activity associated with the crash, if known. 10484 * @param shortMsg Short message describing the crash. 10485 * @param longMsg Long message describing the crash. 10486 * @param stackTrace Full crash stack trace, may be null. 10487 * 10488 * @return Returns a fully-formed AppErrorStateInfo record. 10489 */ 10490 private ActivityManager.ProcessErrorStateInfo generateProcessError(ProcessRecord app, 10491 int condition, String activity, String shortMsg, String longMsg, String stackTrace) { 10492 ActivityManager.ProcessErrorStateInfo report = new ActivityManager.ProcessErrorStateInfo(); 10493 10494 report.condition = condition; 10495 report.processName = app.processName; 10496 report.pid = app.pid; 10497 report.uid = app.info.uid; 10498 report.tag = activity; 10499 report.shortMsg = shortMsg; 10500 report.longMsg = longMsg; 10501 report.stackTrace = stackTrace; 10502 10503 return report; 10504 } 10505 10506 void killAppAtUsersRequest(ProcessRecord app, Dialog fromDialog) { 10507 synchronized (this) { 10508 app.crashing = false; 10509 app.crashingReport = null; 10510 app.notResponding = false; 10511 app.notRespondingReport = null; 10512 if (app.anrDialog == fromDialog) { 10513 app.anrDialog = null; 10514 } 10515 if (app.waitDialog == fromDialog) { 10516 app.waitDialog = null; 10517 } 10518 if (app.pid > 0 && app.pid != MY_PID) { 10519 handleAppCrashLocked(app, null, null, null); 10520 killUnneededProcessLocked(app, "user request after error"); 10521 } 10522 } 10523 } 10524 10525 private boolean handleAppCrashLocked(ProcessRecord app, String shortMsg, String longMsg, 10526 String stackTrace) { 10527 long now = SystemClock.uptimeMillis(); 10528 10529 Long crashTime; 10530 if (!app.isolated) { 10531 crashTime = mProcessCrashTimes.get(app.info.processName, app.uid); 10532 } else { 10533 crashTime = null; 10534 } 10535 if (crashTime != null && now < crashTime+ProcessList.MIN_CRASH_INTERVAL) { 10536 // This process loses! 10537 Slog.w(TAG, "Process " + app.info.processName 10538 + " has crashed too many times: killing!"); 10539 EventLog.writeEvent(EventLogTags.AM_PROCESS_CRASHED_TOO_MUCH, 10540 app.userId, app.info.processName, app.uid); 10541 mStackSupervisor.handleAppCrashLocked(app); 10542 if (!app.persistent) { 10543 // We don't want to start this process again until the user 10544 // explicitly does so... but for persistent process, we really 10545 // need to keep it running. If a persistent process is actually 10546 // repeatedly crashing, then badness for everyone. 10547 EventLog.writeEvent(EventLogTags.AM_PROC_BAD, app.userId, app.uid, 10548 app.info.processName); 10549 if (!app.isolated) { 10550 // XXX We don't have a way to mark isolated processes 10551 // as bad, since they don't have a peristent identity. 10552 mBadProcesses.put(app.info.processName, app.uid, 10553 new BadProcessInfo(now, shortMsg, longMsg, stackTrace)); 10554 mProcessCrashTimes.remove(app.info.processName, app.uid); 10555 } 10556 app.bad = true; 10557 app.removed = true; 10558 // Don't let services in this process be restarted and potentially 10559 // annoy the user repeatedly. Unless it is persistent, since those 10560 // processes run critical code. 10561 removeProcessLocked(app, false, false, "crash"); 10562 mStackSupervisor.resumeTopActivitiesLocked(); 10563 return false; 10564 } 10565 mStackSupervisor.resumeTopActivitiesLocked(); 10566 } else { 10567 mStackSupervisor.finishTopRunningActivityLocked(app); 10568 } 10569 10570 // Bump up the crash count of any services currently running in the proc. 10571 for (int i=app.services.size()-1; i>=0; i--) { 10572 // Any services running in the application need to be placed 10573 // back in the pending list. 10574 ServiceRecord sr = app.services.valueAt(i); 10575 sr.crashCount++; 10576 } 10577 10578 // If the crashing process is what we consider to be the "home process" and it has been 10579 // replaced by a third-party app, clear the package preferred activities from packages 10580 // with a home activity running in the process to prevent a repeatedly crashing app 10581 // from blocking the user to manually clear the list. 10582 final ArrayList<ActivityRecord> activities = app.activities; 10583 if (app == mHomeProcess && activities.size() > 0 10584 && (mHomeProcess.info.flags & ApplicationInfo.FLAG_SYSTEM) == 0) { 10585 for (int activityNdx = activities.size() - 1; activityNdx >= 0; --activityNdx) { 10586 final ActivityRecord r = activities.get(activityNdx); 10587 if (r.isHomeActivity()) { 10588 Log.i(TAG, "Clearing package preferred activities from " + r.packageName); 10589 try { 10590 ActivityThread.getPackageManager() 10591 .clearPackagePreferredActivities(r.packageName); 10592 } catch (RemoteException c) { 10593 // pm is in same process, this will never happen. 10594 } 10595 } 10596 } 10597 } 10598 10599 if (!app.isolated) { 10600 // XXX Can't keep track of crash times for isolated processes, 10601 // because they don't have a perisistent identity. 10602 mProcessCrashTimes.put(app.info.processName, app.uid, now); 10603 } 10604 10605 if (app.crashHandler != null) mHandler.post(app.crashHandler); 10606 return true; 10607 } 10608 10609 void startAppProblemLocked(ProcessRecord app) { 10610 // If this app is not running under the current user, then we 10611 // can't give it a report button because that would require 10612 // launching the report UI under a different user. 10613 app.errorReportReceiver = null; 10614 10615 for (int userId : mCurrentProfileIds) { 10616 if (app.userId == userId) { 10617 app.errorReportReceiver = ApplicationErrorReport.getErrorReportReceiver( 10618 mContext, app.info.packageName, app.info.flags); 10619 } 10620 } 10621 skipCurrentReceiverLocked(app); 10622 } 10623 10624 void skipCurrentReceiverLocked(ProcessRecord app) { 10625 for (BroadcastQueue queue : mBroadcastQueues) { 10626 queue.skipCurrentReceiverLocked(app); 10627 } 10628 } 10629 10630 /** 10631 * Used by {@link com.android.internal.os.RuntimeInit} to report when an application crashes. 10632 * The application process will exit immediately after this call returns. 10633 * @param app object of the crashing app, null for the system server 10634 * @param crashInfo describing the exception 10635 */ 10636 public void handleApplicationCrash(IBinder app, ApplicationErrorReport.CrashInfo crashInfo) { 10637 ProcessRecord r = findAppProcess(app, "Crash"); 10638 final String processName = app == null ? "system_server" 10639 : (r == null ? "unknown" : r.processName); 10640 10641 handleApplicationCrashInner("crash", r, processName, crashInfo); 10642 } 10643 10644 /* Native crash reporting uses this inner version because it needs to be somewhat 10645 * decoupled from the AM-managed cleanup lifecycle 10646 */ 10647 void handleApplicationCrashInner(String eventType, ProcessRecord r, String processName, 10648 ApplicationErrorReport.CrashInfo crashInfo) { 10649 EventLog.writeEvent(EventLogTags.AM_CRASH, Binder.getCallingPid(), 10650 UserHandle.getUserId(Binder.getCallingUid()), processName, 10651 r == null ? -1 : r.info.flags, 10652 crashInfo.exceptionClassName, 10653 crashInfo.exceptionMessage, 10654 crashInfo.throwFileName, 10655 crashInfo.throwLineNumber); 10656 10657 addErrorToDropBox(eventType, r, processName, null, null, null, null, null, crashInfo); 10658 10659 crashApplication(r, crashInfo); 10660 } 10661 10662 public void handleApplicationStrictModeViolation( 10663 IBinder app, 10664 int violationMask, 10665 StrictMode.ViolationInfo info) { 10666 ProcessRecord r = findAppProcess(app, "StrictMode"); 10667 if (r == null) { 10668 return; 10669 } 10670 10671 if ((violationMask & StrictMode.PENALTY_DROPBOX) != 0) { 10672 Integer stackFingerprint = info.hashCode(); 10673 boolean logIt = true; 10674 synchronized (mAlreadyLoggedViolatedStacks) { 10675 if (mAlreadyLoggedViolatedStacks.contains(stackFingerprint)) { 10676 logIt = false; 10677 // TODO: sub-sample into EventLog for these, with 10678 // the info.durationMillis? Then we'd get 10679 // the relative pain numbers, without logging all 10680 // the stack traces repeatedly. We'd want to do 10681 // likewise in the client code, which also does 10682 // dup suppression, before the Binder call. 10683 } else { 10684 if (mAlreadyLoggedViolatedStacks.size() >= MAX_DUP_SUPPRESSED_STACKS) { 10685 mAlreadyLoggedViolatedStacks.clear(); 10686 } 10687 mAlreadyLoggedViolatedStacks.add(stackFingerprint); 10688 } 10689 } 10690 if (logIt) { 10691 logStrictModeViolationToDropBox(r, info); 10692 } 10693 } 10694 10695 if ((violationMask & StrictMode.PENALTY_DIALOG) != 0) { 10696 AppErrorResult result = new AppErrorResult(); 10697 synchronized (this) { 10698 final long origId = Binder.clearCallingIdentity(); 10699 10700 Message msg = Message.obtain(); 10701 msg.what = SHOW_STRICT_MODE_VIOLATION_MSG; 10702 HashMap<String, Object> data = new HashMap<String, Object>(); 10703 data.put("result", result); 10704 data.put("app", r); 10705 data.put("violationMask", violationMask); 10706 data.put("info", info); 10707 msg.obj = data; 10708 mHandler.sendMessage(msg); 10709 10710 Binder.restoreCallingIdentity(origId); 10711 } 10712 int res = result.get(); 10713 Slog.w(TAG, "handleApplicationStrictModeViolation; res=" + res); 10714 } 10715 } 10716 10717 // Depending on the policy in effect, there could be a bunch of 10718 // these in quick succession so we try to batch these together to 10719 // minimize disk writes, number of dropbox entries, and maximize 10720 // compression, by having more fewer, larger records. 10721 private void logStrictModeViolationToDropBox( 10722 ProcessRecord process, 10723 StrictMode.ViolationInfo info) { 10724 if (info == null) { 10725 return; 10726 } 10727 final boolean isSystemApp = process == null || 10728 (process.info.flags & (ApplicationInfo.FLAG_SYSTEM | 10729 ApplicationInfo.FLAG_UPDATED_SYSTEM_APP)) != 0; 10730 final String processName = process == null ? "unknown" : process.processName; 10731 final String dropboxTag = isSystemApp ? "system_app_strictmode" : "data_app_strictmode"; 10732 final DropBoxManager dbox = (DropBoxManager) 10733 mContext.getSystemService(Context.DROPBOX_SERVICE); 10734 10735 // Exit early if the dropbox isn't configured to accept this report type. 10736 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 10737 10738 boolean bufferWasEmpty; 10739 boolean needsFlush; 10740 final StringBuilder sb = isSystemApp ? mStrictModeBuffer : new StringBuilder(1024); 10741 synchronized (sb) { 10742 bufferWasEmpty = sb.length() == 0; 10743 appendDropBoxProcessHeaders(process, processName, sb); 10744 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 10745 sb.append("System-App: ").append(isSystemApp).append("\n"); 10746 sb.append("Uptime-Millis: ").append(info.violationUptimeMillis).append("\n"); 10747 if (info.violationNumThisLoop != 0) { 10748 sb.append("Loop-Violation-Number: ").append(info.violationNumThisLoop).append("\n"); 10749 } 10750 if (info.numAnimationsRunning != 0) { 10751 sb.append("Animations-Running: ").append(info.numAnimationsRunning).append("\n"); 10752 } 10753 if (info.broadcastIntentAction != null) { 10754 sb.append("Broadcast-Intent-Action: ").append(info.broadcastIntentAction).append("\n"); 10755 } 10756 if (info.durationMillis != -1) { 10757 sb.append("Duration-Millis: ").append(info.durationMillis).append("\n"); 10758 } 10759 if (info.numInstances != -1) { 10760 sb.append("Instance-Count: ").append(info.numInstances).append("\n"); 10761 } 10762 if (info.tags != null) { 10763 for (String tag : info.tags) { 10764 sb.append("Span-Tag: ").append(tag).append("\n"); 10765 } 10766 } 10767 sb.append("\n"); 10768 if (info.crashInfo != null && info.crashInfo.stackTrace != null) { 10769 sb.append(info.crashInfo.stackTrace); 10770 } 10771 sb.append("\n"); 10772 10773 // Only buffer up to ~64k. Various logging bits truncate 10774 // things at 128k. 10775 needsFlush = (sb.length() > 64 * 1024); 10776 } 10777 10778 // Flush immediately if the buffer's grown too large, or this 10779 // is a non-system app. Non-system apps are isolated with a 10780 // different tag & policy and not batched. 10781 // 10782 // Batching is useful during internal testing with 10783 // StrictMode settings turned up high. Without batching, 10784 // thousands of separate files could be created on boot. 10785 if (!isSystemApp || needsFlush) { 10786 new Thread("Error dump: " + dropboxTag) { 10787 @Override 10788 public void run() { 10789 String report; 10790 synchronized (sb) { 10791 report = sb.toString(); 10792 sb.delete(0, sb.length()); 10793 sb.trimToSize(); 10794 } 10795 if (report.length() != 0) { 10796 dbox.addText(dropboxTag, report); 10797 } 10798 } 10799 }.start(); 10800 return; 10801 } 10802 10803 // System app batching: 10804 if (!bufferWasEmpty) { 10805 // An existing dropbox-writing thread is outstanding, so 10806 // we don't need to start it up. The existing thread will 10807 // catch the buffer appends we just did. 10808 return; 10809 } 10810 10811 // Worker thread to both batch writes and to avoid blocking the caller on I/O. 10812 // (After this point, we shouldn't access AMS internal data structures.) 10813 new Thread("Error dump: " + dropboxTag) { 10814 @Override 10815 public void run() { 10816 // 5 second sleep to let stacks arrive and be batched together 10817 try { 10818 Thread.sleep(5000); // 5 seconds 10819 } catch (InterruptedException e) {} 10820 10821 String errorReport; 10822 synchronized (mStrictModeBuffer) { 10823 errorReport = mStrictModeBuffer.toString(); 10824 if (errorReport.length() == 0) { 10825 return; 10826 } 10827 mStrictModeBuffer.delete(0, mStrictModeBuffer.length()); 10828 mStrictModeBuffer.trimToSize(); 10829 } 10830 dbox.addText(dropboxTag, errorReport); 10831 } 10832 }.start(); 10833 } 10834 10835 /** 10836 * Used by {@link Log} via {@link com.android.internal.os.RuntimeInit} to report serious errors. 10837 * @param app object of the crashing app, null for the system server 10838 * @param tag reported by the caller 10839 * @param crashInfo describing the context of the error 10840 * @return true if the process should exit immediately (WTF is fatal) 10841 */ 10842 public boolean handleApplicationWtf(IBinder app, String tag, 10843 ApplicationErrorReport.CrashInfo crashInfo) { 10844 ProcessRecord r = findAppProcess(app, "WTF"); 10845 final String processName = app == null ? "system_server" 10846 : (r == null ? "unknown" : r.processName); 10847 10848 EventLog.writeEvent(EventLogTags.AM_WTF, 10849 UserHandle.getUserId(Binder.getCallingUid()), Binder.getCallingPid(), 10850 processName, 10851 r == null ? -1 : r.info.flags, 10852 tag, crashInfo.exceptionMessage); 10853 10854 addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, crashInfo); 10855 10856 if (r != null && r.pid != Process.myPid() && 10857 Settings.Global.getInt(mContext.getContentResolver(), 10858 Settings.Global.WTF_IS_FATAL, 0) != 0) { 10859 crashApplication(r, crashInfo); 10860 return true; 10861 } else { 10862 return false; 10863 } 10864 } 10865 10866 /** 10867 * @param app object of some object (as stored in {@link com.android.internal.os.RuntimeInit}) 10868 * @return the corresponding {@link ProcessRecord} object, or null if none could be found 10869 */ 10870 private ProcessRecord findAppProcess(IBinder app, String reason) { 10871 if (app == null) { 10872 return null; 10873 } 10874 10875 synchronized (this) { 10876 final int NP = mProcessNames.getMap().size(); 10877 for (int ip=0; ip<NP; ip++) { 10878 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 10879 final int NA = apps.size(); 10880 for (int ia=0; ia<NA; ia++) { 10881 ProcessRecord p = apps.valueAt(ia); 10882 if (p.thread != null && p.thread.asBinder() == app) { 10883 return p; 10884 } 10885 } 10886 } 10887 10888 Slog.w(TAG, "Can't find mystery application for " + reason 10889 + " from pid=" + Binder.getCallingPid() 10890 + " uid=" + Binder.getCallingUid() + ": " + app); 10891 return null; 10892 } 10893 } 10894 10895 /** 10896 * Utility function for addErrorToDropBox and handleStrictModeViolation's logging 10897 * to append various headers to the dropbox log text. 10898 */ 10899 private void appendDropBoxProcessHeaders(ProcessRecord process, String processName, 10900 StringBuilder sb) { 10901 // Watchdog thread ends up invoking this function (with 10902 // a null ProcessRecord) to add the stack file to dropbox. 10903 // Do not acquire a lock on this (am) in such cases, as it 10904 // could cause a potential deadlock, if and when watchdog 10905 // is invoked due to unavailability of lock on am and it 10906 // would prevent watchdog from killing system_server. 10907 if (process == null) { 10908 sb.append("Process: ").append(processName).append("\n"); 10909 return; 10910 } 10911 // Note: ProcessRecord 'process' is guarded by the service 10912 // instance. (notably process.pkgList, which could otherwise change 10913 // concurrently during execution of this method) 10914 synchronized (this) { 10915 sb.append("Process: ").append(processName).append("\n"); 10916 int flags = process.info.flags; 10917 IPackageManager pm = AppGlobals.getPackageManager(); 10918 sb.append("Flags: 0x").append(Integer.toString(flags, 16)).append("\n"); 10919 for (int ip=0; ip<process.pkgList.size(); ip++) { 10920 String pkg = process.pkgList.keyAt(ip); 10921 sb.append("Package: ").append(pkg); 10922 try { 10923 PackageInfo pi = pm.getPackageInfo(pkg, 0, UserHandle.getCallingUserId()); 10924 if (pi != null) { 10925 sb.append(" v").append(pi.versionCode); 10926 if (pi.versionName != null) { 10927 sb.append(" (").append(pi.versionName).append(")"); 10928 } 10929 } 10930 } catch (RemoteException e) { 10931 Slog.e(TAG, "Error getting package info: " + pkg, e); 10932 } 10933 sb.append("\n"); 10934 } 10935 } 10936 } 10937 10938 private static String processClass(ProcessRecord process) { 10939 if (process == null || process.pid == MY_PID) { 10940 return "system_server"; 10941 } else if ((process.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 10942 return "system_app"; 10943 } else { 10944 return "data_app"; 10945 } 10946 } 10947 10948 /** 10949 * Write a description of an error (crash, WTF, ANR) to the drop box. 10950 * @param eventType to include in the drop box tag ("crash", "wtf", etc.) 10951 * @param process which caused the error, null means the system server 10952 * @param activity which triggered the error, null if unknown 10953 * @param parent activity related to the error, null if unknown 10954 * @param subject line related to the error, null if absent 10955 * @param report in long form describing the error, null if absent 10956 * @param logFile to include in the report, null if none 10957 * @param crashInfo giving an application stack trace, null if absent 10958 */ 10959 public void addErrorToDropBox(String eventType, 10960 ProcessRecord process, String processName, ActivityRecord activity, 10961 ActivityRecord parent, String subject, 10962 final String report, final File logFile, 10963 final ApplicationErrorReport.CrashInfo crashInfo) { 10964 // NOTE -- this must never acquire the ActivityManagerService lock, 10965 // otherwise the watchdog may be prevented from resetting the system. 10966 10967 final String dropboxTag = processClass(process) + "_" + eventType; 10968 final DropBoxManager dbox = (DropBoxManager) 10969 mContext.getSystemService(Context.DROPBOX_SERVICE); 10970 10971 // Exit early if the dropbox isn't configured to accept this report type. 10972 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 10973 10974 final StringBuilder sb = new StringBuilder(1024); 10975 appendDropBoxProcessHeaders(process, processName, sb); 10976 if (activity != null) { 10977 sb.append("Activity: ").append(activity.shortComponentName).append("\n"); 10978 } 10979 if (parent != null && parent.app != null && parent.app.pid != process.pid) { 10980 sb.append("Parent-Process: ").append(parent.app.processName).append("\n"); 10981 } 10982 if (parent != null && parent != activity) { 10983 sb.append("Parent-Activity: ").append(parent.shortComponentName).append("\n"); 10984 } 10985 if (subject != null) { 10986 sb.append("Subject: ").append(subject).append("\n"); 10987 } 10988 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 10989 if (Debug.isDebuggerConnected()) { 10990 sb.append("Debugger: Connected\n"); 10991 } 10992 sb.append("\n"); 10993 10994 // Do the rest in a worker thread to avoid blocking the caller on I/O 10995 // (After this point, we shouldn't access AMS internal data structures.) 10996 Thread worker = new Thread("Error dump: " + dropboxTag) { 10997 @Override 10998 public void run() { 10999 if (report != null) { 11000 sb.append(report); 11001 } 11002 if (logFile != null) { 11003 try { 11004 sb.append(FileUtils.readTextFile(logFile, DROPBOX_MAX_SIZE, 11005 "\n\n[[TRUNCATED]]")); 11006 } catch (IOException e) { 11007 Slog.e(TAG, "Error reading " + logFile, e); 11008 } 11009 } 11010 if (crashInfo != null && crashInfo.stackTrace != null) { 11011 sb.append(crashInfo.stackTrace); 11012 } 11013 11014 String setting = Settings.Global.ERROR_LOGCAT_PREFIX + dropboxTag; 11015 int lines = Settings.Global.getInt(mContext.getContentResolver(), setting, 0); 11016 if (lines > 0) { 11017 sb.append("\n"); 11018 11019 // Merge several logcat streams, and take the last N lines 11020 InputStreamReader input = null; 11021 try { 11022 java.lang.Process logcat = new ProcessBuilder("/system/bin/logcat", 11023 "-v", "time", "-b", "events", "-b", "system", "-b", "main", 11024 "-t", String.valueOf(lines)).redirectErrorStream(true).start(); 11025 11026 try { logcat.getOutputStream().close(); } catch (IOException e) {} 11027 try { logcat.getErrorStream().close(); } catch (IOException e) {} 11028 input = new InputStreamReader(logcat.getInputStream()); 11029 11030 int num; 11031 char[] buf = new char[8192]; 11032 while ((num = input.read(buf)) > 0) sb.append(buf, 0, num); 11033 } catch (IOException e) { 11034 Slog.e(TAG, "Error running logcat", e); 11035 } finally { 11036 if (input != null) try { input.close(); } catch (IOException e) {} 11037 } 11038 } 11039 11040 dbox.addText(dropboxTag, sb.toString()); 11041 } 11042 }; 11043 11044 if (process == null) { 11045 // If process is null, we are being called from some internal code 11046 // and may be about to die -- run this synchronously. 11047 worker.run(); 11048 } else { 11049 worker.start(); 11050 } 11051 } 11052 11053 /** 11054 * Bring up the "unexpected error" dialog box for a crashing app. 11055 * Deal with edge cases (intercepts from instrumented applications, 11056 * ActivityController, error intent receivers, that sort of thing). 11057 * @param r the application crashing 11058 * @param crashInfo describing the failure 11059 */ 11060 private void crashApplication(ProcessRecord r, ApplicationErrorReport.CrashInfo crashInfo) { 11061 long timeMillis = System.currentTimeMillis(); 11062 String shortMsg = crashInfo.exceptionClassName; 11063 String longMsg = crashInfo.exceptionMessage; 11064 String stackTrace = crashInfo.stackTrace; 11065 if (shortMsg != null && longMsg != null) { 11066 longMsg = shortMsg + ": " + longMsg; 11067 } else if (shortMsg != null) { 11068 longMsg = shortMsg; 11069 } 11070 11071 AppErrorResult result = new AppErrorResult(); 11072 synchronized (this) { 11073 if (mController != null) { 11074 try { 11075 String name = r != null ? r.processName : null; 11076 int pid = r != null ? r.pid : Binder.getCallingPid(); 11077 int uid = r != null ? r.info.uid : Binder.getCallingUid(); 11078 if (!mController.appCrashed(name, pid, 11079 shortMsg, longMsg, timeMillis, crashInfo.stackTrace)) { 11080 if ("1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")) 11081 && "Native crash".equals(crashInfo.exceptionClassName)) { 11082 Slog.w(TAG, "Skip killing native crashed app " + name 11083 + "(" + pid + ") during testing"); 11084 } else { 11085 Slog.w(TAG, "Force-killing crashed app " + name 11086 + " at watcher's request"); 11087 Process.killProcess(pid); 11088 if (r != null) { 11089 Process.killProcessGroup(uid, pid); 11090 } 11091 } 11092 return; 11093 } 11094 } catch (RemoteException e) { 11095 mController = null; 11096 Watchdog.getInstance().setActivityController(null); 11097 } 11098 } 11099 11100 final long origId = Binder.clearCallingIdentity(); 11101 11102 // If this process is running instrumentation, finish it. 11103 if (r != null && r.instrumentationClass != null) { 11104 Slog.w(TAG, "Error in app " + r.processName 11105 + " running instrumentation " + r.instrumentationClass + ":"); 11106 if (shortMsg != null) Slog.w(TAG, " " + shortMsg); 11107 if (longMsg != null) Slog.w(TAG, " " + longMsg); 11108 Bundle info = new Bundle(); 11109 info.putString("shortMsg", shortMsg); 11110 info.putString("longMsg", longMsg); 11111 finishInstrumentationLocked(r, Activity.RESULT_CANCELED, info); 11112 Binder.restoreCallingIdentity(origId); 11113 return; 11114 } 11115 11116 // If we can't identify the process or it's already exceeded its crash quota, 11117 // quit right away without showing a crash dialog. 11118 if (r == null || !makeAppCrashingLocked(r, shortMsg, longMsg, stackTrace)) { 11119 Binder.restoreCallingIdentity(origId); 11120 return; 11121 } 11122 11123 Message msg = Message.obtain(); 11124 msg.what = SHOW_ERROR_MSG; 11125 HashMap data = new HashMap(); 11126 data.put("result", result); 11127 data.put("app", r); 11128 msg.obj = data; 11129 mHandler.sendMessage(msg); 11130 11131 Binder.restoreCallingIdentity(origId); 11132 } 11133 11134 int res = result.get(); 11135 11136 Intent appErrorIntent = null; 11137 synchronized (this) { 11138 if (r != null && !r.isolated) { 11139 // XXX Can't keep track of crash time for isolated processes, 11140 // since they don't have a persistent identity. 11141 mProcessCrashTimes.put(r.info.processName, r.uid, 11142 SystemClock.uptimeMillis()); 11143 } 11144 if (res == AppErrorDialog.FORCE_QUIT_AND_REPORT) { 11145 appErrorIntent = createAppErrorIntentLocked(r, timeMillis, crashInfo); 11146 } 11147 } 11148 11149 if (appErrorIntent != null) { 11150 try { 11151 mContext.startActivityAsUser(appErrorIntent, new UserHandle(r.userId)); 11152 } catch (ActivityNotFoundException e) { 11153 Slog.w(TAG, "bug report receiver dissappeared", e); 11154 } 11155 } 11156 } 11157 11158 Intent createAppErrorIntentLocked(ProcessRecord r, 11159 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 11160 ApplicationErrorReport report = createAppErrorReportLocked(r, timeMillis, crashInfo); 11161 if (report == null) { 11162 return null; 11163 } 11164 Intent result = new Intent(Intent.ACTION_APP_ERROR); 11165 result.setComponent(r.errorReportReceiver); 11166 result.putExtra(Intent.EXTRA_BUG_REPORT, report); 11167 result.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 11168 return result; 11169 } 11170 11171 private ApplicationErrorReport createAppErrorReportLocked(ProcessRecord r, 11172 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 11173 if (r.errorReportReceiver == null) { 11174 return null; 11175 } 11176 11177 if (!r.crashing && !r.notResponding && !r.forceCrashReport) { 11178 return null; 11179 } 11180 11181 ApplicationErrorReport report = new ApplicationErrorReport(); 11182 report.packageName = r.info.packageName; 11183 report.installerPackageName = r.errorReportReceiver.getPackageName(); 11184 report.processName = r.processName; 11185 report.time = timeMillis; 11186 report.systemApp = (r.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0; 11187 11188 if (r.crashing || r.forceCrashReport) { 11189 report.type = ApplicationErrorReport.TYPE_CRASH; 11190 report.crashInfo = crashInfo; 11191 } else if (r.notResponding) { 11192 report.type = ApplicationErrorReport.TYPE_ANR; 11193 report.anrInfo = new ApplicationErrorReport.AnrInfo(); 11194 11195 report.anrInfo.activity = r.notRespondingReport.tag; 11196 report.anrInfo.cause = r.notRespondingReport.shortMsg; 11197 report.anrInfo.info = r.notRespondingReport.longMsg; 11198 } 11199 11200 return report; 11201 } 11202 11203 public List<ActivityManager.ProcessErrorStateInfo> getProcessesInErrorState() { 11204 enforceNotIsolatedCaller("getProcessesInErrorState"); 11205 // assume our apps are happy - lazy create the list 11206 List<ActivityManager.ProcessErrorStateInfo> errList = null; 11207 11208 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 11209 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 11210 int userId = UserHandle.getUserId(Binder.getCallingUid()); 11211 11212 synchronized (this) { 11213 11214 // iterate across all processes 11215 for (int i=mLruProcesses.size()-1; i>=0; i--) { 11216 ProcessRecord app = mLruProcesses.get(i); 11217 if (!allUsers && app.userId != userId) { 11218 continue; 11219 } 11220 if ((app.thread != null) && (app.crashing || app.notResponding)) { 11221 // This one's in trouble, so we'll generate a report for it 11222 // crashes are higher priority (in case there's a crash *and* an anr) 11223 ActivityManager.ProcessErrorStateInfo report = null; 11224 if (app.crashing) { 11225 report = app.crashingReport; 11226 } else if (app.notResponding) { 11227 report = app.notRespondingReport; 11228 } 11229 11230 if (report != null) { 11231 if (errList == null) { 11232 errList = new ArrayList<ActivityManager.ProcessErrorStateInfo>(1); 11233 } 11234 errList.add(report); 11235 } else { 11236 Slog.w(TAG, "Missing app error report, app = " + app.processName + 11237 " crashing = " + app.crashing + 11238 " notResponding = " + app.notResponding); 11239 } 11240 } 11241 } 11242 } 11243 11244 return errList; 11245 } 11246 11247 static int procStateToImportance(int procState, int memAdj, 11248 ActivityManager.RunningAppProcessInfo currApp) { 11249 int imp = ActivityManager.RunningAppProcessInfo.procStateToImportance(procState); 11250 if (imp == ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND) { 11251 currApp.lru = memAdj; 11252 } else { 11253 currApp.lru = 0; 11254 } 11255 return imp; 11256 } 11257 11258 private void fillInProcMemInfo(ProcessRecord app, 11259 ActivityManager.RunningAppProcessInfo outInfo) { 11260 outInfo.pid = app.pid; 11261 outInfo.uid = app.info.uid; 11262 if (mHeavyWeightProcess == app) { 11263 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_CANT_SAVE_STATE; 11264 } 11265 if (app.persistent) { 11266 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_PERSISTENT; 11267 } 11268 if (app.activities.size() > 0) { 11269 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_HAS_ACTIVITIES; 11270 } 11271 outInfo.lastTrimLevel = app.trimMemoryLevel; 11272 int adj = app.curAdj; 11273 int procState = app.curProcState; 11274 outInfo.importance = procStateToImportance(procState, adj, outInfo); 11275 outInfo.importanceReasonCode = app.adjTypeCode; 11276 outInfo.processState = app.curProcState; 11277 } 11278 11279 public List<ActivityManager.RunningAppProcessInfo> getRunningAppProcesses() { 11280 enforceNotIsolatedCaller("getRunningAppProcesses"); 11281 // Lazy instantiation of list 11282 List<ActivityManager.RunningAppProcessInfo> runList = null; 11283 final boolean allUsers = ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, 11284 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 11285 int userId = UserHandle.getUserId(Binder.getCallingUid()); 11286 synchronized (this) { 11287 // Iterate across all processes 11288 for (int i=mLruProcesses.size()-1; i>=0; i--) { 11289 ProcessRecord app = mLruProcesses.get(i); 11290 if (!allUsers && app.userId != userId) { 11291 continue; 11292 } 11293 if ((app.thread != null) && (!app.crashing && !app.notResponding)) { 11294 // Generate process state info for running application 11295 ActivityManager.RunningAppProcessInfo currApp = 11296 new ActivityManager.RunningAppProcessInfo(app.processName, 11297 app.pid, app.getPackageList()); 11298 fillInProcMemInfo(app, currApp); 11299 if (app.adjSource instanceof ProcessRecord) { 11300 currApp.importanceReasonPid = ((ProcessRecord)app.adjSource).pid; 11301 currApp.importanceReasonImportance = 11302 ActivityManager.RunningAppProcessInfo.procStateToImportance( 11303 app.adjSourceProcState); 11304 } else if (app.adjSource instanceof ActivityRecord) { 11305 ActivityRecord r = (ActivityRecord)app.adjSource; 11306 if (r.app != null) currApp.importanceReasonPid = r.app.pid; 11307 } 11308 if (app.adjTarget instanceof ComponentName) { 11309 currApp.importanceReasonComponent = (ComponentName)app.adjTarget; 11310 } 11311 //Slog.v(TAG, "Proc " + app.processName + ": imp=" + currApp.importance 11312 // + " lru=" + currApp.lru); 11313 if (runList == null) { 11314 runList = new ArrayList<ActivityManager.RunningAppProcessInfo>(); 11315 } 11316 runList.add(currApp); 11317 } 11318 } 11319 } 11320 return runList; 11321 } 11322 11323 public List<ApplicationInfo> getRunningExternalApplications() { 11324 enforceNotIsolatedCaller("getRunningExternalApplications"); 11325 List<ActivityManager.RunningAppProcessInfo> runningApps = getRunningAppProcesses(); 11326 List<ApplicationInfo> retList = new ArrayList<ApplicationInfo>(); 11327 if (runningApps != null && runningApps.size() > 0) { 11328 Set<String> extList = new HashSet<String>(); 11329 for (ActivityManager.RunningAppProcessInfo app : runningApps) { 11330 if (app.pkgList != null) { 11331 for (String pkg : app.pkgList) { 11332 extList.add(pkg); 11333 } 11334 } 11335 } 11336 IPackageManager pm = AppGlobals.getPackageManager(); 11337 for (String pkg : extList) { 11338 try { 11339 ApplicationInfo info = pm.getApplicationInfo(pkg, 0, UserHandle.getCallingUserId()); 11340 if ((info.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0) { 11341 retList.add(info); 11342 } 11343 } catch (RemoteException e) { 11344 } 11345 } 11346 } 11347 return retList; 11348 } 11349 11350 @Override 11351 public void getMyMemoryState(ActivityManager.RunningAppProcessInfo outInfo) { 11352 enforceNotIsolatedCaller("getMyMemoryState"); 11353 synchronized (this) { 11354 ProcessRecord proc; 11355 synchronized (mPidsSelfLocked) { 11356 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 11357 } 11358 fillInProcMemInfo(proc, outInfo); 11359 } 11360 } 11361 11362 @Override 11363 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 11364 if (checkCallingPermission(android.Manifest.permission.DUMP) 11365 != PackageManager.PERMISSION_GRANTED) { 11366 pw.println("Permission Denial: can't dump ActivityManager from from pid=" 11367 + Binder.getCallingPid() 11368 + ", uid=" + Binder.getCallingUid() 11369 + " without permission " 11370 + android.Manifest.permission.DUMP); 11371 return; 11372 } 11373 11374 boolean dumpAll = false; 11375 boolean dumpClient = false; 11376 String dumpPackage = null; 11377 11378 int opti = 0; 11379 while (opti < args.length) { 11380 String opt = args[opti]; 11381 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 11382 break; 11383 } 11384 opti++; 11385 if ("-a".equals(opt)) { 11386 dumpAll = true; 11387 } else if ("-c".equals(opt)) { 11388 dumpClient = true; 11389 } else if ("-h".equals(opt)) { 11390 pw.println("Activity manager dump options:"); 11391 pw.println(" [-a] [-c] [-h] [cmd] ..."); 11392 pw.println(" cmd may be one of:"); 11393 pw.println(" a[ctivities]: activity stack state"); 11394 pw.println(" b[roadcasts] [PACKAGE_NAME] [history [-s]]: broadcast state"); 11395 pw.println(" i[ntents] [PACKAGE_NAME]: pending intent state"); 11396 pw.println(" p[rocesses] [PACKAGE_NAME]: process state"); 11397 pw.println(" o[om]: out of memory management"); 11398 pw.println(" prov[iders] [COMP_SPEC ...]: content provider state"); 11399 pw.println(" provider [COMP_SPEC]: provider client-side state"); 11400 pw.println(" s[ervices] [COMP_SPEC ...]: service state"); 11401 pw.println(" service [COMP_SPEC]: service client-side state"); 11402 pw.println(" package [PACKAGE_NAME]: all state related to given package"); 11403 pw.println(" all: dump all activities"); 11404 pw.println(" top: dump the top activity"); 11405 pw.println(" cmd may also be a COMP_SPEC to dump activities."); 11406 pw.println(" COMP_SPEC may be a component name (com.foo/.myApp),"); 11407 pw.println(" a partial substring in a component name, a"); 11408 pw.println(" hex object identifier."); 11409 pw.println(" -a: include all available server state."); 11410 pw.println(" -c: include client state."); 11411 return; 11412 } else { 11413 pw.println("Unknown argument: " + opt + "; use -h for help"); 11414 } 11415 } 11416 11417 long origId = Binder.clearCallingIdentity(); 11418 boolean more = false; 11419 // Is the caller requesting to dump a particular piece of data? 11420 if (opti < args.length) { 11421 String cmd = args[opti]; 11422 opti++; 11423 if ("activities".equals(cmd) || "a".equals(cmd)) { 11424 synchronized (this) { 11425 dumpActivitiesLocked(fd, pw, args, opti, true, dumpClient, null); 11426 } 11427 } else if ("broadcasts".equals(cmd) || "b".equals(cmd)) { 11428 String[] newArgs; 11429 String name; 11430 if (opti >= args.length) { 11431 name = null; 11432 newArgs = EMPTY_STRING_ARRAY; 11433 } else { 11434 name = args[opti]; 11435 opti++; 11436 newArgs = new String[args.length - opti]; 11437 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11438 args.length - opti); 11439 } 11440 synchronized (this) { 11441 dumpBroadcastsLocked(fd, pw, args, opti, true, name); 11442 } 11443 } else if ("intents".equals(cmd) || "i".equals(cmd)) { 11444 String[] newArgs; 11445 String name; 11446 if (opti >= args.length) { 11447 name = null; 11448 newArgs = EMPTY_STRING_ARRAY; 11449 } else { 11450 name = args[opti]; 11451 opti++; 11452 newArgs = new String[args.length - opti]; 11453 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11454 args.length - opti); 11455 } 11456 synchronized (this) { 11457 dumpPendingIntentsLocked(fd, pw, args, opti, true, name); 11458 } 11459 } else if ("processes".equals(cmd) || "p".equals(cmd)) { 11460 String[] newArgs; 11461 String name; 11462 if (opti >= args.length) { 11463 name = null; 11464 newArgs = EMPTY_STRING_ARRAY; 11465 } else { 11466 name = args[opti]; 11467 opti++; 11468 newArgs = new String[args.length - opti]; 11469 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11470 args.length - opti); 11471 } 11472 synchronized (this) { 11473 dumpProcessesLocked(fd, pw, args, opti, true, name); 11474 } 11475 } else if ("oom".equals(cmd) || "o".equals(cmd)) { 11476 synchronized (this) { 11477 dumpOomLocked(fd, pw, args, opti, true); 11478 } 11479 } else if ("provider".equals(cmd)) { 11480 String[] newArgs; 11481 String name; 11482 if (opti >= args.length) { 11483 name = null; 11484 newArgs = EMPTY_STRING_ARRAY; 11485 } else { 11486 name = args[opti]; 11487 opti++; 11488 newArgs = new String[args.length - opti]; 11489 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, args.length - opti); 11490 } 11491 if (!dumpProvider(fd, pw, name, newArgs, 0, dumpAll)) { 11492 pw.println("No providers match: " + name); 11493 pw.println("Use -h for help."); 11494 } 11495 } else if ("providers".equals(cmd) || "prov".equals(cmd)) { 11496 synchronized (this) { 11497 dumpProvidersLocked(fd, pw, args, opti, true, null); 11498 } 11499 } else if ("service".equals(cmd)) { 11500 String[] newArgs; 11501 String name; 11502 if (opti >= args.length) { 11503 name = null; 11504 newArgs = EMPTY_STRING_ARRAY; 11505 } else { 11506 name = args[opti]; 11507 opti++; 11508 newArgs = new String[args.length - opti]; 11509 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11510 args.length - opti); 11511 } 11512 if (!mServices.dumpService(fd, pw, name, newArgs, 0, dumpAll)) { 11513 pw.println("No services match: " + name); 11514 pw.println("Use -h for help."); 11515 } 11516 } else if ("package".equals(cmd)) { 11517 String[] newArgs; 11518 if (opti >= args.length) { 11519 pw.println("package: no package name specified"); 11520 pw.println("Use -h for help."); 11521 } else { 11522 dumpPackage = args[opti]; 11523 opti++; 11524 newArgs = new String[args.length - opti]; 11525 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 11526 args.length - opti); 11527 args = newArgs; 11528 opti = 0; 11529 more = true; 11530 } 11531 } else if ("services".equals(cmd) || "s".equals(cmd)) { 11532 synchronized (this) { 11533 mServices.dumpServicesLocked(fd, pw, args, opti, true, dumpClient, null); 11534 } 11535 } else { 11536 // Dumping a single activity? 11537 if (!dumpActivity(fd, pw, cmd, args, opti, dumpAll)) { 11538 pw.println("Bad activity command, or no activities match: " + cmd); 11539 pw.println("Use -h for help."); 11540 } 11541 } 11542 if (!more) { 11543 Binder.restoreCallingIdentity(origId); 11544 return; 11545 } 11546 } 11547 11548 // No piece of data specified, dump everything. 11549 synchronized (this) { 11550 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11551 pw.println(); 11552 if (dumpAll) { 11553 pw.println("-------------------------------------------------------------------------------"); 11554 } 11555 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11556 pw.println(); 11557 if (dumpAll) { 11558 pw.println("-------------------------------------------------------------------------------"); 11559 } 11560 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11561 pw.println(); 11562 if (dumpAll) { 11563 pw.println("-------------------------------------------------------------------------------"); 11564 } 11565 mServices.dumpServicesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 11566 pw.println(); 11567 if (dumpAll) { 11568 pw.println("-------------------------------------------------------------------------------"); 11569 } 11570 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 11571 pw.println(); 11572 if (dumpAll) { 11573 pw.println("-------------------------------------------------------------------------------"); 11574 } 11575 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage); 11576 } 11577 Binder.restoreCallingIdentity(origId); 11578 } 11579 11580 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11581 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) { 11582 pw.println("ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)"); 11583 11584 boolean printedAnything = mStackSupervisor.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient, 11585 dumpPackage); 11586 boolean needSep = printedAnything; 11587 11588 boolean printed = ActivityStackSupervisor.printThisActivity(pw, mFocusedActivity, 11589 dumpPackage, needSep, " mFocusedActivity: "); 11590 if (printed) { 11591 printedAnything = true; 11592 needSep = false; 11593 } 11594 11595 if (dumpPackage == null) { 11596 if (needSep) { 11597 pw.println(); 11598 } 11599 needSep = true; 11600 printedAnything = true; 11601 mStackSupervisor.dump(pw, " "); 11602 } 11603 11604 if (mRecentTasks.size() > 0) { 11605 boolean printedHeader = false; 11606 11607 final int N = mRecentTasks.size(); 11608 for (int i=0; i<N; i++) { 11609 TaskRecord tr = mRecentTasks.get(i); 11610 if (dumpPackage != null) { 11611 if (tr.realActivity == null || 11612 !dumpPackage.equals(tr.realActivity)) { 11613 continue; 11614 } 11615 } 11616 if (!printedHeader) { 11617 if (needSep) { 11618 pw.println(); 11619 } 11620 pw.println(" Recent tasks:"); 11621 printedHeader = true; 11622 printedAnything = true; 11623 } 11624 pw.print(" * Recent #"); pw.print(i); pw.print(": "); 11625 pw.println(tr); 11626 if (dumpAll) { 11627 mRecentTasks.get(i).dump(pw, " "); 11628 } 11629 } 11630 } 11631 11632 if (!printedAnything) { 11633 pw.println(" (nothing)"); 11634 } 11635 } 11636 11637 void dumpProcessesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11638 int opti, boolean dumpAll, String dumpPackage) { 11639 boolean needSep = false; 11640 boolean printedAnything = false; 11641 int numPers = 0; 11642 11643 pw.println("ACTIVITY MANAGER RUNNING PROCESSES (dumpsys activity processes)"); 11644 11645 if (dumpAll) { 11646 final int NP = mProcessNames.getMap().size(); 11647 for (int ip=0; ip<NP; ip++) { 11648 SparseArray<ProcessRecord> procs = mProcessNames.getMap().valueAt(ip); 11649 final int NA = procs.size(); 11650 for (int ia=0; ia<NA; ia++) { 11651 ProcessRecord r = procs.valueAt(ia); 11652 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11653 continue; 11654 } 11655 if (!needSep) { 11656 pw.println(" All known processes:"); 11657 needSep = true; 11658 printedAnything = true; 11659 } 11660 pw.print(r.persistent ? " *PERS*" : " *APP*"); 11661 pw.print(" UID "); pw.print(procs.keyAt(ia)); 11662 pw.print(" "); pw.println(r); 11663 r.dump(pw, " "); 11664 if (r.persistent) { 11665 numPers++; 11666 } 11667 } 11668 } 11669 } 11670 11671 if (mIsolatedProcesses.size() > 0) { 11672 boolean printed = false; 11673 for (int i=0; i<mIsolatedProcesses.size(); i++) { 11674 ProcessRecord r = mIsolatedProcesses.valueAt(i); 11675 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11676 continue; 11677 } 11678 if (!printed) { 11679 if (needSep) { 11680 pw.println(); 11681 } 11682 pw.println(" Isolated process list (sorted by uid):"); 11683 printedAnything = true; 11684 printed = true; 11685 needSep = true; 11686 } 11687 pw.println(String.format("%sIsolated #%2d: %s", 11688 " ", i, r.toString())); 11689 } 11690 } 11691 11692 if (mLruProcesses.size() > 0) { 11693 if (needSep) { 11694 pw.println(); 11695 } 11696 pw.print(" Process LRU list (sorted by oom_adj, "); pw.print(mLruProcesses.size()); 11697 pw.print(" total, non-act at "); 11698 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 11699 pw.print(", non-svc at "); 11700 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 11701 pw.println("):"); 11702 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", false, dumpPackage); 11703 needSep = true; 11704 printedAnything = true; 11705 } 11706 11707 if (dumpAll || dumpPackage != null) { 11708 synchronized (mPidsSelfLocked) { 11709 boolean printed = false; 11710 for (int i=0; i<mPidsSelfLocked.size(); i++) { 11711 ProcessRecord r = mPidsSelfLocked.valueAt(i); 11712 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11713 continue; 11714 } 11715 if (!printed) { 11716 if (needSep) pw.println(); 11717 needSep = true; 11718 pw.println(" PID mappings:"); 11719 printed = true; 11720 printedAnything = true; 11721 } 11722 pw.print(" PID #"); pw.print(mPidsSelfLocked.keyAt(i)); 11723 pw.print(": "); pw.println(mPidsSelfLocked.valueAt(i)); 11724 } 11725 } 11726 } 11727 11728 if (mForegroundProcesses.size() > 0) { 11729 synchronized (mPidsSelfLocked) { 11730 boolean printed = false; 11731 for (int i=0; i<mForegroundProcesses.size(); i++) { 11732 ProcessRecord r = mPidsSelfLocked.get( 11733 mForegroundProcesses.valueAt(i).pid); 11734 if (dumpPackage != null && (r == null 11735 || !r.pkgList.containsKey(dumpPackage))) { 11736 continue; 11737 } 11738 if (!printed) { 11739 if (needSep) pw.println(); 11740 needSep = true; 11741 pw.println(" Foreground Processes:"); 11742 printed = true; 11743 printedAnything = true; 11744 } 11745 pw.print(" PID #"); pw.print(mForegroundProcesses.keyAt(i)); 11746 pw.print(": "); pw.println(mForegroundProcesses.valueAt(i)); 11747 } 11748 } 11749 } 11750 11751 if (mPersistentStartingProcesses.size() > 0) { 11752 if (needSep) pw.println(); 11753 needSep = true; 11754 printedAnything = true; 11755 pw.println(" Persisent processes that are starting:"); 11756 dumpProcessList(pw, this, mPersistentStartingProcesses, " ", 11757 "Starting Norm", "Restarting PERS", dumpPackage); 11758 } 11759 11760 if (mRemovedProcesses.size() > 0) { 11761 if (needSep) pw.println(); 11762 needSep = true; 11763 printedAnything = true; 11764 pw.println(" Processes that are being removed:"); 11765 dumpProcessList(pw, this, mRemovedProcesses, " ", 11766 "Removed Norm", "Removed PERS", dumpPackage); 11767 } 11768 11769 if (mProcessesOnHold.size() > 0) { 11770 if (needSep) pw.println(); 11771 needSep = true; 11772 printedAnything = true; 11773 pw.println(" Processes that are on old until the system is ready:"); 11774 dumpProcessList(pw, this, mProcessesOnHold, " ", 11775 "OnHold Norm", "OnHold PERS", dumpPackage); 11776 } 11777 11778 needSep = dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, dumpPackage); 11779 11780 if (mProcessCrashTimes.getMap().size() > 0) { 11781 boolean printed = false; 11782 long now = SystemClock.uptimeMillis(); 11783 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 11784 final int NP = pmap.size(); 11785 for (int ip=0; ip<NP; ip++) { 11786 String pname = pmap.keyAt(ip); 11787 SparseArray<Long> uids = pmap.valueAt(ip); 11788 final int N = uids.size(); 11789 for (int i=0; i<N; i++) { 11790 int puid = uids.keyAt(i); 11791 ProcessRecord r = mProcessNames.get(pname, puid); 11792 if (dumpPackage != null && (r == null 11793 || !r.pkgList.containsKey(dumpPackage))) { 11794 continue; 11795 } 11796 if (!printed) { 11797 if (needSep) pw.println(); 11798 needSep = true; 11799 pw.println(" Time since processes crashed:"); 11800 printed = true; 11801 printedAnything = true; 11802 } 11803 pw.print(" Process "); pw.print(pname); 11804 pw.print(" uid "); pw.print(puid); 11805 pw.print(": last crashed "); 11806 TimeUtils.formatDuration(now-uids.valueAt(i), pw); 11807 pw.println(" ago"); 11808 } 11809 } 11810 } 11811 11812 if (mBadProcesses.getMap().size() > 0) { 11813 boolean printed = false; 11814 final ArrayMap<String, SparseArray<BadProcessInfo>> pmap = mBadProcesses.getMap(); 11815 final int NP = pmap.size(); 11816 for (int ip=0; ip<NP; ip++) { 11817 String pname = pmap.keyAt(ip); 11818 SparseArray<BadProcessInfo> uids = pmap.valueAt(ip); 11819 final int N = uids.size(); 11820 for (int i=0; i<N; i++) { 11821 int puid = uids.keyAt(i); 11822 ProcessRecord r = mProcessNames.get(pname, puid); 11823 if (dumpPackage != null && (r == null 11824 || !r.pkgList.containsKey(dumpPackage))) { 11825 continue; 11826 } 11827 if (!printed) { 11828 if (needSep) pw.println(); 11829 needSep = true; 11830 pw.println(" Bad processes:"); 11831 printedAnything = true; 11832 } 11833 BadProcessInfo info = uids.valueAt(i); 11834 pw.print(" Bad process "); pw.print(pname); 11835 pw.print(" uid "); pw.print(puid); 11836 pw.print(": crashed at time "); pw.println(info.time); 11837 if (info.shortMsg != null) { 11838 pw.print(" Short msg: "); pw.println(info.shortMsg); 11839 } 11840 if (info.longMsg != null) { 11841 pw.print(" Long msg: "); pw.println(info.longMsg); 11842 } 11843 if (info.stack != null) { 11844 pw.println(" Stack:"); 11845 int lastPos = 0; 11846 for (int pos=0; pos<info.stack.length(); pos++) { 11847 if (info.stack.charAt(pos) == '\n') { 11848 pw.print(" "); 11849 pw.write(info.stack, lastPos, pos-lastPos); 11850 pw.println(); 11851 lastPos = pos+1; 11852 } 11853 } 11854 if (lastPos < info.stack.length()) { 11855 pw.print(" "); 11856 pw.write(info.stack, lastPos, info.stack.length()-lastPos); 11857 pw.println(); 11858 } 11859 } 11860 } 11861 } 11862 } 11863 11864 if (dumpPackage == null) { 11865 pw.println(); 11866 needSep = false; 11867 pw.println(" mStartedUsers:"); 11868 for (int i=0; i<mStartedUsers.size(); i++) { 11869 UserStartedState uss = mStartedUsers.valueAt(i); 11870 pw.print(" User #"); pw.print(uss.mHandle.getIdentifier()); 11871 pw.print(": "); uss.dump("", pw); 11872 } 11873 pw.print(" mStartedUserArray: ["); 11874 for (int i=0; i<mStartedUserArray.length; i++) { 11875 if (i > 0) pw.print(", "); 11876 pw.print(mStartedUserArray[i]); 11877 } 11878 pw.println("]"); 11879 pw.print(" mUserLru: ["); 11880 for (int i=0; i<mUserLru.size(); i++) { 11881 if (i > 0) pw.print(", "); 11882 pw.print(mUserLru.get(i)); 11883 } 11884 pw.println("]"); 11885 if (dumpAll) { 11886 pw.print(" mStartedUserArray: "); pw.println(Arrays.toString(mStartedUserArray)); 11887 } 11888 synchronized (mUserProfileGroupIdsSelfLocked) { 11889 if (mUserProfileGroupIdsSelfLocked.size() > 0) { 11890 pw.println(" mUserProfileGroupIds:"); 11891 for (int i=0; i<mUserProfileGroupIdsSelfLocked.size(); i++) { 11892 pw.print(" User #"); 11893 pw.print(mUserProfileGroupIdsSelfLocked.keyAt(i)); 11894 pw.print(" -> profile #"); 11895 pw.println(mUserProfileGroupIdsSelfLocked.valueAt(i)); 11896 } 11897 } 11898 } 11899 } 11900 if (mHomeProcess != null && (dumpPackage == null 11901 || mHomeProcess.pkgList.containsKey(dumpPackage))) { 11902 if (needSep) { 11903 pw.println(); 11904 needSep = false; 11905 } 11906 pw.println(" mHomeProcess: " + mHomeProcess); 11907 } 11908 if (mPreviousProcess != null && (dumpPackage == null 11909 || mPreviousProcess.pkgList.containsKey(dumpPackage))) { 11910 if (needSep) { 11911 pw.println(); 11912 needSep = false; 11913 } 11914 pw.println(" mPreviousProcess: " + mPreviousProcess); 11915 } 11916 if (dumpAll) { 11917 StringBuilder sb = new StringBuilder(128); 11918 sb.append(" mPreviousProcessVisibleTime: "); 11919 TimeUtils.formatDuration(mPreviousProcessVisibleTime, sb); 11920 pw.println(sb); 11921 } 11922 if (mHeavyWeightProcess != null && (dumpPackage == null 11923 || mHeavyWeightProcess.pkgList.containsKey(dumpPackage))) { 11924 if (needSep) { 11925 pw.println(); 11926 needSep = false; 11927 } 11928 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 11929 } 11930 if (dumpPackage == null) { 11931 pw.println(" mConfiguration: " + mConfiguration); 11932 } 11933 if (dumpAll) { 11934 pw.println(" mConfigWillChange: " + getFocusedStack().mConfigWillChange); 11935 if (mCompatModePackages.getPackages().size() > 0) { 11936 boolean printed = false; 11937 for (Map.Entry<String, Integer> entry 11938 : mCompatModePackages.getPackages().entrySet()) { 11939 String pkg = entry.getKey(); 11940 int mode = entry.getValue(); 11941 if (dumpPackage != null && !dumpPackage.equals(pkg)) { 11942 continue; 11943 } 11944 if (!printed) { 11945 pw.println(" mScreenCompatPackages:"); 11946 printed = true; 11947 } 11948 pw.print(" "); pw.print(pkg); pw.print(": "); 11949 pw.print(mode); pw.println(); 11950 } 11951 } 11952 } 11953 if (dumpPackage == null) { 11954 if (mSleeping || mWentToSleep || mLockScreenShown) { 11955 pw.println(" mSleeping=" + mSleeping + " mWentToSleep=" + mWentToSleep 11956 + " mLockScreenShown " + mLockScreenShown); 11957 } 11958 if (mShuttingDown || mRunningVoice) { 11959 pw.print(" mShuttingDown=" + mShuttingDown + " mRunningVoice=" + mRunningVoice); 11960 } 11961 } 11962 if (mDebugApp != null || mOrigDebugApp != null || mDebugTransient 11963 || mOrigWaitForDebugger) { 11964 if (dumpPackage == null || dumpPackage.equals(mDebugApp) 11965 || dumpPackage.equals(mOrigDebugApp)) { 11966 if (needSep) { 11967 pw.println(); 11968 needSep = false; 11969 } 11970 pw.println(" mDebugApp=" + mDebugApp + "/orig=" + mOrigDebugApp 11971 + " mDebugTransient=" + mDebugTransient 11972 + " mOrigWaitForDebugger=" + mOrigWaitForDebugger); 11973 } 11974 } 11975 if (mOpenGlTraceApp != null) { 11976 if (dumpPackage == null || dumpPackage.equals(mOpenGlTraceApp)) { 11977 if (needSep) { 11978 pw.println(); 11979 needSep = false; 11980 } 11981 pw.println(" mOpenGlTraceApp=" + mOpenGlTraceApp); 11982 } 11983 } 11984 if (mProfileApp != null || mProfileProc != null || mProfileFile != null 11985 || mProfileFd != null) { 11986 if (dumpPackage == null || dumpPackage.equals(mProfileApp)) { 11987 if (needSep) { 11988 pw.println(); 11989 needSep = false; 11990 } 11991 pw.println(" mProfileApp=" + mProfileApp + " mProfileProc=" + mProfileProc); 11992 pw.println(" mProfileFile=" + mProfileFile + " mProfileFd=" + mProfileFd); 11993 pw.println(" mProfileType=" + mProfileType + " mAutoStopProfiler=" 11994 + mAutoStopProfiler); 11995 } 11996 } 11997 if (dumpPackage == null) { 11998 if (mAlwaysFinishActivities || mController != null) { 11999 pw.println(" mAlwaysFinishActivities=" + mAlwaysFinishActivities 12000 + " mController=" + mController); 12001 } 12002 if (dumpAll) { 12003 pw.println(" Total persistent processes: " + numPers); 12004 pw.println(" mProcessesReady=" + mProcessesReady 12005 + " mSystemReady=" + mSystemReady); 12006 pw.println(" mBooting=" + mBooting 12007 + " mBooted=" + mBooted 12008 + " mFactoryTest=" + mFactoryTest); 12009 pw.print(" mLastPowerCheckRealtime="); 12010 TimeUtils.formatDuration(mLastPowerCheckRealtime, pw); 12011 pw.println(""); 12012 pw.print(" mLastPowerCheckUptime="); 12013 TimeUtils.formatDuration(mLastPowerCheckUptime, pw); 12014 pw.println(""); 12015 pw.println(" mGoingToSleep=" + mStackSupervisor.mGoingToSleep); 12016 pw.println(" mLaunchingActivity=" + mStackSupervisor.mLaunchingActivity); 12017 pw.println(" mAdjSeq=" + mAdjSeq + " mLruSeq=" + mLruSeq); 12018 pw.println(" mNumNonCachedProcs=" + mNumNonCachedProcs 12019 + " (" + mLruProcesses.size() + " total)" 12020 + " mNumCachedHiddenProcs=" + mNumCachedHiddenProcs 12021 + " mNumServiceProcs=" + mNumServiceProcs 12022 + " mNewNumServiceProcs=" + mNewNumServiceProcs); 12023 pw.println(" mAllowLowerMemLevel=" + mAllowLowerMemLevel 12024 + " mLastMemoryLevel" + mLastMemoryLevel 12025 + " mLastNumProcesses" + mLastNumProcesses); 12026 long now = SystemClock.uptimeMillis(); 12027 pw.print(" mLastIdleTime="); 12028 TimeUtils.formatDuration(now, mLastIdleTime, pw); 12029 pw.print(" mLowRamSinceLastIdle="); 12030 TimeUtils.formatDuration(getLowRamTimeSinceIdle(now), pw); 12031 pw.println(); 12032 } 12033 } 12034 12035 if (!printedAnything) { 12036 pw.println(" (nothing)"); 12037 } 12038 } 12039 12040 boolean dumpProcessesToGc(FileDescriptor fd, PrintWriter pw, String[] args, 12041 int opti, boolean needSep, boolean dumpAll, String dumpPackage) { 12042 if (mProcessesToGc.size() > 0) { 12043 boolean printed = false; 12044 long now = SystemClock.uptimeMillis(); 12045 for (int i=0; i<mProcessesToGc.size(); i++) { 12046 ProcessRecord proc = mProcessesToGc.get(i); 12047 if (dumpPackage != null && !dumpPackage.equals(proc.info.packageName)) { 12048 continue; 12049 } 12050 if (!printed) { 12051 if (needSep) pw.println(); 12052 needSep = true; 12053 pw.println(" Processes that are waiting to GC:"); 12054 printed = true; 12055 } 12056 pw.print(" Process "); pw.println(proc); 12057 pw.print(" lowMem="); pw.print(proc.reportLowMemory); 12058 pw.print(", last gced="); 12059 pw.print(now-proc.lastRequestedGc); 12060 pw.print(" ms ago, last lowMem="); 12061 pw.print(now-proc.lastLowMemory); 12062 pw.println(" ms ago"); 12063 12064 } 12065 } 12066 return needSep; 12067 } 12068 12069 void printOomLevel(PrintWriter pw, String name, int adj) { 12070 pw.print(" "); 12071 if (adj >= 0) { 12072 pw.print(' '); 12073 if (adj < 10) pw.print(' '); 12074 } else { 12075 if (adj > -10) pw.print(' '); 12076 } 12077 pw.print(adj); 12078 pw.print(": "); 12079 pw.print(name); 12080 pw.print(" ("); 12081 pw.print(mProcessList.getMemLevel(adj)/1024); 12082 pw.println(" kB)"); 12083 } 12084 12085 boolean dumpOomLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12086 int opti, boolean dumpAll) { 12087 boolean needSep = false; 12088 12089 if (mLruProcesses.size() > 0) { 12090 if (needSep) pw.println(); 12091 needSep = true; 12092 pw.println(" OOM levels:"); 12093 printOomLevel(pw, "SYSTEM_ADJ", ProcessList.SYSTEM_ADJ); 12094 printOomLevel(pw, "PERSISTENT_PROC_ADJ", ProcessList.PERSISTENT_PROC_ADJ); 12095 printOomLevel(pw, "FOREGROUND_APP_ADJ", ProcessList.FOREGROUND_APP_ADJ); 12096 printOomLevel(pw, "VISIBLE_APP_ADJ", ProcessList.VISIBLE_APP_ADJ); 12097 printOomLevel(pw, "PERCEPTIBLE_APP_ADJ", ProcessList.PERCEPTIBLE_APP_ADJ); 12098 printOomLevel(pw, "BACKUP_APP_ADJ", ProcessList.BACKUP_APP_ADJ); 12099 printOomLevel(pw, "HEAVY_WEIGHT_APP_ADJ", ProcessList.HEAVY_WEIGHT_APP_ADJ); 12100 printOomLevel(pw, "SERVICE_ADJ", ProcessList.SERVICE_ADJ); 12101 printOomLevel(pw, "HOME_APP_ADJ", ProcessList.HOME_APP_ADJ); 12102 printOomLevel(pw, "PREVIOUS_APP_ADJ", ProcessList.PREVIOUS_APP_ADJ); 12103 printOomLevel(pw, "SERVICE_B_ADJ", ProcessList.SERVICE_B_ADJ); 12104 printOomLevel(pw, "CACHED_APP_MIN_ADJ", ProcessList.CACHED_APP_MIN_ADJ); 12105 printOomLevel(pw, "CACHED_APP_MAX_ADJ", ProcessList.CACHED_APP_MAX_ADJ); 12106 12107 if (needSep) pw.println(); 12108 pw.print(" Process OOM control ("); pw.print(mLruProcesses.size()); 12109 pw.print(" total, non-act at "); 12110 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 12111 pw.print(", non-svc at "); 12112 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 12113 pw.println("):"); 12114 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", true, null); 12115 needSep = true; 12116 } 12117 12118 dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, null); 12119 12120 pw.println(); 12121 pw.println(" mHomeProcess: " + mHomeProcess); 12122 pw.println(" mPreviousProcess: " + mPreviousProcess); 12123 if (mHeavyWeightProcess != null) { 12124 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 12125 } 12126 12127 return true; 12128 } 12129 12130 /** 12131 * There are three ways to call this: 12132 * - no provider specified: dump all the providers 12133 * - a flattened component name that matched an existing provider was specified as the 12134 * first arg: dump that one provider 12135 * - the first arg isn't the flattened component name of an existing provider: 12136 * dump all providers whose component contains the first arg as a substring 12137 */ 12138 protected boolean dumpProvider(FileDescriptor fd, PrintWriter pw, String name, String[] args, 12139 int opti, boolean dumpAll) { 12140 return mProviderMap.dumpProvider(fd, pw, name, args, opti, dumpAll); 12141 } 12142 12143 static class ItemMatcher { 12144 ArrayList<ComponentName> components; 12145 ArrayList<String> strings; 12146 ArrayList<Integer> objects; 12147 boolean all; 12148 12149 ItemMatcher() { 12150 all = true; 12151 } 12152 12153 void build(String name) { 12154 ComponentName componentName = ComponentName.unflattenFromString(name); 12155 if (componentName != null) { 12156 if (components == null) { 12157 components = new ArrayList<ComponentName>(); 12158 } 12159 components.add(componentName); 12160 all = false; 12161 } else { 12162 int objectId = 0; 12163 // Not a '/' separated full component name; maybe an object ID? 12164 try { 12165 objectId = Integer.parseInt(name, 16); 12166 if (objects == null) { 12167 objects = new ArrayList<Integer>(); 12168 } 12169 objects.add(objectId); 12170 all = false; 12171 } catch (RuntimeException e) { 12172 // Not an integer; just do string match. 12173 if (strings == null) { 12174 strings = new ArrayList<String>(); 12175 } 12176 strings.add(name); 12177 all = false; 12178 } 12179 } 12180 } 12181 12182 int build(String[] args, int opti) { 12183 for (; opti<args.length; opti++) { 12184 String name = args[opti]; 12185 if ("--".equals(name)) { 12186 return opti+1; 12187 } 12188 build(name); 12189 } 12190 return opti; 12191 } 12192 12193 boolean match(Object object, ComponentName comp) { 12194 if (all) { 12195 return true; 12196 } 12197 if (components != null) { 12198 for (int i=0; i<components.size(); i++) { 12199 if (components.get(i).equals(comp)) { 12200 return true; 12201 } 12202 } 12203 } 12204 if (objects != null) { 12205 for (int i=0; i<objects.size(); i++) { 12206 if (System.identityHashCode(object) == objects.get(i)) { 12207 return true; 12208 } 12209 } 12210 } 12211 if (strings != null) { 12212 String flat = comp.flattenToString(); 12213 for (int i=0; i<strings.size(); i++) { 12214 if (flat.contains(strings.get(i))) { 12215 return true; 12216 } 12217 } 12218 } 12219 return false; 12220 } 12221 } 12222 12223 /** 12224 * There are three things that cmd can be: 12225 * - a flattened component name that matches an existing activity 12226 * - the cmd arg isn't the flattened component name of an existing activity: 12227 * dump all activity whose component contains the cmd as a substring 12228 * - A hex number of the ActivityRecord object instance. 12229 */ 12230 protected boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name, String[] args, 12231 int opti, boolean dumpAll) { 12232 ArrayList<ActivityRecord> activities; 12233 12234 synchronized (this) { 12235 activities = mStackSupervisor.getDumpActivitiesLocked(name); 12236 } 12237 12238 if (activities.size() <= 0) { 12239 return false; 12240 } 12241 12242 String[] newArgs = new String[args.length - opti]; 12243 System.arraycopy(args, opti, newArgs, 0, args.length - opti); 12244 12245 TaskRecord lastTask = null; 12246 boolean needSep = false; 12247 for (int i=activities.size()-1; i>=0; i--) { 12248 ActivityRecord r = activities.get(i); 12249 if (needSep) { 12250 pw.println(); 12251 } 12252 needSep = true; 12253 synchronized (this) { 12254 if (lastTask != r.task) { 12255 lastTask = r.task; 12256 pw.print("TASK "); pw.print(lastTask.affinity); 12257 pw.print(" id="); pw.println(lastTask.taskId); 12258 if (dumpAll) { 12259 lastTask.dump(pw, " "); 12260 } 12261 } 12262 } 12263 dumpActivity(" ", fd, pw, activities.get(i), newArgs, dumpAll); 12264 } 12265 return true; 12266 } 12267 12268 /** 12269 * Invokes IApplicationThread.dumpActivity() on the thread of the specified activity if 12270 * there is a thread associated with the activity. 12271 */ 12272 private void dumpActivity(String prefix, FileDescriptor fd, PrintWriter pw, 12273 final ActivityRecord r, String[] args, boolean dumpAll) { 12274 String innerPrefix = prefix + " "; 12275 synchronized (this) { 12276 pw.print(prefix); pw.print("ACTIVITY "); pw.print(r.shortComponentName); 12277 pw.print(" "); pw.print(Integer.toHexString(System.identityHashCode(r))); 12278 pw.print(" pid="); 12279 if (r.app != null) pw.println(r.app.pid); 12280 else pw.println("(not running)"); 12281 if (dumpAll) { 12282 r.dump(pw, innerPrefix); 12283 } 12284 } 12285 if (r.app != null && r.app.thread != null) { 12286 // flush anything that is already in the PrintWriter since the thread is going 12287 // to write to the file descriptor directly 12288 pw.flush(); 12289 try { 12290 TransferPipe tp = new TransferPipe(); 12291 try { 12292 r.app.thread.dumpActivity(tp.getWriteFd().getFileDescriptor(), 12293 r.appToken, innerPrefix, args); 12294 tp.go(fd); 12295 } finally { 12296 tp.kill(); 12297 } 12298 } catch (IOException e) { 12299 pw.println(innerPrefix + "Failure while dumping the activity: " + e); 12300 } catch (RemoteException e) { 12301 pw.println(innerPrefix + "Got a RemoteException while dumping the activity"); 12302 } 12303 } 12304 } 12305 12306 void dumpBroadcastsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12307 int opti, boolean dumpAll, String dumpPackage) { 12308 boolean needSep = false; 12309 boolean onlyHistory = false; 12310 boolean printedAnything = false; 12311 12312 if ("history".equals(dumpPackage)) { 12313 if (opti < args.length && "-s".equals(args[opti])) { 12314 dumpAll = false; 12315 } 12316 onlyHistory = true; 12317 dumpPackage = null; 12318 } 12319 12320 pw.println("ACTIVITY MANAGER BROADCAST STATE (dumpsys activity broadcasts)"); 12321 if (!onlyHistory && dumpAll) { 12322 if (mRegisteredReceivers.size() > 0) { 12323 boolean printed = false; 12324 Iterator it = mRegisteredReceivers.values().iterator(); 12325 while (it.hasNext()) { 12326 ReceiverList r = (ReceiverList)it.next(); 12327 if (dumpPackage != null && (r.app == null || 12328 !dumpPackage.equals(r.app.info.packageName))) { 12329 continue; 12330 } 12331 if (!printed) { 12332 pw.println(" Registered Receivers:"); 12333 needSep = true; 12334 printed = true; 12335 printedAnything = true; 12336 } 12337 pw.print(" * "); pw.println(r); 12338 r.dump(pw, " "); 12339 } 12340 } 12341 12342 if (mReceiverResolver.dump(pw, needSep ? 12343 "\n Receiver Resolver Table:" : " Receiver Resolver Table:", 12344 " ", dumpPackage, false)) { 12345 needSep = true; 12346 printedAnything = true; 12347 } 12348 } 12349 12350 for (BroadcastQueue q : mBroadcastQueues) { 12351 needSep = q.dumpLocked(fd, pw, args, opti, dumpAll, dumpPackage, needSep); 12352 printedAnything |= needSep; 12353 } 12354 12355 needSep = true; 12356 12357 if (!onlyHistory && mStickyBroadcasts != null && dumpPackage == null) { 12358 for (int user=0; user<mStickyBroadcasts.size(); user++) { 12359 if (needSep) { 12360 pw.println(); 12361 } 12362 needSep = true; 12363 printedAnything = true; 12364 pw.print(" Sticky broadcasts for user "); 12365 pw.print(mStickyBroadcasts.keyAt(user)); pw.println(":"); 12366 StringBuilder sb = new StringBuilder(128); 12367 for (Map.Entry<String, ArrayList<Intent>> ent 12368 : mStickyBroadcasts.valueAt(user).entrySet()) { 12369 pw.print(" * Sticky action "); pw.print(ent.getKey()); 12370 if (dumpAll) { 12371 pw.println(":"); 12372 ArrayList<Intent> intents = ent.getValue(); 12373 final int N = intents.size(); 12374 for (int i=0; i<N; i++) { 12375 sb.setLength(0); 12376 sb.append(" Intent: "); 12377 intents.get(i).toShortString(sb, false, true, false, false); 12378 pw.println(sb.toString()); 12379 Bundle bundle = intents.get(i).getExtras(); 12380 if (bundle != null) { 12381 pw.print(" "); 12382 pw.println(bundle.toString()); 12383 } 12384 } 12385 } else { 12386 pw.println(""); 12387 } 12388 } 12389 } 12390 } 12391 12392 if (!onlyHistory && dumpAll) { 12393 pw.println(); 12394 for (BroadcastQueue queue : mBroadcastQueues) { 12395 pw.println(" mBroadcastsScheduled [" + queue.mQueueName + "]=" 12396 + queue.mBroadcastsScheduled); 12397 } 12398 pw.println(" mHandler:"); 12399 mHandler.dump(new PrintWriterPrinter(pw), " "); 12400 needSep = true; 12401 printedAnything = true; 12402 } 12403 12404 if (!printedAnything) { 12405 pw.println(" (nothing)"); 12406 } 12407 } 12408 12409 void dumpProvidersLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12410 int opti, boolean dumpAll, String dumpPackage) { 12411 boolean needSep; 12412 boolean printedAnything = false; 12413 12414 ItemMatcher matcher = new ItemMatcher(); 12415 matcher.build(args, opti); 12416 12417 pw.println("ACTIVITY MANAGER CONTENT PROVIDERS (dumpsys activity providers)"); 12418 12419 needSep = mProviderMap.dumpProvidersLocked(pw, dumpAll, dumpPackage); 12420 printedAnything |= needSep; 12421 12422 if (mLaunchingProviders.size() > 0) { 12423 boolean printed = false; 12424 for (int i=mLaunchingProviders.size()-1; i>=0; i--) { 12425 ContentProviderRecord r = mLaunchingProviders.get(i); 12426 if (dumpPackage != null && !dumpPackage.equals(r.name.getPackageName())) { 12427 continue; 12428 } 12429 if (!printed) { 12430 if (needSep) pw.println(); 12431 needSep = true; 12432 pw.println(" Launching content providers:"); 12433 printed = true; 12434 printedAnything = true; 12435 } 12436 pw.print(" Launching #"); pw.print(i); pw.print(": "); 12437 pw.println(r); 12438 } 12439 } 12440 12441 if (mGrantedUriPermissions.size() > 0) { 12442 boolean printed = false; 12443 int dumpUid = -2; 12444 if (dumpPackage != null) { 12445 try { 12446 dumpUid = mContext.getPackageManager().getPackageUid(dumpPackage, 0); 12447 } catch (NameNotFoundException e) { 12448 dumpUid = -1; 12449 } 12450 } 12451 for (int i=0; i<mGrantedUriPermissions.size(); i++) { 12452 int uid = mGrantedUriPermissions.keyAt(i); 12453 if (dumpUid >= -1 && UserHandle.getAppId(uid) != dumpUid) { 12454 continue; 12455 } 12456 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 12457 if (!printed) { 12458 if (needSep) pw.println(); 12459 needSep = true; 12460 pw.println(" Granted Uri Permissions:"); 12461 printed = true; 12462 printedAnything = true; 12463 } 12464 pw.print(" * UID "); pw.print(uid); pw.println(" holds:"); 12465 for (UriPermission perm : perms.values()) { 12466 pw.print(" "); pw.println(perm); 12467 if (dumpAll) { 12468 perm.dump(pw, " "); 12469 } 12470 } 12471 } 12472 } 12473 12474 if (!printedAnything) { 12475 pw.println(" (nothing)"); 12476 } 12477 } 12478 12479 void dumpPendingIntentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 12480 int opti, boolean dumpAll, String dumpPackage) { 12481 boolean printed = false; 12482 12483 pw.println("ACTIVITY MANAGER PENDING INTENTS (dumpsys activity intents)"); 12484 12485 if (mIntentSenderRecords.size() > 0) { 12486 Iterator<WeakReference<PendingIntentRecord>> it 12487 = mIntentSenderRecords.values().iterator(); 12488 while (it.hasNext()) { 12489 WeakReference<PendingIntentRecord> ref = it.next(); 12490 PendingIntentRecord rec = ref != null ? ref.get(): null; 12491 if (dumpPackage != null && (rec == null 12492 || !dumpPackage.equals(rec.key.packageName))) { 12493 continue; 12494 } 12495 printed = true; 12496 if (rec != null) { 12497 pw.print(" * "); pw.println(rec); 12498 if (dumpAll) { 12499 rec.dump(pw, " "); 12500 } 12501 } else { 12502 pw.print(" * "); pw.println(ref); 12503 } 12504 } 12505 } 12506 12507 if (!printed) { 12508 pw.println(" (nothing)"); 12509 } 12510 } 12511 12512 private static final int dumpProcessList(PrintWriter pw, 12513 ActivityManagerService service, List list, 12514 String prefix, String normalLabel, String persistentLabel, 12515 String dumpPackage) { 12516 int numPers = 0; 12517 final int N = list.size()-1; 12518 for (int i=N; i>=0; i--) { 12519 ProcessRecord r = (ProcessRecord)list.get(i); 12520 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 12521 continue; 12522 } 12523 pw.println(String.format("%s%s #%2d: %s", 12524 prefix, (r.persistent ? persistentLabel : normalLabel), 12525 i, r.toString())); 12526 if (r.persistent) { 12527 numPers++; 12528 } 12529 } 12530 return numPers; 12531 } 12532 12533 private static final boolean dumpProcessOomList(PrintWriter pw, 12534 ActivityManagerService service, List<ProcessRecord> origList, 12535 String prefix, String normalLabel, String persistentLabel, 12536 boolean inclDetails, String dumpPackage) { 12537 12538 ArrayList<Pair<ProcessRecord, Integer>> list 12539 = new ArrayList<Pair<ProcessRecord, Integer>>(origList.size()); 12540 for (int i=0; i<origList.size(); i++) { 12541 ProcessRecord r = origList.get(i); 12542 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 12543 continue; 12544 } 12545 list.add(new Pair<ProcessRecord, Integer>(origList.get(i), i)); 12546 } 12547 12548 if (list.size() <= 0) { 12549 return false; 12550 } 12551 12552 Comparator<Pair<ProcessRecord, Integer>> comparator 12553 = new Comparator<Pair<ProcessRecord, Integer>>() { 12554 @Override 12555 public int compare(Pair<ProcessRecord, Integer> object1, 12556 Pair<ProcessRecord, Integer> object2) { 12557 if (object1.first.setAdj != object2.first.setAdj) { 12558 return object1.first.setAdj > object2.first.setAdj ? -1 : 1; 12559 } 12560 if (object1.second.intValue() != object2.second.intValue()) { 12561 return object1.second.intValue() > object2.second.intValue() ? -1 : 1; 12562 } 12563 return 0; 12564 } 12565 }; 12566 12567 Collections.sort(list, comparator); 12568 12569 final long curRealtime = SystemClock.elapsedRealtime(); 12570 final long realtimeSince = curRealtime - service.mLastPowerCheckRealtime; 12571 final long curUptime = SystemClock.uptimeMillis(); 12572 final long uptimeSince = curUptime - service.mLastPowerCheckUptime; 12573 12574 for (int i=list.size()-1; i>=0; i--) { 12575 ProcessRecord r = list.get(i).first; 12576 String oomAdj = ProcessList.makeOomAdjString(r.setAdj); 12577 char schedGroup; 12578 switch (r.setSchedGroup) { 12579 case Process.THREAD_GROUP_BG_NONINTERACTIVE: 12580 schedGroup = 'B'; 12581 break; 12582 case Process.THREAD_GROUP_DEFAULT: 12583 schedGroup = 'F'; 12584 break; 12585 default: 12586 schedGroup = '?'; 12587 break; 12588 } 12589 char foreground; 12590 if (r.foregroundActivities) { 12591 foreground = 'A'; 12592 } else if (r.foregroundServices) { 12593 foreground = 'S'; 12594 } else { 12595 foreground = ' '; 12596 } 12597 String procState = ProcessList.makeProcStateString(r.curProcState); 12598 pw.print(prefix); 12599 pw.print(r.persistent ? persistentLabel : normalLabel); 12600 pw.print(" #"); 12601 int num = (origList.size()-1)-list.get(i).second; 12602 if (num < 10) pw.print(' '); 12603 pw.print(num); 12604 pw.print(": "); 12605 pw.print(oomAdj); 12606 pw.print(' '); 12607 pw.print(schedGroup); 12608 pw.print('/'); 12609 pw.print(foreground); 12610 pw.print('/'); 12611 pw.print(procState); 12612 pw.print(" trm:"); 12613 if (r.trimMemoryLevel < 10) pw.print(' '); 12614 pw.print(r.trimMemoryLevel); 12615 pw.print(' '); 12616 pw.print(r.toShortString()); 12617 pw.print(" ("); 12618 pw.print(r.adjType); 12619 pw.println(')'); 12620 if (r.adjSource != null || r.adjTarget != null) { 12621 pw.print(prefix); 12622 pw.print(" "); 12623 if (r.adjTarget instanceof ComponentName) { 12624 pw.print(((ComponentName)r.adjTarget).flattenToShortString()); 12625 } else if (r.adjTarget != null) { 12626 pw.print(r.adjTarget.toString()); 12627 } else { 12628 pw.print("{null}"); 12629 } 12630 pw.print("<="); 12631 if (r.adjSource instanceof ProcessRecord) { 12632 pw.print("Proc{"); 12633 pw.print(((ProcessRecord)r.adjSource).toShortString()); 12634 pw.println("}"); 12635 } else if (r.adjSource != null) { 12636 pw.println(r.adjSource.toString()); 12637 } else { 12638 pw.println("{null}"); 12639 } 12640 } 12641 if (inclDetails) { 12642 pw.print(prefix); 12643 pw.print(" "); 12644 pw.print("oom: max="); pw.print(r.maxAdj); 12645 pw.print(" curRaw="); pw.print(r.curRawAdj); 12646 pw.print(" setRaw="); pw.print(r.setRawAdj); 12647 pw.print(" cur="); pw.print(r.curAdj); 12648 pw.print(" set="); pw.println(r.setAdj); 12649 pw.print(prefix); 12650 pw.print(" "); 12651 pw.print("state: cur="); pw.print(ProcessList.makeProcStateString(r.curProcState)); 12652 pw.print(" set="); pw.print(ProcessList.makeProcStateString(r.setProcState)); 12653 pw.print(" lastPss="); pw.print(r.lastPss); 12654 pw.print(" lastCachedPss="); pw.println(r.lastCachedPss); 12655 pw.print(prefix); 12656 pw.print(" "); 12657 pw.print("cached="); pw.print(r.cached); 12658 pw.print(" empty="); pw.print(r.empty); 12659 pw.print(" hasAboveClient="); pw.println(r.hasAboveClient); 12660 12661 if (r.setProcState >= ActivityManager.PROCESS_STATE_SERVICE) { 12662 if (r.lastWakeTime != 0) { 12663 long wtime; 12664 BatteryStatsImpl stats = service.mBatteryStatsService.getActiveStatistics(); 12665 synchronized (stats) { 12666 wtime = stats.getProcessWakeTime(r.info.uid, 12667 r.pid, curRealtime); 12668 } 12669 long timeUsed = wtime - r.lastWakeTime; 12670 pw.print(prefix); 12671 pw.print(" "); 12672 pw.print("keep awake over "); 12673 TimeUtils.formatDuration(realtimeSince, pw); 12674 pw.print(" used "); 12675 TimeUtils.formatDuration(timeUsed, pw); 12676 pw.print(" ("); 12677 pw.print((timeUsed*100)/realtimeSince); 12678 pw.println("%)"); 12679 } 12680 if (r.lastCpuTime != 0) { 12681 long timeUsed = r.curCpuTime - r.lastCpuTime; 12682 pw.print(prefix); 12683 pw.print(" "); 12684 pw.print("run cpu over "); 12685 TimeUtils.formatDuration(uptimeSince, pw); 12686 pw.print(" used "); 12687 TimeUtils.formatDuration(timeUsed, pw); 12688 pw.print(" ("); 12689 pw.print((timeUsed*100)/uptimeSince); 12690 pw.println("%)"); 12691 } 12692 } 12693 } 12694 } 12695 return true; 12696 } 12697 12698 ArrayList<ProcessRecord> collectProcesses(PrintWriter pw, int start, String[] args) { 12699 ArrayList<ProcessRecord> procs; 12700 synchronized (this) { 12701 if (args != null && args.length > start 12702 && args[start].charAt(0) != '-') { 12703 procs = new ArrayList<ProcessRecord>(); 12704 int pid = -1; 12705 try { 12706 pid = Integer.parseInt(args[start]); 12707 } catch (NumberFormatException e) { 12708 } 12709 for (int i=mLruProcesses.size()-1; i>=0; i--) { 12710 ProcessRecord proc = mLruProcesses.get(i); 12711 if (proc.pid == pid) { 12712 procs.add(proc); 12713 } else if (proc.processName.equals(args[start])) { 12714 procs.add(proc); 12715 } 12716 } 12717 if (procs.size() <= 0) { 12718 return null; 12719 } 12720 } else { 12721 procs = new ArrayList<ProcessRecord>(mLruProcesses); 12722 } 12723 } 12724 return procs; 12725 } 12726 12727 final void dumpGraphicsHardwareUsage(FileDescriptor fd, 12728 PrintWriter pw, String[] args) { 12729 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 12730 if (procs == null) { 12731 pw.println("No process found for: " + args[0]); 12732 return; 12733 } 12734 12735 long uptime = SystemClock.uptimeMillis(); 12736 long realtime = SystemClock.elapsedRealtime(); 12737 pw.println("Applications Graphics Acceleration Info:"); 12738 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 12739 12740 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12741 ProcessRecord r = procs.get(i); 12742 if (r.thread != null) { 12743 pw.println("\n** Graphics info for pid " + r.pid + " [" + r.processName + "] **"); 12744 pw.flush(); 12745 try { 12746 TransferPipe tp = new TransferPipe(); 12747 try { 12748 r.thread.dumpGfxInfo(tp.getWriteFd().getFileDescriptor(), args); 12749 tp.go(fd); 12750 } finally { 12751 tp.kill(); 12752 } 12753 } catch (IOException e) { 12754 pw.println("Failure while dumping the app: " + r); 12755 pw.flush(); 12756 } catch (RemoteException e) { 12757 pw.println("Got a RemoteException while dumping the app " + r); 12758 pw.flush(); 12759 } 12760 } 12761 } 12762 } 12763 12764 final void dumpDbInfo(FileDescriptor fd, PrintWriter pw, String[] args) { 12765 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 12766 if (procs == null) { 12767 pw.println("No process found for: " + args[0]); 12768 return; 12769 } 12770 12771 pw.println("Applications Database Info:"); 12772 12773 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12774 ProcessRecord r = procs.get(i); 12775 if (r.thread != null) { 12776 pw.println("\n** Database info for pid " + r.pid + " [" + r.processName + "] **"); 12777 pw.flush(); 12778 try { 12779 TransferPipe tp = new TransferPipe(); 12780 try { 12781 r.thread.dumpDbInfo(tp.getWriteFd().getFileDescriptor(), args); 12782 tp.go(fd); 12783 } finally { 12784 tp.kill(); 12785 } 12786 } catch (IOException e) { 12787 pw.println("Failure while dumping the app: " + r); 12788 pw.flush(); 12789 } catch (RemoteException e) { 12790 pw.println("Got a RemoteException while dumping the app " + r); 12791 pw.flush(); 12792 } 12793 } 12794 } 12795 } 12796 12797 final static class MemItem { 12798 final boolean isProc; 12799 final String label; 12800 final String shortLabel; 12801 final long pss; 12802 final int id; 12803 final boolean hasActivities; 12804 ArrayList<MemItem> subitems; 12805 12806 public MemItem(String _label, String _shortLabel, long _pss, int _id, 12807 boolean _hasActivities) { 12808 isProc = true; 12809 label = _label; 12810 shortLabel = _shortLabel; 12811 pss = _pss; 12812 id = _id; 12813 hasActivities = _hasActivities; 12814 } 12815 12816 public MemItem(String _label, String _shortLabel, long _pss, int _id) { 12817 isProc = false; 12818 label = _label; 12819 shortLabel = _shortLabel; 12820 pss = _pss; 12821 id = _id; 12822 hasActivities = false; 12823 } 12824 } 12825 12826 static final void dumpMemItems(PrintWriter pw, String prefix, String tag, 12827 ArrayList<MemItem> items, boolean sort, boolean isCompact) { 12828 if (sort && !isCompact) { 12829 Collections.sort(items, new Comparator<MemItem>() { 12830 @Override 12831 public int compare(MemItem lhs, MemItem rhs) { 12832 if (lhs.pss < rhs.pss) { 12833 return 1; 12834 } else if (lhs.pss > rhs.pss) { 12835 return -1; 12836 } 12837 return 0; 12838 } 12839 }); 12840 } 12841 12842 for (int i=0; i<items.size(); i++) { 12843 MemItem mi = items.get(i); 12844 if (!isCompact) { 12845 pw.print(prefix); pw.printf("%7d kB: ", mi.pss); pw.println(mi.label); 12846 } else if (mi.isProc) { 12847 pw.print("proc,"); pw.print(tag); pw.print(","); pw.print(mi.shortLabel); 12848 pw.print(","); pw.print(mi.id); pw.print(","); pw.print(mi.pss); 12849 pw.println(mi.hasActivities ? ",a" : ",e"); 12850 } else { 12851 pw.print(tag); pw.print(","); pw.print(mi.shortLabel); pw.print(","); 12852 pw.println(mi.pss); 12853 } 12854 if (mi.subitems != null) { 12855 dumpMemItems(pw, prefix + " ", mi.shortLabel, mi.subitems, 12856 true, isCompact); 12857 } 12858 } 12859 } 12860 12861 // These are in KB. 12862 static final long[] DUMP_MEM_BUCKETS = new long[] { 12863 5*1024, 7*1024, 10*1024, 15*1024, 20*1024, 30*1024, 40*1024, 80*1024, 12864 120*1024, 160*1024, 200*1024, 12865 250*1024, 300*1024, 350*1024, 400*1024, 500*1024, 600*1024, 800*1024, 12866 1*1024*1024, 2*1024*1024, 5*1024*1024, 10*1024*1024, 20*1024*1024 12867 }; 12868 12869 static final void appendMemBucket(StringBuilder out, long memKB, String label, 12870 boolean stackLike) { 12871 int start = label.lastIndexOf('.'); 12872 if (start >= 0) start++; 12873 else start = 0; 12874 int end = label.length(); 12875 for (int i=0; i<DUMP_MEM_BUCKETS.length; i++) { 12876 if (DUMP_MEM_BUCKETS[i] >= memKB) { 12877 long bucket = DUMP_MEM_BUCKETS[i]/1024; 12878 out.append(bucket); 12879 out.append(stackLike ? "MB." : "MB "); 12880 out.append(label, start, end); 12881 return; 12882 } 12883 } 12884 out.append(memKB/1024); 12885 out.append(stackLike ? "MB." : "MB "); 12886 out.append(label, start, end); 12887 } 12888 12889 static final int[] DUMP_MEM_OOM_ADJ = new int[] { 12890 ProcessList.NATIVE_ADJ, 12891 ProcessList.SYSTEM_ADJ, ProcessList.PERSISTENT_PROC_ADJ, ProcessList.FOREGROUND_APP_ADJ, 12892 ProcessList.VISIBLE_APP_ADJ, ProcessList.PERCEPTIBLE_APP_ADJ, 12893 ProcessList.BACKUP_APP_ADJ, ProcessList.HEAVY_WEIGHT_APP_ADJ, 12894 ProcessList.SERVICE_ADJ, ProcessList.HOME_APP_ADJ, 12895 ProcessList.PREVIOUS_APP_ADJ, ProcessList.SERVICE_B_ADJ, ProcessList.CACHED_APP_MAX_ADJ 12896 }; 12897 static final String[] DUMP_MEM_OOM_LABEL = new String[] { 12898 "Native", 12899 "System", "Persistent", "Foreground", 12900 "Visible", "Perceptible", 12901 "Heavy Weight", "Backup", 12902 "A Services", "Home", 12903 "Previous", "B Services", "Cached" 12904 }; 12905 static final String[] DUMP_MEM_OOM_COMPACT_LABEL = new String[] { 12906 "native", 12907 "sys", "pers", "fore", 12908 "vis", "percept", 12909 "heavy", "backup", 12910 "servicea", "home", 12911 "prev", "serviceb", "cached" 12912 }; 12913 12914 private final void dumpApplicationMemoryUsageHeader(PrintWriter pw, long uptime, 12915 long realtime, boolean isCheckinRequest, boolean isCompact) { 12916 if (isCheckinRequest || isCompact) { 12917 // short checkin version 12918 pw.print("time,"); pw.print(uptime); pw.print(","); pw.println(realtime); 12919 } else { 12920 pw.println("Applications Memory Usage (kB):"); 12921 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 12922 } 12923 } 12924 12925 final void dumpApplicationMemoryUsage(FileDescriptor fd, 12926 PrintWriter pw, String prefix, String[] args, boolean brief, PrintWriter categoryPw) { 12927 boolean dumpDetails = false; 12928 boolean dumpFullDetails = false; 12929 boolean dumpDalvik = false; 12930 boolean oomOnly = false; 12931 boolean isCompact = false; 12932 boolean localOnly = false; 12933 12934 int opti = 0; 12935 while (opti < args.length) { 12936 String opt = args[opti]; 12937 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 12938 break; 12939 } 12940 opti++; 12941 if ("-a".equals(opt)) { 12942 dumpDetails = true; 12943 dumpFullDetails = true; 12944 dumpDalvik = true; 12945 } else if ("-d".equals(opt)) { 12946 dumpDalvik = true; 12947 } else if ("-c".equals(opt)) { 12948 isCompact = true; 12949 } else if ("--oom".equals(opt)) { 12950 oomOnly = true; 12951 } else if ("--local".equals(opt)) { 12952 localOnly = true; 12953 } else if ("-h".equals(opt)) { 12954 pw.println("meminfo dump options: [-a] [-d] [-c] [--oom] [process]"); 12955 pw.println(" -a: include all available information for each process."); 12956 pw.println(" -d: include dalvik details when dumping process details."); 12957 pw.println(" -c: dump in a compact machine-parseable representation."); 12958 pw.println(" --oom: only show processes organized by oom adj."); 12959 pw.println(" --local: only collect details locally, don't call process."); 12960 pw.println("If [process] is specified it can be the name or "); 12961 pw.println("pid of a specific process to dump."); 12962 return; 12963 } else { 12964 pw.println("Unknown argument: " + opt + "; use -h for help"); 12965 } 12966 } 12967 12968 final boolean isCheckinRequest = scanArgs(args, "--checkin"); 12969 long uptime = SystemClock.uptimeMillis(); 12970 long realtime = SystemClock.elapsedRealtime(); 12971 final long[] tmpLong = new long[1]; 12972 12973 ArrayList<ProcessRecord> procs = collectProcesses(pw, opti, args); 12974 if (procs == null) { 12975 // No Java processes. Maybe they want to print a native process. 12976 if (args != null && args.length > opti 12977 && args[opti].charAt(0) != '-') { 12978 ArrayList<ProcessCpuTracker.Stats> nativeProcs 12979 = new ArrayList<ProcessCpuTracker.Stats>(); 12980 updateCpuStatsNow(); 12981 int findPid = -1; 12982 try { 12983 findPid = Integer.parseInt(args[opti]); 12984 } catch (NumberFormatException e) { 12985 } 12986 synchronized (mProcessCpuThread) { 12987 final int N = mProcessCpuTracker.countStats(); 12988 for (int i=0; i<N; i++) { 12989 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 12990 if (st.pid == findPid || (st.baseName != null 12991 && st.baseName.equals(args[opti]))) { 12992 nativeProcs.add(st); 12993 } 12994 } 12995 } 12996 if (nativeProcs.size() > 0) { 12997 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, 12998 isCompact); 12999 Debug.MemoryInfo mi = null; 13000 for (int i = nativeProcs.size() - 1 ; i >= 0 ; i--) { 13001 final ProcessCpuTracker.Stats r = nativeProcs.get(i); 13002 final int pid = r.pid; 13003 if (!isCheckinRequest && dumpDetails) { 13004 pw.println("\n** MEMINFO in pid " + pid + " [" + r.baseName + "] **"); 13005 } 13006 if (mi == null) { 13007 mi = new Debug.MemoryInfo(); 13008 } 13009 if (dumpDetails || (!brief && !oomOnly)) { 13010 Debug.getMemoryInfo(pid, mi); 13011 } else { 13012 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 13013 mi.dalvikPrivateDirty = (int)tmpLong[0]; 13014 } 13015 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 13016 dumpDalvik, pid, r.baseName, 0, 0, 0, 0, 0, 0); 13017 if (isCheckinRequest) { 13018 pw.println(); 13019 } 13020 } 13021 return; 13022 } 13023 } 13024 pw.println("No process found for: " + args[opti]); 13025 return; 13026 } 13027 13028 if (!brief && !oomOnly && (procs.size() == 1 || isCheckinRequest)) { 13029 dumpDetails = true; 13030 } 13031 13032 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, isCompact); 13033 13034 String[] innerArgs = new String[args.length-opti]; 13035 System.arraycopy(args, opti, innerArgs, 0, args.length-opti); 13036 13037 ArrayList<MemItem> procMems = new ArrayList<MemItem>(); 13038 final SparseArray<MemItem> procMemsMap = new SparseArray<MemItem>(); 13039 long nativePss=0, dalvikPss=0, otherPss=0; 13040 long[] miscPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 13041 13042 long oomPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 13043 ArrayList<MemItem>[] oomProcs = (ArrayList<MemItem>[]) 13044 new ArrayList[DUMP_MEM_OOM_LABEL.length]; 13045 13046 long totalPss = 0; 13047 long cachedPss = 0; 13048 13049 Debug.MemoryInfo mi = null; 13050 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 13051 final ProcessRecord r = procs.get(i); 13052 final IApplicationThread thread; 13053 final int pid; 13054 final int oomAdj; 13055 final boolean hasActivities; 13056 synchronized (this) { 13057 thread = r.thread; 13058 pid = r.pid; 13059 oomAdj = r.getSetAdjWithServices(); 13060 hasActivities = r.activities.size() > 0; 13061 } 13062 if (thread != null) { 13063 if (!isCheckinRequest && dumpDetails) { 13064 pw.println("\n** MEMINFO in pid " + pid + " [" + r.processName + "] **"); 13065 } 13066 if (mi == null) { 13067 mi = new Debug.MemoryInfo(); 13068 } 13069 if (dumpDetails || (!brief && !oomOnly)) { 13070 Debug.getMemoryInfo(pid, mi); 13071 } else { 13072 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 13073 mi.dalvikPrivateDirty = (int)tmpLong[0]; 13074 } 13075 if (dumpDetails) { 13076 if (localOnly) { 13077 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 13078 dumpDalvik, pid, r.processName, 0, 0, 0, 0, 0, 0); 13079 if (isCheckinRequest) { 13080 pw.println(); 13081 } 13082 } else { 13083 try { 13084 pw.flush(); 13085 thread.dumpMemInfo(fd, mi, isCheckinRequest, dumpFullDetails, 13086 dumpDalvik, innerArgs); 13087 } catch (RemoteException e) { 13088 if (!isCheckinRequest) { 13089 pw.println("Got RemoteException!"); 13090 pw.flush(); 13091 } 13092 } 13093 } 13094 } 13095 13096 final long myTotalPss = mi.getTotalPss(); 13097 final long myTotalUss = mi.getTotalUss(); 13098 13099 synchronized (this) { 13100 if (r.thread != null && oomAdj == r.getSetAdjWithServices()) { 13101 // Record this for posterity if the process has been stable. 13102 r.baseProcessTracker.addPss(myTotalPss, myTotalUss, true, r.pkgList); 13103 } 13104 } 13105 13106 if (!isCheckinRequest && mi != null) { 13107 totalPss += myTotalPss; 13108 MemItem pssItem = new MemItem(r.processName + " (pid " + pid + 13109 (hasActivities ? " / activities)" : ")"), 13110 r.processName, myTotalPss, pid, hasActivities); 13111 procMems.add(pssItem); 13112 procMemsMap.put(pid, pssItem); 13113 13114 nativePss += mi.nativePss; 13115 dalvikPss += mi.dalvikPss; 13116 otherPss += mi.otherPss; 13117 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 13118 long mem = mi.getOtherPss(j); 13119 miscPss[j] += mem; 13120 otherPss -= mem; 13121 } 13122 13123 if (oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 13124 cachedPss += myTotalPss; 13125 } 13126 13127 for (int oomIndex=0; oomIndex<oomPss.length; oomIndex++) { 13128 if (oomAdj <= DUMP_MEM_OOM_ADJ[oomIndex] 13129 || oomIndex == (oomPss.length-1)) { 13130 oomPss[oomIndex] += myTotalPss; 13131 if (oomProcs[oomIndex] == null) { 13132 oomProcs[oomIndex] = new ArrayList<MemItem>(); 13133 } 13134 oomProcs[oomIndex].add(pssItem); 13135 break; 13136 } 13137 } 13138 } 13139 } 13140 } 13141 13142 long nativeProcTotalPss = 0; 13143 13144 if (!isCheckinRequest && procs.size() > 1) { 13145 // If we are showing aggregations, also look for native processes to 13146 // include so that our aggregations are more accurate. 13147 updateCpuStatsNow(); 13148 synchronized (mProcessCpuThread) { 13149 final int N = mProcessCpuTracker.countStats(); 13150 for (int i=0; i<N; i++) { 13151 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 13152 if (st.vsize > 0 && procMemsMap.indexOfKey(st.pid) < 0) { 13153 if (mi == null) { 13154 mi = new Debug.MemoryInfo(); 13155 } 13156 if (!brief && !oomOnly) { 13157 Debug.getMemoryInfo(st.pid, mi); 13158 } else { 13159 mi.nativePss = (int)Debug.getPss(st.pid, tmpLong); 13160 mi.nativePrivateDirty = (int)tmpLong[0]; 13161 } 13162 13163 final long myTotalPss = mi.getTotalPss(); 13164 totalPss += myTotalPss; 13165 nativeProcTotalPss += myTotalPss; 13166 13167 MemItem pssItem = new MemItem(st.name + " (pid " + st.pid + ")", 13168 st.name, myTotalPss, st.pid, false); 13169 procMems.add(pssItem); 13170 13171 nativePss += mi.nativePss; 13172 dalvikPss += mi.dalvikPss; 13173 otherPss += mi.otherPss; 13174 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 13175 long mem = mi.getOtherPss(j); 13176 miscPss[j] += mem; 13177 otherPss -= mem; 13178 } 13179 oomPss[0] += myTotalPss; 13180 if (oomProcs[0] == null) { 13181 oomProcs[0] = new ArrayList<MemItem>(); 13182 } 13183 oomProcs[0].add(pssItem); 13184 } 13185 } 13186 } 13187 13188 ArrayList<MemItem> catMems = new ArrayList<MemItem>(); 13189 13190 catMems.add(new MemItem("Native", "Native", nativePss, -1)); 13191 catMems.add(new MemItem("Dalvik", "Dalvik", dalvikPss, -2)); 13192 catMems.add(new MemItem("Unknown", "Unknown", otherPss, -3)); 13193 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 13194 String label = Debug.MemoryInfo.getOtherLabel(j); 13195 catMems.add(new MemItem(label, label, miscPss[j], j)); 13196 } 13197 13198 ArrayList<MemItem> oomMems = new ArrayList<MemItem>(); 13199 for (int j=0; j<oomPss.length; j++) { 13200 if (oomPss[j] != 0) { 13201 String label = isCompact ? DUMP_MEM_OOM_COMPACT_LABEL[j] 13202 : DUMP_MEM_OOM_LABEL[j]; 13203 MemItem item = new MemItem(label, label, oomPss[j], 13204 DUMP_MEM_OOM_ADJ[j]); 13205 item.subitems = oomProcs[j]; 13206 oomMems.add(item); 13207 } 13208 } 13209 13210 if (!brief && !oomOnly && !isCompact) { 13211 pw.println(); 13212 pw.println("Total PSS by process:"); 13213 dumpMemItems(pw, " ", "proc", procMems, true, isCompact); 13214 pw.println(); 13215 } 13216 if (!isCompact) { 13217 pw.println("Total PSS by OOM adjustment:"); 13218 } 13219 dumpMemItems(pw, " ", "oom", oomMems, false, isCompact); 13220 if (!brief && !oomOnly) { 13221 PrintWriter out = categoryPw != null ? categoryPw : pw; 13222 if (!isCompact) { 13223 out.println(); 13224 out.println("Total PSS by category:"); 13225 } 13226 dumpMemItems(out, " ", "cat", catMems, true, isCompact); 13227 } 13228 if (!isCompact) { 13229 pw.println(); 13230 } 13231 MemInfoReader memInfo = new MemInfoReader(); 13232 memInfo.readMemInfo(); 13233 if (nativeProcTotalPss > 0) { 13234 synchronized (this) { 13235 mProcessStats.addSysMemUsageLocked(memInfo.getCachedSizeKb(), 13236 memInfo.getFreeSizeKb(), memInfo.getZramTotalSizeKb(), 13237 memInfo.getBuffersSizeKb()+memInfo.getShmemSizeKb()+memInfo.getSlabSizeKb(), 13238 nativeProcTotalPss); 13239 } 13240 } 13241 if (!brief) { 13242 if (!isCompact) { 13243 pw.print("Total RAM: "); pw.print(memInfo.getTotalSizeKb()); 13244 pw.print(" kB (status "); 13245 switch (mLastMemoryLevel) { 13246 case ProcessStats.ADJ_MEM_FACTOR_NORMAL: 13247 pw.println("normal)"); 13248 break; 13249 case ProcessStats.ADJ_MEM_FACTOR_MODERATE: 13250 pw.println("moderate)"); 13251 break; 13252 case ProcessStats.ADJ_MEM_FACTOR_LOW: 13253 pw.println("low)"); 13254 break; 13255 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 13256 pw.println("critical)"); 13257 break; 13258 default: 13259 pw.print(mLastMemoryLevel); 13260 pw.println(")"); 13261 break; 13262 } 13263 pw.print(" Free RAM: "); pw.print(cachedPss + memInfo.getCachedSizeKb() 13264 + memInfo.getFreeSizeKb()); pw.print(" kB ("); 13265 pw.print(cachedPss); pw.print(" cached pss + "); 13266 pw.print(memInfo.getCachedSizeKb()); pw.print(" cached + "); 13267 pw.print(memInfo.getFreeSizeKb()); pw.println(" free)"); 13268 } else { 13269 pw.print("ram,"); pw.print(memInfo.getTotalSizeKb()); pw.print(","); 13270 pw.print(cachedPss + memInfo.getCachedSizeKb() 13271 + memInfo.getFreeSizeKb()); pw.print(","); 13272 pw.println(totalPss - cachedPss); 13273 } 13274 } 13275 if (!isCompact) { 13276 pw.print(" Used RAM: "); pw.print(totalPss - cachedPss 13277 + memInfo.getBuffersSizeKb() + memInfo.getShmemSizeKb() 13278 + memInfo.getSlabSizeKb()); pw.print(" kB ("); 13279 pw.print(totalPss - cachedPss); pw.print(" used pss + "); 13280 pw.print(memInfo.getBuffersSizeKb()); pw.print(" buffers + "); 13281 pw.print(memInfo.getShmemSizeKb()); pw.print(" shmem + "); 13282 pw.print(memInfo.getSlabSizeKb()); pw.println(" slab)"); 13283 pw.print(" Lost RAM: "); pw.print(memInfo.getTotalSizeKb() 13284 - totalPss - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 13285 - memInfo.getBuffersSizeKb() - memInfo.getShmemSizeKb() 13286 - memInfo.getSlabSizeKb()); pw.println(" kB"); 13287 } 13288 if (!brief) { 13289 if (memInfo.getZramTotalSizeKb() != 0) { 13290 if (!isCompact) { 13291 pw.print(" ZRAM: "); pw.print(memInfo.getZramTotalSizeKb()); 13292 pw.print(" kB physical used for "); 13293 pw.print(memInfo.getSwapTotalSizeKb() 13294 - memInfo.getSwapFreeSizeKb()); 13295 pw.print(" kB in swap ("); 13296 pw.print(memInfo.getSwapTotalSizeKb()); 13297 pw.println(" kB total swap)"); 13298 } else { 13299 pw.print("zram,"); pw.print(memInfo.getZramTotalSizeKb()); pw.print(","); 13300 pw.print(memInfo.getSwapTotalSizeKb()); pw.print(","); 13301 pw.println(memInfo.getSwapFreeSizeKb()); 13302 } 13303 } 13304 final int[] SINGLE_LONG_FORMAT = new int[] { 13305 Process.PROC_SPACE_TERM|Process.PROC_OUT_LONG 13306 }; 13307 long[] longOut = new long[1]; 13308 Process.readProcFile("/sys/kernel/mm/ksm/pages_shared", 13309 SINGLE_LONG_FORMAT, null, longOut, null); 13310 long shared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13311 longOut[0] = 0; 13312 Process.readProcFile("/sys/kernel/mm/ksm/pages_sharing", 13313 SINGLE_LONG_FORMAT, null, longOut, null); 13314 long sharing = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13315 longOut[0] = 0; 13316 Process.readProcFile("/sys/kernel/mm/ksm/pages_unshared", 13317 SINGLE_LONG_FORMAT, null, longOut, null); 13318 long unshared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13319 longOut[0] = 0; 13320 Process.readProcFile("/sys/kernel/mm/ksm/pages_volatile", 13321 SINGLE_LONG_FORMAT, null, longOut, null); 13322 long voltile = longOut[0] * ProcessList.PAGE_SIZE / 1024; 13323 if (!isCompact) { 13324 if (sharing != 0 || shared != 0 || unshared != 0 || voltile != 0) { 13325 pw.print(" KSM: "); pw.print(sharing); 13326 pw.print(" kB saved from shared "); 13327 pw.print(shared); pw.println(" kB"); 13328 pw.print(" "); pw.print(unshared); pw.print(" kB unshared; "); 13329 pw.print(voltile); pw.println(" kB volatile"); 13330 } 13331 pw.print(" Tuning: "); 13332 pw.print(ActivityManager.staticGetMemoryClass()); 13333 pw.print(" (large "); 13334 pw.print(ActivityManager.staticGetLargeMemoryClass()); 13335 pw.print("), oom "); 13336 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 13337 pw.print(" kB"); 13338 pw.print(", restore limit "); 13339 pw.print(mProcessList.getCachedRestoreThresholdKb()); 13340 pw.print(" kB"); 13341 if (ActivityManager.isLowRamDeviceStatic()) { 13342 pw.print(" (low-ram)"); 13343 } 13344 if (ActivityManager.isHighEndGfx()) { 13345 pw.print(" (high-end-gfx)"); 13346 } 13347 pw.println(); 13348 } else { 13349 pw.print("ksm,"); pw.print(sharing); pw.print(","); 13350 pw.print(shared); pw.print(","); pw.print(unshared); pw.print(","); 13351 pw.println(voltile); 13352 pw.print("tuning,"); 13353 pw.print(ActivityManager.staticGetMemoryClass()); 13354 pw.print(','); 13355 pw.print(ActivityManager.staticGetLargeMemoryClass()); 13356 pw.print(','); 13357 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 13358 if (ActivityManager.isLowRamDeviceStatic()) { 13359 pw.print(",low-ram"); 13360 } 13361 if (ActivityManager.isHighEndGfx()) { 13362 pw.print(",high-end-gfx"); 13363 } 13364 pw.println(); 13365 } 13366 } 13367 } 13368 } 13369 13370 /** 13371 * Searches array of arguments for the specified string 13372 * @param args array of argument strings 13373 * @param value value to search for 13374 * @return true if the value is contained in the array 13375 */ 13376 private static boolean scanArgs(String[] args, String value) { 13377 if (args != null) { 13378 for (String arg : args) { 13379 if (value.equals(arg)) { 13380 return true; 13381 } 13382 } 13383 } 13384 return false; 13385 } 13386 13387 private final boolean removeDyingProviderLocked(ProcessRecord proc, 13388 ContentProviderRecord cpr, boolean always) { 13389 final boolean inLaunching = mLaunchingProviders.contains(cpr); 13390 13391 if (!inLaunching || always) { 13392 synchronized (cpr) { 13393 cpr.launchingApp = null; 13394 cpr.notifyAll(); 13395 } 13396 mProviderMap.removeProviderByClass(cpr.name, UserHandle.getUserId(cpr.uid)); 13397 String names[] = cpr.info.authority.split(";"); 13398 for (int j = 0; j < names.length; j++) { 13399 mProviderMap.removeProviderByName(names[j], UserHandle.getUserId(cpr.uid)); 13400 } 13401 } 13402 13403 for (int i=0; i<cpr.connections.size(); i++) { 13404 ContentProviderConnection conn = cpr.connections.get(i); 13405 if (conn.waiting) { 13406 // If this connection is waiting for the provider, then we don't 13407 // need to mess with its process unless we are always removing 13408 // or for some reason the provider is not currently launching. 13409 if (inLaunching && !always) { 13410 continue; 13411 } 13412 } 13413 ProcessRecord capp = conn.client; 13414 conn.dead = true; 13415 if (conn.stableCount > 0) { 13416 if (!capp.persistent && capp.thread != null 13417 && capp.pid != 0 13418 && capp.pid != MY_PID) { 13419 killUnneededProcessLocked(capp, "depends on provider " 13420 + cpr.name.flattenToShortString() 13421 + " in dying proc " + (proc != null ? proc.processName : "??")); 13422 } 13423 } else if (capp.thread != null && conn.provider.provider != null) { 13424 try { 13425 capp.thread.unstableProviderDied(conn.provider.provider.asBinder()); 13426 } catch (RemoteException e) { 13427 } 13428 // In the protocol here, we don't expect the client to correctly 13429 // clean up this connection, we'll just remove it. 13430 cpr.connections.remove(i); 13431 conn.client.conProviders.remove(conn); 13432 } 13433 } 13434 13435 if (inLaunching && always) { 13436 mLaunchingProviders.remove(cpr); 13437 } 13438 return inLaunching; 13439 } 13440 13441 /** 13442 * Main code for cleaning up a process when it has gone away. This is 13443 * called both as a result of the process dying, or directly when stopping 13444 * a process when running in single process mode. 13445 */ 13446 private final void cleanUpApplicationRecordLocked(ProcessRecord app, 13447 boolean restarting, boolean allowRestart, int index) { 13448 if (index >= 0) { 13449 removeLruProcessLocked(app); 13450 ProcessList.remove(app.pid); 13451 } 13452 13453 mProcessesToGc.remove(app); 13454 mPendingPssProcesses.remove(app); 13455 13456 // Dismiss any open dialogs. 13457 if (app.crashDialog != null && !app.forceCrashReport) { 13458 app.crashDialog.dismiss(); 13459 app.crashDialog = null; 13460 } 13461 if (app.anrDialog != null) { 13462 app.anrDialog.dismiss(); 13463 app.anrDialog = null; 13464 } 13465 if (app.waitDialog != null) { 13466 app.waitDialog.dismiss(); 13467 app.waitDialog = null; 13468 } 13469 13470 app.crashing = false; 13471 app.notResponding = false; 13472 13473 app.resetPackageList(mProcessStats); 13474 app.unlinkDeathRecipient(); 13475 app.makeInactive(mProcessStats); 13476 app.waitingToKill = null; 13477 app.forcingToForeground = null; 13478 updateProcessForegroundLocked(app, false, false); 13479 app.foregroundActivities = false; 13480 app.hasShownUi = false; 13481 app.treatLikeActivity = false; 13482 app.hasAboveClient = false; 13483 app.hasClientActivities = false; 13484 13485 mServices.killServicesLocked(app, allowRestart); 13486 13487 boolean restart = false; 13488 13489 // Remove published content providers. 13490 for (int i=app.pubProviders.size()-1; i>=0; i--) { 13491 ContentProviderRecord cpr = app.pubProviders.valueAt(i); 13492 final boolean always = app.bad || !allowRestart; 13493 if (removeDyingProviderLocked(app, cpr, always) || always) { 13494 // We left the provider in the launching list, need to 13495 // restart it. 13496 restart = true; 13497 } 13498 13499 cpr.provider = null; 13500 cpr.proc = null; 13501 } 13502 app.pubProviders.clear(); 13503 13504 // Take care of any launching providers waiting for this process. 13505 if (checkAppInLaunchingProvidersLocked(app, false)) { 13506 restart = true; 13507 } 13508 13509 // Unregister from connected content providers. 13510 if (!app.conProviders.isEmpty()) { 13511 for (int i=0; i<app.conProviders.size(); i++) { 13512 ContentProviderConnection conn = app.conProviders.get(i); 13513 conn.provider.connections.remove(conn); 13514 } 13515 app.conProviders.clear(); 13516 } 13517 13518 // At this point there may be remaining entries in mLaunchingProviders 13519 // where we were the only one waiting, so they are no longer of use. 13520 // Look for these and clean up if found. 13521 // XXX Commented out for now. Trying to figure out a way to reproduce 13522 // the actual situation to identify what is actually going on. 13523 if (false) { 13524 for (int i=0; i<mLaunchingProviders.size(); i++) { 13525 ContentProviderRecord cpr = (ContentProviderRecord) 13526 mLaunchingProviders.get(i); 13527 if (cpr.connections.size() <= 0 && !cpr.hasExternalProcessHandles()) { 13528 synchronized (cpr) { 13529 cpr.launchingApp = null; 13530 cpr.notifyAll(); 13531 } 13532 } 13533 } 13534 } 13535 13536 skipCurrentReceiverLocked(app); 13537 13538 // Unregister any receivers. 13539 for (int i=app.receivers.size()-1; i>=0; i--) { 13540 removeReceiverLocked(app.receivers.valueAt(i)); 13541 } 13542 app.receivers.clear(); 13543 13544 // If the app is undergoing backup, tell the backup manager about it 13545 if (mBackupTarget != null && app.pid == mBackupTarget.app.pid) { 13546 if (DEBUG_BACKUP || DEBUG_CLEANUP) Slog.d(TAG, "App " 13547 + mBackupTarget.appInfo + " died during backup"); 13548 try { 13549 IBackupManager bm = IBackupManager.Stub.asInterface( 13550 ServiceManager.getService(Context.BACKUP_SERVICE)); 13551 bm.agentDisconnected(app.info.packageName); 13552 } catch (RemoteException e) { 13553 // can't happen; backup manager is local 13554 } 13555 } 13556 13557 for (int i = mPendingProcessChanges.size()-1; i>=0; i--) { 13558 ProcessChangeItem item = mPendingProcessChanges.get(i); 13559 if (item.pid == app.pid) { 13560 mPendingProcessChanges.remove(i); 13561 mAvailProcessChanges.add(item); 13562 } 13563 } 13564 mHandler.obtainMessage(DISPATCH_PROCESS_DIED, app.pid, app.info.uid, null).sendToTarget(); 13565 13566 // If the caller is restarting this app, then leave it in its 13567 // current lists and let the caller take care of it. 13568 if (restarting) { 13569 return; 13570 } 13571 13572 if (!app.persistent || app.isolated) { 13573 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, 13574 "Removing non-persistent process during cleanup: " + app); 13575 mProcessNames.remove(app.processName, app.uid); 13576 mIsolatedProcesses.remove(app.uid); 13577 if (mHeavyWeightProcess == app) { 13578 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 13579 mHeavyWeightProcess.userId, 0)); 13580 mHeavyWeightProcess = null; 13581 } 13582 } else if (!app.removed) { 13583 // This app is persistent, so we need to keep its record around. 13584 // If it is not already on the pending app list, add it there 13585 // and start a new process for it. 13586 if (mPersistentStartingProcesses.indexOf(app) < 0) { 13587 mPersistentStartingProcesses.add(app); 13588 restart = true; 13589 } 13590 } 13591 if ((DEBUG_PROCESSES || DEBUG_CLEANUP) && mProcessesOnHold.contains(app)) Slog.v(TAG, 13592 "Clean-up removing on hold: " + app); 13593 mProcessesOnHold.remove(app); 13594 13595 if (app == mHomeProcess) { 13596 mHomeProcess = null; 13597 } 13598 if (app == mPreviousProcess) { 13599 mPreviousProcess = null; 13600 } 13601 13602 if (restart && !app.isolated) { 13603 // We have components that still need to be running in the 13604 // process, so re-launch it. 13605 mProcessNames.put(app.processName, app.uid, app); 13606 startProcessLocked(app, "restart", app.processName); 13607 } else if (app.pid > 0 && app.pid != MY_PID) { 13608 // Goodbye! 13609 boolean removed; 13610 synchronized (mPidsSelfLocked) { 13611 mPidsSelfLocked.remove(app.pid); 13612 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 13613 } 13614 mBatteryStatsService.noteProcessFinish(app.processName, app.info.uid); 13615 if (app.isolated) { 13616 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 13617 } 13618 app.setPid(0); 13619 } 13620 } 13621 13622 boolean checkAppInLaunchingProvidersLocked(ProcessRecord app, boolean alwaysBad) { 13623 // Look through the content providers we are waiting to have launched, 13624 // and if any run in this process then either schedule a restart of 13625 // the process or kill the client waiting for it if this process has 13626 // gone bad. 13627 int NL = mLaunchingProviders.size(); 13628 boolean restart = false; 13629 for (int i=0; i<NL; i++) { 13630 ContentProviderRecord cpr = mLaunchingProviders.get(i); 13631 if (cpr.launchingApp == app) { 13632 if (!alwaysBad && !app.bad) { 13633 restart = true; 13634 } else { 13635 removeDyingProviderLocked(app, cpr, true); 13636 // cpr should have been removed from mLaunchingProviders 13637 NL = mLaunchingProviders.size(); 13638 i--; 13639 } 13640 } 13641 } 13642 return restart; 13643 } 13644 13645 // ========================================================= 13646 // SERVICES 13647 // ========================================================= 13648 13649 @Override 13650 public List<ActivityManager.RunningServiceInfo> getServices(int maxNum, 13651 int flags) { 13652 enforceNotIsolatedCaller("getServices"); 13653 synchronized (this) { 13654 return mServices.getRunningServiceInfoLocked(maxNum, flags); 13655 } 13656 } 13657 13658 @Override 13659 public PendingIntent getRunningServiceControlPanel(ComponentName name) { 13660 enforceNotIsolatedCaller("getRunningServiceControlPanel"); 13661 synchronized (this) { 13662 return mServices.getRunningServiceControlPanelLocked(name); 13663 } 13664 } 13665 13666 @Override 13667 public ComponentName startService(IApplicationThread caller, Intent service, 13668 String resolvedType, int userId) { 13669 enforceNotIsolatedCaller("startService"); 13670 // Refuse possible leaked file descriptors 13671 if (service != null && service.hasFileDescriptors() == true) { 13672 throw new IllegalArgumentException("File descriptors passed in Intent"); 13673 } 13674 13675 if (DEBUG_SERVICE) 13676 Slog.v(TAG, "startService: " + service + " type=" + resolvedType); 13677 synchronized(this) { 13678 final int callingPid = Binder.getCallingPid(); 13679 final int callingUid = Binder.getCallingUid(); 13680 final long origId = Binder.clearCallingIdentity(); 13681 ComponentName res = mServices.startServiceLocked(caller, service, 13682 resolvedType, callingPid, callingUid, userId); 13683 Binder.restoreCallingIdentity(origId); 13684 return res; 13685 } 13686 } 13687 13688 ComponentName startServiceInPackage(int uid, 13689 Intent service, String resolvedType, int userId) { 13690 synchronized(this) { 13691 if (DEBUG_SERVICE) 13692 Slog.v(TAG, "startServiceInPackage: " + service + " type=" + resolvedType); 13693 final long origId = Binder.clearCallingIdentity(); 13694 ComponentName res = mServices.startServiceLocked(null, service, 13695 resolvedType, -1, uid, userId); 13696 Binder.restoreCallingIdentity(origId); 13697 return res; 13698 } 13699 } 13700 13701 @Override 13702 public int stopService(IApplicationThread caller, Intent service, 13703 String resolvedType, int userId) { 13704 enforceNotIsolatedCaller("stopService"); 13705 // Refuse possible leaked file descriptors 13706 if (service != null && service.hasFileDescriptors() == true) { 13707 throw new IllegalArgumentException("File descriptors passed in Intent"); 13708 } 13709 13710 synchronized(this) { 13711 return mServices.stopServiceLocked(caller, service, resolvedType, userId); 13712 } 13713 } 13714 13715 @Override 13716 public IBinder peekService(Intent service, String resolvedType) { 13717 enforceNotIsolatedCaller("peekService"); 13718 // Refuse possible leaked file descriptors 13719 if (service != null && service.hasFileDescriptors() == true) { 13720 throw new IllegalArgumentException("File descriptors passed in Intent"); 13721 } 13722 synchronized(this) { 13723 return mServices.peekServiceLocked(service, resolvedType); 13724 } 13725 } 13726 13727 @Override 13728 public boolean stopServiceToken(ComponentName className, IBinder token, 13729 int startId) { 13730 synchronized(this) { 13731 return mServices.stopServiceTokenLocked(className, token, startId); 13732 } 13733 } 13734 13735 @Override 13736 public void setServiceForeground(ComponentName className, IBinder token, 13737 int id, Notification notification, boolean removeNotification) { 13738 synchronized(this) { 13739 mServices.setServiceForegroundLocked(className, token, id, notification, 13740 removeNotification); 13741 } 13742 } 13743 13744 @Override 13745 public int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 13746 boolean requireFull, String name, String callerPackage) { 13747 return handleIncomingUser(callingPid, callingUid, userId, allowAll, 13748 requireFull ? ALLOW_FULL_ONLY : ALLOW_NON_FULL, name, callerPackage); 13749 } 13750 13751 int unsafeConvertIncomingUser(int userId) { 13752 return (userId == UserHandle.USER_CURRENT || userId == UserHandle.USER_CURRENT_OR_SELF) 13753 ? mCurrentUserId : userId; 13754 } 13755 13756 int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 13757 int allowMode, String name, String callerPackage) { 13758 final int callingUserId = UserHandle.getUserId(callingUid); 13759 if (callingUserId == userId) { 13760 return userId; 13761 } 13762 13763 // Note that we may be accessing mCurrentUserId outside of a lock... 13764 // shouldn't be a big deal, if this is being called outside 13765 // of a locked context there is intrinsically a race with 13766 // the value the caller will receive and someone else changing it. 13767 // We assume that USER_CURRENT_OR_SELF will use the current user; later 13768 // we will switch to the calling user if access to the current user fails. 13769 int targetUserId = unsafeConvertIncomingUser(userId); 13770 13771 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 13772 final boolean allow; 13773 if (checkComponentPermission(INTERACT_ACROSS_USERS_FULL, callingPid, 13774 callingUid, -1, true) == PackageManager.PERMISSION_GRANTED) { 13775 // If the caller has this permission, they always pass go. And collect $200. 13776 allow = true; 13777 } else if (allowMode == ALLOW_FULL_ONLY) { 13778 // We require full access, sucks to be you. 13779 allow = false; 13780 } else if (checkComponentPermission(INTERACT_ACROSS_USERS, callingPid, 13781 callingUid, -1, true) != PackageManager.PERMISSION_GRANTED) { 13782 // If the caller does not have either permission, they are always doomed. 13783 allow = false; 13784 } else if (allowMode == ALLOW_NON_FULL) { 13785 // We are blanket allowing non-full access, you lucky caller! 13786 allow = true; 13787 } else if (allowMode == ALLOW_NON_FULL_IN_PROFILE) { 13788 // We may or may not allow this depending on whether the two users are 13789 // in the same profile. 13790 synchronized (mUserProfileGroupIdsSelfLocked) { 13791 int callingProfile = mUserProfileGroupIdsSelfLocked.get(callingUserId, 13792 UserInfo.NO_PROFILE_GROUP_ID); 13793 int targetProfile = mUserProfileGroupIdsSelfLocked.get(targetUserId, 13794 UserInfo.NO_PROFILE_GROUP_ID); 13795 allow = callingProfile != UserInfo.NO_PROFILE_GROUP_ID 13796 && callingProfile == targetProfile; 13797 } 13798 } else { 13799 throw new IllegalArgumentException("Unknown mode: " + allowMode); 13800 } 13801 if (!allow) { 13802 if (userId == UserHandle.USER_CURRENT_OR_SELF) { 13803 // In this case, they would like to just execute as their 13804 // owner user instead of failing. 13805 targetUserId = callingUserId; 13806 } else { 13807 StringBuilder builder = new StringBuilder(128); 13808 builder.append("Permission Denial: "); 13809 builder.append(name); 13810 if (callerPackage != null) { 13811 builder.append(" from "); 13812 builder.append(callerPackage); 13813 } 13814 builder.append(" asks to run as user "); 13815 builder.append(userId); 13816 builder.append(" but is calling from user "); 13817 builder.append(UserHandle.getUserId(callingUid)); 13818 builder.append("; this requires "); 13819 builder.append(INTERACT_ACROSS_USERS_FULL); 13820 if (allowMode != ALLOW_FULL_ONLY) { 13821 builder.append(" or "); 13822 builder.append(INTERACT_ACROSS_USERS); 13823 } 13824 String msg = builder.toString(); 13825 Slog.w(TAG, msg); 13826 throw new SecurityException(msg); 13827 } 13828 } 13829 } 13830 if (!allowAll && targetUserId < 0) { 13831 throw new IllegalArgumentException( 13832 "Call does not support special user #" + targetUserId); 13833 } 13834 return targetUserId; 13835 } 13836 13837 boolean isSingleton(String componentProcessName, ApplicationInfo aInfo, 13838 String className, int flags) { 13839 boolean result = false; 13840 // For apps that don't have pre-defined UIDs, check for permission 13841 if (UserHandle.getAppId(aInfo.uid) >= Process.FIRST_APPLICATION_UID) { 13842 if ((flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 13843 if (ActivityManager.checkUidPermission( 13844 INTERACT_ACROSS_USERS, 13845 aInfo.uid) != PackageManager.PERMISSION_GRANTED) { 13846 ComponentName comp = new ComponentName(aInfo.packageName, className); 13847 String msg = "Permission Denial: Component " + comp.flattenToShortString() 13848 + " requests FLAG_SINGLE_USER, but app does not hold " 13849 + INTERACT_ACROSS_USERS; 13850 Slog.w(TAG, msg); 13851 throw new SecurityException(msg); 13852 } 13853 // Permission passed 13854 result = true; 13855 } 13856 } else if ("system".equals(componentProcessName)) { 13857 result = true; 13858 } else if (UserHandle.isSameApp(aInfo.uid, Process.PHONE_UID) 13859 && (flags & ServiceInfo.FLAG_SINGLE_USER) != 0) { 13860 // Phone app is allowed to export singleuser providers. 13861 result = true; 13862 } else { 13863 // App with pre-defined UID, check if it's a persistent app 13864 result = (aInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0; 13865 } 13866 if (DEBUG_MU) { 13867 Slog.v(TAG, "isSingleton(" + componentProcessName + ", " + aInfo 13868 + ", " + className + ", 0x" + Integer.toHexString(flags) + ") = " + result); 13869 } 13870 return result; 13871 } 13872 13873 /** 13874 * Checks to see if the caller is in the same app as the singleton 13875 * component, or the component is in a special app. It allows special apps 13876 * to export singleton components but prevents exporting singleton 13877 * components for regular apps. 13878 */ 13879 boolean isValidSingletonCall(int callingUid, int componentUid) { 13880 int componentAppId = UserHandle.getAppId(componentUid); 13881 return UserHandle.isSameApp(callingUid, componentUid) 13882 || componentAppId == Process.SYSTEM_UID 13883 || componentAppId == Process.PHONE_UID 13884 || ActivityManager.checkUidPermission(INTERACT_ACROSS_USERS_FULL, componentUid) 13885 == PackageManager.PERMISSION_GRANTED; 13886 } 13887 13888 public int bindService(IApplicationThread caller, IBinder token, 13889 Intent service, String resolvedType, 13890 IServiceConnection connection, int flags, int userId) { 13891 enforceNotIsolatedCaller("bindService"); 13892 // Refuse possible leaked file descriptors 13893 if (service != null && service.hasFileDescriptors() == true) { 13894 throw new IllegalArgumentException("File descriptors passed in Intent"); 13895 } 13896 13897 synchronized(this) { 13898 return mServices.bindServiceLocked(caller, token, service, resolvedType, 13899 connection, flags, userId); 13900 } 13901 } 13902 13903 public boolean unbindService(IServiceConnection connection) { 13904 synchronized (this) { 13905 return mServices.unbindServiceLocked(connection); 13906 } 13907 } 13908 13909 public void publishService(IBinder token, Intent intent, IBinder service) { 13910 // Refuse possible leaked file descriptors 13911 if (intent != null && intent.hasFileDescriptors() == true) { 13912 throw new IllegalArgumentException("File descriptors passed in Intent"); 13913 } 13914 13915 synchronized(this) { 13916 if (!(token instanceof ServiceRecord)) { 13917 throw new IllegalArgumentException("Invalid service token"); 13918 } 13919 mServices.publishServiceLocked((ServiceRecord)token, intent, service); 13920 } 13921 } 13922 13923 public void unbindFinished(IBinder token, Intent intent, boolean doRebind) { 13924 // Refuse possible leaked file descriptors 13925 if (intent != null && intent.hasFileDescriptors() == true) { 13926 throw new IllegalArgumentException("File descriptors passed in Intent"); 13927 } 13928 13929 synchronized(this) { 13930 mServices.unbindFinishedLocked((ServiceRecord)token, intent, doRebind); 13931 } 13932 } 13933 13934 public void serviceDoneExecuting(IBinder token, int type, int startId, int res) { 13935 synchronized(this) { 13936 if (!(token instanceof ServiceRecord)) { 13937 throw new IllegalArgumentException("Invalid service token"); 13938 } 13939 mServices.serviceDoneExecutingLocked((ServiceRecord)token, type, startId, res); 13940 } 13941 } 13942 13943 // ========================================================= 13944 // BACKUP AND RESTORE 13945 // ========================================================= 13946 13947 // Cause the target app to be launched if necessary and its backup agent 13948 // instantiated. The backup agent will invoke backupAgentCreated() on the 13949 // activity manager to announce its creation. 13950 public boolean bindBackupAgent(ApplicationInfo app, int backupMode) { 13951 if (DEBUG_BACKUP) Slog.v(TAG, "bindBackupAgent: app=" + app + " mode=" + backupMode); 13952 enforceCallingPermission("android.permission.CONFIRM_FULL_BACKUP", "bindBackupAgent"); 13953 13954 synchronized(this) { 13955 // !!! TODO: currently no check here that we're already bound 13956 BatteryStatsImpl.Uid.Pkg.Serv ss = null; 13957 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 13958 synchronized (stats) { 13959 ss = stats.getServiceStatsLocked(app.uid, app.packageName, app.name); 13960 } 13961 13962 // Backup agent is now in use, its package can't be stopped. 13963 try { 13964 AppGlobals.getPackageManager().setPackageStoppedState( 13965 app.packageName, false, UserHandle.getUserId(app.uid)); 13966 } catch (RemoteException e) { 13967 } catch (IllegalArgumentException e) { 13968 Slog.w(TAG, "Failed trying to unstop package " 13969 + app.packageName + ": " + e); 13970 } 13971 13972 BackupRecord r = new BackupRecord(ss, app, backupMode); 13973 ComponentName hostingName = (backupMode == IApplicationThread.BACKUP_MODE_INCREMENTAL) 13974 ? new ComponentName(app.packageName, app.backupAgentName) 13975 : new ComponentName("android", "FullBackupAgent"); 13976 // startProcessLocked() returns existing proc's record if it's already running 13977 ProcessRecord proc = startProcessLocked(app.processName, app, 13978 false, 0, "backup", hostingName, false, false, false); 13979 if (proc == null) { 13980 Slog.e(TAG, "Unable to start backup agent process " + r); 13981 return false; 13982 } 13983 13984 r.app = proc; 13985 mBackupTarget = r; 13986 mBackupAppName = app.packageName; 13987 13988 // Try not to kill the process during backup 13989 updateOomAdjLocked(proc); 13990 13991 // If the process is already attached, schedule the creation of the backup agent now. 13992 // If it is not yet live, this will be done when it attaches to the framework. 13993 if (proc.thread != null) { 13994 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc already running: " + proc); 13995 try { 13996 proc.thread.scheduleCreateBackupAgent(app, 13997 compatibilityInfoForPackageLocked(app), backupMode); 13998 } catch (RemoteException e) { 13999 // Will time out on the backup manager side 14000 } 14001 } else { 14002 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc not running, waiting for attach"); 14003 } 14004 // Invariants: at this point, the target app process exists and the application 14005 // is either already running or in the process of coming up. mBackupTarget and 14006 // mBackupAppName describe the app, so that when it binds back to the AM we 14007 // know that it's scheduled for a backup-agent operation. 14008 } 14009 14010 return true; 14011 } 14012 14013 @Override 14014 public void clearPendingBackup() { 14015 if (DEBUG_BACKUP) Slog.v(TAG, "clearPendingBackup"); 14016 enforceCallingPermission("android.permission.BACKUP", "clearPendingBackup"); 14017 14018 synchronized (this) { 14019 mBackupTarget = null; 14020 mBackupAppName = null; 14021 } 14022 } 14023 14024 // A backup agent has just come up 14025 public void backupAgentCreated(String agentPackageName, IBinder agent) { 14026 if (DEBUG_BACKUP) Slog.v(TAG, "backupAgentCreated: " + agentPackageName 14027 + " = " + agent); 14028 14029 synchronized(this) { 14030 if (!agentPackageName.equals(mBackupAppName)) { 14031 Slog.e(TAG, "Backup agent created for " + agentPackageName + " but not requested!"); 14032 return; 14033 } 14034 } 14035 14036 long oldIdent = Binder.clearCallingIdentity(); 14037 try { 14038 IBackupManager bm = IBackupManager.Stub.asInterface( 14039 ServiceManager.getService(Context.BACKUP_SERVICE)); 14040 bm.agentConnected(agentPackageName, agent); 14041 } catch (RemoteException e) { 14042 // can't happen; the backup manager service is local 14043 } catch (Exception e) { 14044 Slog.w(TAG, "Exception trying to deliver BackupAgent binding: "); 14045 e.printStackTrace(); 14046 } finally { 14047 Binder.restoreCallingIdentity(oldIdent); 14048 } 14049 } 14050 14051 // done with this agent 14052 public void unbindBackupAgent(ApplicationInfo appInfo) { 14053 if (DEBUG_BACKUP) Slog.v(TAG, "unbindBackupAgent: " + appInfo); 14054 if (appInfo == null) { 14055 Slog.w(TAG, "unbind backup agent for null app"); 14056 return; 14057 } 14058 14059 synchronized(this) { 14060 try { 14061 if (mBackupAppName == null) { 14062 Slog.w(TAG, "Unbinding backup agent with no active backup"); 14063 return; 14064 } 14065 14066 if (!mBackupAppName.equals(appInfo.packageName)) { 14067 Slog.e(TAG, "Unbind of " + appInfo + " but is not the current backup target"); 14068 return; 14069 } 14070 14071 // Not backing this app up any more; reset its OOM adjustment 14072 final ProcessRecord proc = mBackupTarget.app; 14073 updateOomAdjLocked(proc); 14074 14075 // If the app crashed during backup, 'thread' will be null here 14076 if (proc.thread != null) { 14077 try { 14078 proc.thread.scheduleDestroyBackupAgent(appInfo, 14079 compatibilityInfoForPackageLocked(appInfo)); 14080 } catch (Exception e) { 14081 Slog.e(TAG, "Exception when unbinding backup agent:"); 14082 e.printStackTrace(); 14083 } 14084 } 14085 } finally { 14086 mBackupTarget = null; 14087 mBackupAppName = null; 14088 } 14089 } 14090 } 14091 // ========================================================= 14092 // BROADCASTS 14093 // ========================================================= 14094 14095 private final List getStickiesLocked(String action, IntentFilter filter, 14096 List cur, int userId) { 14097 final ContentResolver resolver = mContext.getContentResolver(); 14098 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 14099 if (stickies == null) { 14100 return cur; 14101 } 14102 final ArrayList<Intent> list = stickies.get(action); 14103 if (list == null) { 14104 return cur; 14105 } 14106 int N = list.size(); 14107 for (int i=0; i<N; i++) { 14108 Intent intent = list.get(i); 14109 if (filter.match(resolver, intent, true, TAG) >= 0) { 14110 if (cur == null) { 14111 cur = new ArrayList<Intent>(); 14112 } 14113 cur.add(intent); 14114 } 14115 } 14116 return cur; 14117 } 14118 14119 boolean isPendingBroadcastProcessLocked(int pid) { 14120 return mFgBroadcastQueue.isPendingBroadcastProcessLocked(pid) 14121 || mBgBroadcastQueue.isPendingBroadcastProcessLocked(pid); 14122 } 14123 14124 void skipPendingBroadcastLocked(int pid) { 14125 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 14126 for (BroadcastQueue queue : mBroadcastQueues) { 14127 queue.skipPendingBroadcastLocked(pid); 14128 } 14129 } 14130 14131 // The app just attached; send any pending broadcasts that it should receive 14132 boolean sendPendingBroadcastsLocked(ProcessRecord app) { 14133 boolean didSomething = false; 14134 for (BroadcastQueue queue : mBroadcastQueues) { 14135 didSomething |= queue.sendPendingBroadcastsLocked(app); 14136 } 14137 return didSomething; 14138 } 14139 14140 public Intent registerReceiver(IApplicationThread caller, String callerPackage, 14141 IIntentReceiver receiver, IntentFilter filter, String permission, int userId) { 14142 enforceNotIsolatedCaller("registerReceiver"); 14143 int callingUid; 14144 int callingPid; 14145 synchronized(this) { 14146 ProcessRecord callerApp = null; 14147 if (caller != null) { 14148 callerApp = getRecordForAppLocked(caller); 14149 if (callerApp == null) { 14150 throw new SecurityException( 14151 "Unable to find app for caller " + caller 14152 + " (pid=" + Binder.getCallingPid() 14153 + ") when registering receiver " + receiver); 14154 } 14155 if (callerApp.info.uid != Process.SYSTEM_UID && 14156 !callerApp.pkgList.containsKey(callerPackage) && 14157 !"android".equals(callerPackage)) { 14158 throw new SecurityException("Given caller package " + callerPackage 14159 + " is not running in process " + callerApp); 14160 } 14161 callingUid = callerApp.info.uid; 14162 callingPid = callerApp.pid; 14163 } else { 14164 callerPackage = null; 14165 callingUid = Binder.getCallingUid(); 14166 callingPid = Binder.getCallingPid(); 14167 } 14168 14169 userId = this.handleIncomingUser(callingPid, callingUid, userId, 14170 true, ALLOW_FULL_ONLY, "registerReceiver", callerPackage); 14171 14172 List allSticky = null; 14173 14174 // Look for any matching sticky broadcasts... 14175 Iterator actions = filter.actionsIterator(); 14176 if (actions != null) { 14177 while (actions.hasNext()) { 14178 String action = (String)actions.next(); 14179 allSticky = getStickiesLocked(action, filter, allSticky, 14180 UserHandle.USER_ALL); 14181 allSticky = getStickiesLocked(action, filter, allSticky, 14182 UserHandle.getUserId(callingUid)); 14183 } 14184 } else { 14185 allSticky = getStickiesLocked(null, filter, allSticky, 14186 UserHandle.USER_ALL); 14187 allSticky = getStickiesLocked(null, filter, allSticky, 14188 UserHandle.getUserId(callingUid)); 14189 } 14190 14191 // The first sticky in the list is returned directly back to 14192 // the client. 14193 Intent sticky = allSticky != null ? (Intent)allSticky.get(0) : null; 14194 14195 if (DEBUG_BROADCAST) Slog.v(TAG, "Register receiver " + filter 14196 + ": " + sticky); 14197 14198 if (receiver == null) { 14199 return sticky; 14200 } 14201 14202 ReceiverList rl 14203 = (ReceiverList)mRegisteredReceivers.get(receiver.asBinder()); 14204 if (rl == null) { 14205 rl = new ReceiverList(this, callerApp, callingPid, callingUid, 14206 userId, receiver); 14207 if (rl.app != null) { 14208 rl.app.receivers.add(rl); 14209 } else { 14210 try { 14211 receiver.asBinder().linkToDeath(rl, 0); 14212 } catch (RemoteException e) { 14213 return sticky; 14214 } 14215 rl.linkedToDeath = true; 14216 } 14217 mRegisteredReceivers.put(receiver.asBinder(), rl); 14218 } else if (rl.uid != callingUid) { 14219 throw new IllegalArgumentException( 14220 "Receiver requested to register for uid " + callingUid 14221 + " was previously registered for uid " + rl.uid); 14222 } else if (rl.pid != callingPid) { 14223 throw new IllegalArgumentException( 14224 "Receiver requested to register for pid " + callingPid 14225 + " was previously registered for pid " + rl.pid); 14226 } else if (rl.userId != userId) { 14227 throw new IllegalArgumentException( 14228 "Receiver requested to register for user " + userId 14229 + " was previously registered for user " + rl.userId); 14230 } 14231 BroadcastFilter bf = new BroadcastFilter(filter, rl, callerPackage, 14232 permission, callingUid, userId); 14233 rl.add(bf); 14234 if (!bf.debugCheck()) { 14235 Slog.w(TAG, "==> For Dynamic broadast"); 14236 } 14237 mReceiverResolver.addFilter(bf); 14238 14239 // Enqueue broadcasts for all existing stickies that match 14240 // this filter. 14241 if (allSticky != null) { 14242 ArrayList receivers = new ArrayList(); 14243 receivers.add(bf); 14244 14245 int N = allSticky.size(); 14246 for (int i=0; i<N; i++) { 14247 Intent intent = (Intent)allSticky.get(i); 14248 BroadcastQueue queue = broadcastQueueForIntent(intent); 14249 BroadcastRecord r = new BroadcastRecord(queue, intent, null, 14250 null, -1, -1, null, null, AppOpsManager.OP_NONE, receivers, null, 0, 14251 null, null, false, true, true, -1); 14252 queue.enqueueParallelBroadcastLocked(r); 14253 queue.scheduleBroadcastsLocked(); 14254 } 14255 } 14256 14257 return sticky; 14258 } 14259 } 14260 14261 public void unregisterReceiver(IIntentReceiver receiver) { 14262 if (DEBUG_BROADCAST) Slog.v(TAG, "Unregister receiver: " + receiver); 14263 14264 final long origId = Binder.clearCallingIdentity(); 14265 try { 14266 boolean doTrim = false; 14267 14268 synchronized(this) { 14269 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder()); 14270 if (rl != null) { 14271 if (rl.curBroadcast != null) { 14272 BroadcastRecord r = rl.curBroadcast; 14273 final boolean doNext = finishReceiverLocked( 14274 receiver.asBinder(), r.resultCode, r.resultData, 14275 r.resultExtras, r.resultAbort); 14276 if (doNext) { 14277 doTrim = true; 14278 r.queue.processNextBroadcast(false); 14279 } 14280 } 14281 14282 if (rl.app != null) { 14283 rl.app.receivers.remove(rl); 14284 } 14285 removeReceiverLocked(rl); 14286 if (rl.linkedToDeath) { 14287 rl.linkedToDeath = false; 14288 rl.receiver.asBinder().unlinkToDeath(rl, 0); 14289 } 14290 } 14291 } 14292 14293 // If we actually concluded any broadcasts, we might now be able 14294 // to trim the recipients' apps from our working set 14295 if (doTrim) { 14296 trimApplications(); 14297 return; 14298 } 14299 14300 } finally { 14301 Binder.restoreCallingIdentity(origId); 14302 } 14303 } 14304 14305 void removeReceiverLocked(ReceiverList rl) { 14306 mRegisteredReceivers.remove(rl.receiver.asBinder()); 14307 int N = rl.size(); 14308 for (int i=0; i<N; i++) { 14309 mReceiverResolver.removeFilter(rl.get(i)); 14310 } 14311 } 14312 14313 private final void sendPackageBroadcastLocked(int cmd, String[] packages, int userId) { 14314 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 14315 ProcessRecord r = mLruProcesses.get(i); 14316 if (r.thread != null && (userId == UserHandle.USER_ALL || r.userId == userId)) { 14317 try { 14318 r.thread.dispatchPackageBroadcast(cmd, packages); 14319 } catch (RemoteException ex) { 14320 } 14321 } 14322 } 14323 } 14324 14325 private List<ResolveInfo> collectReceiverComponents(Intent intent, String resolvedType, 14326 int[] users) { 14327 List<ResolveInfo> receivers = null; 14328 try { 14329 HashSet<ComponentName> singleUserReceivers = null; 14330 boolean scannedFirstReceivers = false; 14331 for (int user : users) { 14332 List<ResolveInfo> newReceivers = AppGlobals.getPackageManager() 14333 .queryIntentReceivers(intent, resolvedType, STOCK_PM_FLAGS, user); 14334 if (user != 0 && newReceivers != null) { 14335 // If this is not the primary user, we need to check for 14336 // any receivers that should be filtered out. 14337 for (int i=0; i<newReceivers.size(); i++) { 14338 ResolveInfo ri = newReceivers.get(i); 14339 if ((ri.activityInfo.flags&ActivityInfo.FLAG_PRIMARY_USER_ONLY) != 0) { 14340 newReceivers.remove(i); 14341 i--; 14342 } 14343 } 14344 } 14345 if (newReceivers != null && newReceivers.size() == 0) { 14346 newReceivers = null; 14347 } 14348 if (receivers == null) { 14349 receivers = newReceivers; 14350 } else if (newReceivers != null) { 14351 // We need to concatenate the additional receivers 14352 // found with what we have do far. This would be easy, 14353 // but we also need to de-dup any receivers that are 14354 // singleUser. 14355 if (!scannedFirstReceivers) { 14356 // Collect any single user receivers we had already retrieved. 14357 scannedFirstReceivers = true; 14358 for (int i=0; i<receivers.size(); i++) { 14359 ResolveInfo ri = receivers.get(i); 14360 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 14361 ComponentName cn = new ComponentName( 14362 ri.activityInfo.packageName, ri.activityInfo.name); 14363 if (singleUserReceivers == null) { 14364 singleUserReceivers = new HashSet<ComponentName>(); 14365 } 14366 singleUserReceivers.add(cn); 14367 } 14368 } 14369 } 14370 // Add the new results to the existing results, tracking 14371 // and de-dupping single user receivers. 14372 for (int i=0; i<newReceivers.size(); i++) { 14373 ResolveInfo ri = newReceivers.get(i); 14374 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 14375 ComponentName cn = new ComponentName( 14376 ri.activityInfo.packageName, ri.activityInfo.name); 14377 if (singleUserReceivers == null) { 14378 singleUserReceivers = new HashSet<ComponentName>(); 14379 } 14380 if (!singleUserReceivers.contains(cn)) { 14381 singleUserReceivers.add(cn); 14382 receivers.add(ri); 14383 } 14384 } else { 14385 receivers.add(ri); 14386 } 14387 } 14388 } 14389 } 14390 } catch (RemoteException ex) { 14391 // pm is in same process, this will never happen. 14392 } 14393 return receivers; 14394 } 14395 14396 private final int broadcastIntentLocked(ProcessRecord callerApp, 14397 String callerPackage, Intent intent, String resolvedType, 14398 IIntentReceiver resultTo, int resultCode, String resultData, 14399 Bundle map, String requiredPermission, int appOp, 14400 boolean ordered, boolean sticky, int callingPid, int callingUid, 14401 int userId) { 14402 intent = new Intent(intent); 14403 14404 // By default broadcasts do not go to stopped apps. 14405 intent.addFlags(Intent.FLAG_EXCLUDE_STOPPED_PACKAGES); 14406 14407 if (DEBUG_BROADCAST_LIGHT) Slog.v( 14408 TAG, (sticky ? "Broadcast sticky: ": "Broadcast: ") + intent 14409 + " ordered=" + ordered + " userid=" + userId); 14410 if ((resultTo != null) && !ordered) { 14411 Slog.w(TAG, "Broadcast " + intent + " not ordered but result callback requested!"); 14412 } 14413 14414 userId = handleIncomingUser(callingPid, callingUid, userId, 14415 true, ALLOW_NON_FULL, "broadcast", callerPackage); 14416 14417 // Make sure that the user who is receiving this broadcast is started. 14418 // If not, we will just skip it. 14419 14420 14421 if (userId != UserHandle.USER_ALL && mStartedUsers.get(userId) == null) { 14422 if (callingUid != Process.SYSTEM_UID || (intent.getFlags() 14423 & Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) { 14424 Slog.w(TAG, "Skipping broadcast of " + intent 14425 + ": user " + userId + " is stopped"); 14426 return ActivityManager.BROADCAST_SUCCESS; 14427 } 14428 } 14429 14430 /* 14431 * Prevent non-system code (defined here to be non-persistent 14432 * processes) from sending protected broadcasts. 14433 */ 14434 int callingAppId = UserHandle.getAppId(callingUid); 14435 if (callingAppId == Process.SYSTEM_UID || callingAppId == Process.PHONE_UID 14436 || callingAppId == Process.SHELL_UID || callingAppId == Process.BLUETOOTH_UID 14437 || callingAppId == Process.NFC_UID || callingUid == 0) { 14438 // Always okay. 14439 } else if (callerApp == null || !callerApp.persistent) { 14440 try { 14441 if (AppGlobals.getPackageManager().isProtectedBroadcast( 14442 intent.getAction())) { 14443 String msg = "Permission Denial: not allowed to send broadcast " 14444 + intent.getAction() + " from pid=" 14445 + callingPid + ", uid=" + callingUid; 14446 Slog.w(TAG, msg); 14447 throw new SecurityException(msg); 14448 } else if (AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(intent.getAction())) { 14449 // Special case for compatibility: we don't want apps to send this, 14450 // but historically it has not been protected and apps may be using it 14451 // to poke their own app widget. So, instead of making it protected, 14452 // just limit it to the caller. 14453 if (callerApp == null) { 14454 String msg = "Permission Denial: not allowed to send broadcast " 14455 + intent.getAction() + " from unknown caller."; 14456 Slog.w(TAG, msg); 14457 throw new SecurityException(msg); 14458 } else if (intent.getComponent() != null) { 14459 // They are good enough to send to an explicit component... verify 14460 // it is being sent to the calling app. 14461 if (!intent.getComponent().getPackageName().equals( 14462 callerApp.info.packageName)) { 14463 String msg = "Permission Denial: not allowed to send broadcast " 14464 + intent.getAction() + " to " 14465 + intent.getComponent().getPackageName() + " from " 14466 + callerApp.info.packageName; 14467 Slog.w(TAG, msg); 14468 throw new SecurityException(msg); 14469 } 14470 } else { 14471 // Limit broadcast to their own package. 14472 intent.setPackage(callerApp.info.packageName); 14473 } 14474 } 14475 } catch (RemoteException e) { 14476 Slog.w(TAG, "Remote exception", e); 14477 return ActivityManager.BROADCAST_SUCCESS; 14478 } 14479 } 14480 14481 // Handle special intents: if this broadcast is from the package 14482 // manager about a package being removed, we need to remove all of 14483 // its activities from the history stack. 14484 final boolean uidRemoved = Intent.ACTION_UID_REMOVED.equals( 14485 intent.getAction()); 14486 if (Intent.ACTION_PACKAGE_REMOVED.equals(intent.getAction()) 14487 || Intent.ACTION_PACKAGE_CHANGED.equals(intent.getAction()) 14488 || Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction()) 14489 || uidRemoved) { 14490 if (checkComponentPermission( 14491 android.Manifest.permission.BROADCAST_PACKAGE_REMOVED, 14492 callingPid, callingUid, -1, true) 14493 == PackageManager.PERMISSION_GRANTED) { 14494 if (uidRemoved) { 14495 final Bundle intentExtras = intent.getExtras(); 14496 final int uid = intentExtras != null 14497 ? intentExtras.getInt(Intent.EXTRA_UID) : -1; 14498 if (uid >= 0) { 14499 BatteryStatsImpl bs = mBatteryStatsService.getActiveStatistics(); 14500 synchronized (bs) { 14501 bs.removeUidStatsLocked(uid); 14502 } 14503 mAppOpsService.uidRemoved(uid); 14504 } 14505 } else { 14506 // If resources are unavailable just force stop all 14507 // those packages and flush the attribute cache as well. 14508 if (Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction())) { 14509 String list[] = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 14510 if (list != null && (list.length > 0)) { 14511 for (String pkg : list) { 14512 forceStopPackageLocked(pkg, -1, false, true, true, false, false, userId, 14513 "storage unmount"); 14514 } 14515 sendPackageBroadcastLocked( 14516 IApplicationThread.EXTERNAL_STORAGE_UNAVAILABLE, list, userId); 14517 } 14518 } else { 14519 Uri data = intent.getData(); 14520 String ssp; 14521 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 14522 boolean removed = Intent.ACTION_PACKAGE_REMOVED.equals( 14523 intent.getAction()); 14524 boolean fullUninstall = removed && 14525 !intent.getBooleanExtra(Intent.EXTRA_REPLACING, false); 14526 if (!intent.getBooleanExtra(Intent.EXTRA_DONT_KILL_APP, false)) { 14527 forceStopPackageLocked(ssp, UserHandle.getAppId( 14528 intent.getIntExtra(Intent.EXTRA_UID, -1)), false, true, true, 14529 false, fullUninstall, userId, 14530 removed ? "pkg removed" : "pkg changed"); 14531 } 14532 if (removed) { 14533 sendPackageBroadcastLocked(IApplicationThread.PACKAGE_REMOVED, 14534 new String[] {ssp}, userId); 14535 if (!intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)) { 14536 mAppOpsService.packageRemoved( 14537 intent.getIntExtra(Intent.EXTRA_UID, -1), ssp); 14538 14539 // Remove all permissions granted from/to this package 14540 removeUriPermissionsForPackageLocked(ssp, userId, true); 14541 } 14542 } 14543 } 14544 } 14545 } 14546 } else { 14547 String msg = "Permission Denial: " + intent.getAction() 14548 + " broadcast from " + callerPackage + " (pid=" + callingPid 14549 + ", uid=" + callingUid + ")" 14550 + " requires " 14551 + android.Manifest.permission.BROADCAST_PACKAGE_REMOVED; 14552 Slog.w(TAG, msg); 14553 throw new SecurityException(msg); 14554 } 14555 14556 // Special case for adding a package: by default turn on compatibility 14557 // mode. 14558 } else if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction())) { 14559 Uri data = intent.getData(); 14560 String ssp; 14561 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 14562 mCompatModePackages.handlePackageAddedLocked(ssp, 14563 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)); 14564 } 14565 } 14566 14567 /* 14568 * If this is the time zone changed action, queue up a message that will reset the timezone 14569 * of all currently running processes. This message will get queued up before the broadcast 14570 * happens. 14571 */ 14572 if (Intent.ACTION_TIMEZONE_CHANGED.equals(intent.getAction())) { 14573 mHandler.sendEmptyMessage(UPDATE_TIME_ZONE); 14574 } 14575 14576 /* 14577 * If the user set the time, let all running processes know. 14578 */ 14579 if (Intent.ACTION_TIME_CHANGED.equals(intent.getAction())) { 14580 final int is24Hour = intent.getBooleanExtra( 14581 Intent.EXTRA_TIME_PREF_24_HOUR_FORMAT, false) ? 1 : 0; 14582 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_TIME, is24Hour, 0)); 14583 } 14584 14585 if (Intent.ACTION_CLEAR_DNS_CACHE.equals(intent.getAction())) { 14586 mHandler.sendEmptyMessage(CLEAR_DNS_CACHE_MSG); 14587 } 14588 14589 if (Proxy.PROXY_CHANGE_ACTION.equals(intent.getAction())) { 14590 ProxyInfo proxy = intent.getParcelableExtra(Proxy.EXTRA_PROXY_INFO); 14591 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_HTTP_PROXY_MSG, proxy)); 14592 } 14593 14594 // Add to the sticky list if requested. 14595 if (sticky) { 14596 if (checkPermission(android.Manifest.permission.BROADCAST_STICKY, 14597 callingPid, callingUid) 14598 != PackageManager.PERMISSION_GRANTED) { 14599 String msg = "Permission Denial: broadcastIntent() requesting a sticky broadcast from pid=" 14600 + callingPid + ", uid=" + callingUid 14601 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 14602 Slog.w(TAG, msg); 14603 throw new SecurityException(msg); 14604 } 14605 if (requiredPermission != null) { 14606 Slog.w(TAG, "Can't broadcast sticky intent " + intent 14607 + " and enforce permission " + requiredPermission); 14608 return ActivityManager.BROADCAST_STICKY_CANT_HAVE_PERMISSION; 14609 } 14610 if (intent.getComponent() != null) { 14611 throw new SecurityException( 14612 "Sticky broadcasts can't target a specific component"); 14613 } 14614 // We use userId directly here, since the "all" target is maintained 14615 // as a separate set of sticky broadcasts. 14616 if (userId != UserHandle.USER_ALL) { 14617 // But first, if this is not a broadcast to all users, then 14618 // make sure it doesn't conflict with an existing broadcast to 14619 // all users. 14620 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get( 14621 UserHandle.USER_ALL); 14622 if (stickies != null) { 14623 ArrayList<Intent> list = stickies.get(intent.getAction()); 14624 if (list != null) { 14625 int N = list.size(); 14626 int i; 14627 for (i=0; i<N; i++) { 14628 if (intent.filterEquals(list.get(i))) { 14629 throw new IllegalArgumentException( 14630 "Sticky broadcast " + intent + " for user " 14631 + userId + " conflicts with existing global broadcast"); 14632 } 14633 } 14634 } 14635 } 14636 } 14637 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 14638 if (stickies == null) { 14639 stickies = new ArrayMap<String, ArrayList<Intent>>(); 14640 mStickyBroadcasts.put(userId, stickies); 14641 } 14642 ArrayList<Intent> list = stickies.get(intent.getAction()); 14643 if (list == null) { 14644 list = new ArrayList<Intent>(); 14645 stickies.put(intent.getAction(), list); 14646 } 14647 int N = list.size(); 14648 int i; 14649 for (i=0; i<N; i++) { 14650 if (intent.filterEquals(list.get(i))) { 14651 // This sticky already exists, replace it. 14652 list.set(i, new Intent(intent)); 14653 break; 14654 } 14655 } 14656 if (i >= N) { 14657 list.add(new Intent(intent)); 14658 } 14659 } 14660 14661 int[] users; 14662 if (userId == UserHandle.USER_ALL) { 14663 // Caller wants broadcast to go to all started users. 14664 users = mStartedUserArray; 14665 } else { 14666 // Caller wants broadcast to go to one specific user. 14667 users = new int[] {userId}; 14668 } 14669 14670 // Figure out who all will receive this broadcast. 14671 List receivers = null; 14672 List<BroadcastFilter> registeredReceivers = null; 14673 // Need to resolve the intent to interested receivers... 14674 if ((intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) 14675 == 0) { 14676 receivers = collectReceiverComponents(intent, resolvedType, users); 14677 } 14678 if (intent.getComponent() == null) { 14679 registeredReceivers = mReceiverResolver.queryIntent(intent, 14680 resolvedType, false, userId); 14681 } 14682 14683 final boolean replacePending = 14684 (intent.getFlags()&Intent.FLAG_RECEIVER_REPLACE_PENDING) != 0; 14685 14686 if (DEBUG_BROADCAST) Slog.v(TAG, "Enqueing broadcast: " + intent.getAction() 14687 + " replacePending=" + replacePending); 14688 14689 int NR = registeredReceivers != null ? registeredReceivers.size() : 0; 14690 if (!ordered && NR > 0) { 14691 // If we are not serializing this broadcast, then send the 14692 // registered receivers separately so they don't wait for the 14693 // components to be launched. 14694 final BroadcastQueue queue = broadcastQueueForIntent(intent); 14695 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 14696 callerPackage, callingPid, callingUid, resolvedType, requiredPermission, 14697 appOp, registeredReceivers, resultTo, resultCode, resultData, map, 14698 ordered, sticky, false, userId); 14699 if (DEBUG_BROADCAST) Slog.v( 14700 TAG, "Enqueueing parallel broadcast " + r); 14701 final boolean replaced = replacePending && queue.replaceParallelBroadcastLocked(r); 14702 if (!replaced) { 14703 queue.enqueueParallelBroadcastLocked(r); 14704 queue.scheduleBroadcastsLocked(); 14705 } 14706 registeredReceivers = null; 14707 NR = 0; 14708 } 14709 14710 // Merge into one list. 14711 int ir = 0; 14712 if (receivers != null) { 14713 // A special case for PACKAGE_ADDED: do not allow the package 14714 // being added to see this broadcast. This prevents them from 14715 // using this as a back door to get run as soon as they are 14716 // installed. Maybe in the future we want to have a special install 14717 // broadcast or such for apps, but we'd like to deliberately make 14718 // this decision. 14719 String skipPackages[] = null; 14720 if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction()) 14721 || Intent.ACTION_PACKAGE_RESTARTED.equals(intent.getAction()) 14722 || Intent.ACTION_PACKAGE_DATA_CLEARED.equals(intent.getAction())) { 14723 Uri data = intent.getData(); 14724 if (data != null) { 14725 String pkgName = data.getSchemeSpecificPart(); 14726 if (pkgName != null) { 14727 skipPackages = new String[] { pkgName }; 14728 } 14729 } 14730 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction())) { 14731 skipPackages = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 14732 } 14733 if (skipPackages != null && (skipPackages.length > 0)) { 14734 for (String skipPackage : skipPackages) { 14735 if (skipPackage != null) { 14736 int NT = receivers.size(); 14737 for (int it=0; it<NT; it++) { 14738 ResolveInfo curt = (ResolveInfo)receivers.get(it); 14739 if (curt.activityInfo.packageName.equals(skipPackage)) { 14740 receivers.remove(it); 14741 it--; 14742 NT--; 14743 } 14744 } 14745 } 14746 } 14747 } 14748 14749 int NT = receivers != null ? receivers.size() : 0; 14750 int it = 0; 14751 ResolveInfo curt = null; 14752 BroadcastFilter curr = null; 14753 while (it < NT && ir < NR) { 14754 if (curt == null) { 14755 curt = (ResolveInfo)receivers.get(it); 14756 } 14757 if (curr == null) { 14758 curr = registeredReceivers.get(ir); 14759 } 14760 if (curr.getPriority() >= curt.priority) { 14761 // Insert this broadcast record into the final list. 14762 receivers.add(it, curr); 14763 ir++; 14764 curr = null; 14765 it++; 14766 NT++; 14767 } else { 14768 // Skip to the next ResolveInfo in the final list. 14769 it++; 14770 curt = null; 14771 } 14772 } 14773 } 14774 while (ir < NR) { 14775 if (receivers == null) { 14776 receivers = new ArrayList(); 14777 } 14778 receivers.add(registeredReceivers.get(ir)); 14779 ir++; 14780 } 14781 14782 if ((receivers != null && receivers.size() > 0) 14783 || resultTo != null) { 14784 BroadcastQueue queue = broadcastQueueForIntent(intent); 14785 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 14786 callerPackage, callingPid, callingUid, resolvedType, 14787 requiredPermission, appOp, receivers, resultTo, resultCode, 14788 resultData, map, ordered, sticky, false, userId); 14789 if (DEBUG_BROADCAST) Slog.v( 14790 TAG, "Enqueueing ordered broadcast " + r 14791 + ": prev had " + queue.mOrderedBroadcasts.size()); 14792 if (DEBUG_BROADCAST) { 14793 int seq = r.intent.getIntExtra("seq", -1); 14794 Slog.i(TAG, "Enqueueing broadcast " + r.intent.getAction() + " seq=" + seq); 14795 } 14796 boolean replaced = replacePending && queue.replaceOrderedBroadcastLocked(r); 14797 if (!replaced) { 14798 queue.enqueueOrderedBroadcastLocked(r); 14799 queue.scheduleBroadcastsLocked(); 14800 } 14801 } 14802 14803 return ActivityManager.BROADCAST_SUCCESS; 14804 } 14805 14806 final Intent verifyBroadcastLocked(Intent intent) { 14807 // Refuse possible leaked file descriptors 14808 if (intent != null && intent.hasFileDescriptors() == true) { 14809 throw new IllegalArgumentException("File descriptors passed in Intent"); 14810 } 14811 14812 int flags = intent.getFlags(); 14813 14814 if (!mProcessesReady) { 14815 // if the caller really truly claims to know what they're doing, go 14816 // ahead and allow the broadcast without launching any receivers 14817 if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT) != 0) { 14818 intent = new Intent(intent); 14819 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 14820 } else if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) { 14821 Slog.e(TAG, "Attempt to launch receivers of broadcast intent " + intent 14822 + " before boot completion"); 14823 throw new IllegalStateException("Cannot broadcast before boot completed"); 14824 } 14825 } 14826 14827 if ((flags&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 14828 throw new IllegalArgumentException( 14829 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 14830 } 14831 14832 return intent; 14833 } 14834 14835 public final int broadcastIntent(IApplicationThread caller, 14836 Intent intent, String resolvedType, IIntentReceiver resultTo, 14837 int resultCode, String resultData, Bundle map, 14838 String requiredPermission, int appOp, boolean serialized, boolean sticky, int userId) { 14839 enforceNotIsolatedCaller("broadcastIntent"); 14840 synchronized(this) { 14841 intent = verifyBroadcastLocked(intent); 14842 14843 final ProcessRecord callerApp = getRecordForAppLocked(caller); 14844 final int callingPid = Binder.getCallingPid(); 14845 final int callingUid = Binder.getCallingUid(); 14846 final long origId = Binder.clearCallingIdentity(); 14847 int res = broadcastIntentLocked(callerApp, 14848 callerApp != null ? callerApp.info.packageName : null, 14849 intent, resolvedType, resultTo, 14850 resultCode, resultData, map, requiredPermission, appOp, serialized, sticky, 14851 callingPid, callingUid, userId); 14852 Binder.restoreCallingIdentity(origId); 14853 return res; 14854 } 14855 } 14856 14857 int broadcastIntentInPackage(String packageName, int uid, 14858 Intent intent, String resolvedType, IIntentReceiver resultTo, 14859 int resultCode, String resultData, Bundle map, 14860 String requiredPermission, boolean serialized, boolean sticky, int userId) { 14861 synchronized(this) { 14862 intent = verifyBroadcastLocked(intent); 14863 14864 final long origId = Binder.clearCallingIdentity(); 14865 int res = broadcastIntentLocked(null, packageName, intent, resolvedType, 14866 resultTo, resultCode, resultData, map, requiredPermission, 14867 AppOpsManager.OP_NONE, serialized, sticky, -1, uid, userId); 14868 Binder.restoreCallingIdentity(origId); 14869 return res; 14870 } 14871 } 14872 14873 public final void unbroadcastIntent(IApplicationThread caller, Intent intent, int userId) { 14874 // Refuse possible leaked file descriptors 14875 if (intent != null && intent.hasFileDescriptors() == true) { 14876 throw new IllegalArgumentException("File descriptors passed in Intent"); 14877 } 14878 14879 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 14880 userId, true, ALLOW_NON_FULL, "removeStickyBroadcast", null); 14881 14882 synchronized(this) { 14883 if (checkCallingPermission(android.Manifest.permission.BROADCAST_STICKY) 14884 != PackageManager.PERMISSION_GRANTED) { 14885 String msg = "Permission Denial: unbroadcastIntent() from pid=" 14886 + Binder.getCallingPid() 14887 + ", uid=" + Binder.getCallingUid() 14888 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 14889 Slog.w(TAG, msg); 14890 throw new SecurityException(msg); 14891 } 14892 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 14893 if (stickies != null) { 14894 ArrayList<Intent> list = stickies.get(intent.getAction()); 14895 if (list != null) { 14896 int N = list.size(); 14897 int i; 14898 for (i=0; i<N; i++) { 14899 if (intent.filterEquals(list.get(i))) { 14900 list.remove(i); 14901 break; 14902 } 14903 } 14904 if (list.size() <= 0) { 14905 stickies.remove(intent.getAction()); 14906 } 14907 } 14908 if (stickies.size() <= 0) { 14909 mStickyBroadcasts.remove(userId); 14910 } 14911 } 14912 } 14913 } 14914 14915 private final boolean finishReceiverLocked(IBinder receiver, int resultCode, 14916 String resultData, Bundle resultExtras, boolean resultAbort) { 14917 final BroadcastRecord r = broadcastRecordForReceiverLocked(receiver); 14918 if (r == null) { 14919 Slog.w(TAG, "finishReceiver called but not found on queue"); 14920 return false; 14921 } 14922 14923 return r.queue.finishReceiverLocked(r, resultCode, resultData, resultExtras, resultAbort, false); 14924 } 14925 14926 void backgroundServicesFinishedLocked(int userId) { 14927 for (BroadcastQueue queue : mBroadcastQueues) { 14928 queue.backgroundServicesFinishedLocked(userId); 14929 } 14930 } 14931 14932 public void finishReceiver(IBinder who, int resultCode, String resultData, 14933 Bundle resultExtras, boolean resultAbort) { 14934 if (DEBUG_BROADCAST) Slog.v(TAG, "Finish receiver: " + who); 14935 14936 // Refuse possible leaked file descriptors 14937 if (resultExtras != null && resultExtras.hasFileDescriptors()) { 14938 throw new IllegalArgumentException("File descriptors passed in Bundle"); 14939 } 14940 14941 final long origId = Binder.clearCallingIdentity(); 14942 try { 14943 boolean doNext = false; 14944 BroadcastRecord r; 14945 14946 synchronized(this) { 14947 r = broadcastRecordForReceiverLocked(who); 14948 if (r != null) { 14949 doNext = r.queue.finishReceiverLocked(r, resultCode, 14950 resultData, resultExtras, resultAbort, true); 14951 } 14952 } 14953 14954 if (doNext) { 14955 r.queue.processNextBroadcast(false); 14956 } 14957 trimApplications(); 14958 } finally { 14959 Binder.restoreCallingIdentity(origId); 14960 } 14961 } 14962 14963 // ========================================================= 14964 // INSTRUMENTATION 14965 // ========================================================= 14966 14967 public boolean startInstrumentation(ComponentName className, 14968 String profileFile, int flags, Bundle arguments, 14969 IInstrumentationWatcher watcher, IUiAutomationConnection uiAutomationConnection, 14970 int userId, String abiOverride) { 14971 enforceNotIsolatedCaller("startInstrumentation"); 14972 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 14973 userId, false, ALLOW_FULL_ONLY, "startInstrumentation", null); 14974 // Refuse possible leaked file descriptors 14975 if (arguments != null && arguments.hasFileDescriptors()) { 14976 throw new IllegalArgumentException("File descriptors passed in Bundle"); 14977 } 14978 14979 synchronized(this) { 14980 InstrumentationInfo ii = null; 14981 ApplicationInfo ai = null; 14982 try { 14983 ii = mContext.getPackageManager().getInstrumentationInfo( 14984 className, STOCK_PM_FLAGS); 14985 ai = AppGlobals.getPackageManager().getApplicationInfo( 14986 ii.targetPackage, STOCK_PM_FLAGS, userId); 14987 } catch (PackageManager.NameNotFoundException e) { 14988 } catch (RemoteException e) { 14989 } 14990 if (ii == null) { 14991 reportStartInstrumentationFailure(watcher, className, 14992 "Unable to find instrumentation info for: " + className); 14993 return false; 14994 } 14995 if (ai == null) { 14996 reportStartInstrumentationFailure(watcher, className, 14997 "Unable to find instrumentation target package: " + ii.targetPackage); 14998 return false; 14999 } 15000 15001 int match = mContext.getPackageManager().checkSignatures( 15002 ii.targetPackage, ii.packageName); 15003 if (match < 0 && match != PackageManager.SIGNATURE_FIRST_NOT_SIGNED) { 15004 String msg = "Permission Denial: starting instrumentation " 15005 + className + " from pid=" 15006 + Binder.getCallingPid() 15007 + ", uid=" + Binder.getCallingPid() 15008 + " not allowed because package " + ii.packageName 15009 + " does not have a signature matching the target " 15010 + ii.targetPackage; 15011 reportStartInstrumentationFailure(watcher, className, msg); 15012 throw new SecurityException(msg); 15013 } 15014 15015 final long origId = Binder.clearCallingIdentity(); 15016 // Instrumentation can kill and relaunch even persistent processes 15017 forceStopPackageLocked(ii.targetPackage, -1, true, false, true, true, false, userId, 15018 "start instr"); 15019 ProcessRecord app = addAppLocked(ai, false, abiOverride); 15020 app.instrumentationClass = className; 15021 app.instrumentationInfo = ai; 15022 app.instrumentationProfileFile = profileFile; 15023 app.instrumentationArguments = arguments; 15024 app.instrumentationWatcher = watcher; 15025 app.instrumentationUiAutomationConnection = uiAutomationConnection; 15026 app.instrumentationResultClass = className; 15027 Binder.restoreCallingIdentity(origId); 15028 } 15029 15030 return true; 15031 } 15032 15033 /** 15034 * Report errors that occur while attempting to start Instrumentation. Always writes the 15035 * error to the logs, but if somebody is watching, send the report there too. This enables 15036 * the "am" command to report errors with more information. 15037 * 15038 * @param watcher The IInstrumentationWatcher. Null if there isn't one. 15039 * @param cn The component name of the instrumentation. 15040 * @param report The error report. 15041 */ 15042 private void reportStartInstrumentationFailure(IInstrumentationWatcher watcher, 15043 ComponentName cn, String report) { 15044 Slog.w(TAG, report); 15045 try { 15046 if (watcher != null) { 15047 Bundle results = new Bundle(); 15048 results.putString(Instrumentation.REPORT_KEY_IDENTIFIER, "ActivityManagerService"); 15049 results.putString("Error", report); 15050 watcher.instrumentationStatus(cn, -1, results); 15051 } 15052 } catch (RemoteException e) { 15053 Slog.w(TAG, e); 15054 } 15055 } 15056 15057 void finishInstrumentationLocked(ProcessRecord app, int resultCode, Bundle results) { 15058 if (app.instrumentationWatcher != null) { 15059 try { 15060 // NOTE: IInstrumentationWatcher *must* be oneway here 15061 app.instrumentationWatcher.instrumentationFinished( 15062 app.instrumentationClass, 15063 resultCode, 15064 results); 15065 } catch (RemoteException e) { 15066 } 15067 } 15068 if (app.instrumentationUiAutomationConnection != null) { 15069 try { 15070 app.instrumentationUiAutomationConnection.shutdown(); 15071 } catch (RemoteException re) { 15072 /* ignore */ 15073 } 15074 // Only a UiAutomation can set this flag and now that 15075 // it is finished we make sure it is reset to its default. 15076 mUserIsMonkey = false; 15077 } 15078 app.instrumentationWatcher = null; 15079 app.instrumentationUiAutomationConnection = null; 15080 app.instrumentationClass = null; 15081 app.instrumentationInfo = null; 15082 app.instrumentationProfileFile = null; 15083 app.instrumentationArguments = null; 15084 15085 forceStopPackageLocked(app.info.packageName, -1, false, false, true, true, false, app.userId, 15086 "finished inst"); 15087 } 15088 15089 public void finishInstrumentation(IApplicationThread target, 15090 int resultCode, Bundle results) { 15091 int userId = UserHandle.getCallingUserId(); 15092 // Refuse possible leaked file descriptors 15093 if (results != null && results.hasFileDescriptors()) { 15094 throw new IllegalArgumentException("File descriptors passed in Intent"); 15095 } 15096 15097 synchronized(this) { 15098 ProcessRecord app = getRecordForAppLocked(target); 15099 if (app == null) { 15100 Slog.w(TAG, "finishInstrumentation: no app for " + target); 15101 return; 15102 } 15103 final long origId = Binder.clearCallingIdentity(); 15104 finishInstrumentationLocked(app, resultCode, results); 15105 Binder.restoreCallingIdentity(origId); 15106 } 15107 } 15108 15109 // ========================================================= 15110 // CONFIGURATION 15111 // ========================================================= 15112 15113 public ConfigurationInfo getDeviceConfigurationInfo() { 15114 ConfigurationInfo config = new ConfigurationInfo(); 15115 synchronized (this) { 15116 config.reqTouchScreen = mConfiguration.touchscreen; 15117 config.reqKeyboardType = mConfiguration.keyboard; 15118 config.reqNavigation = mConfiguration.navigation; 15119 if (mConfiguration.navigation == Configuration.NAVIGATION_DPAD 15120 || mConfiguration.navigation == Configuration.NAVIGATION_TRACKBALL) { 15121 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_FIVE_WAY_NAV; 15122 } 15123 if (mConfiguration.keyboard != Configuration.KEYBOARD_UNDEFINED 15124 && mConfiguration.keyboard != Configuration.KEYBOARD_NOKEYS) { 15125 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_HARD_KEYBOARD; 15126 } 15127 config.reqGlEsVersion = GL_ES_VERSION; 15128 } 15129 return config; 15130 } 15131 15132 ActivityStack getFocusedStack() { 15133 return mStackSupervisor.getFocusedStack(); 15134 } 15135 15136 public Configuration getConfiguration() { 15137 Configuration ci; 15138 synchronized(this) { 15139 ci = new Configuration(mConfiguration); 15140 } 15141 return ci; 15142 } 15143 15144 public void updatePersistentConfiguration(Configuration values) { 15145 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 15146 "updateConfiguration()"); 15147 enforceCallingPermission(android.Manifest.permission.WRITE_SETTINGS, 15148 "updateConfiguration()"); 15149 if (values == null) { 15150 throw new NullPointerException("Configuration must not be null"); 15151 } 15152 15153 synchronized(this) { 15154 final long origId = Binder.clearCallingIdentity(); 15155 updateConfigurationLocked(values, null, true, false); 15156 Binder.restoreCallingIdentity(origId); 15157 } 15158 } 15159 15160 public void updateConfiguration(Configuration values) { 15161 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 15162 "updateConfiguration()"); 15163 15164 synchronized(this) { 15165 if (values == null && mWindowManager != null) { 15166 // sentinel: fetch the current configuration from the window manager 15167 values = mWindowManager.computeNewConfiguration(); 15168 } 15169 15170 if (mWindowManager != null) { 15171 mProcessList.applyDisplaySize(mWindowManager); 15172 } 15173 15174 final long origId = Binder.clearCallingIdentity(); 15175 if (values != null) { 15176 Settings.System.clearConfiguration(values); 15177 } 15178 updateConfigurationLocked(values, null, false, false); 15179 Binder.restoreCallingIdentity(origId); 15180 } 15181 } 15182 15183 /** 15184 * Do either or both things: (1) change the current configuration, and (2) 15185 * make sure the given activity is running with the (now) current 15186 * configuration. Returns true if the activity has been left running, or 15187 * false if <var>starting</var> is being destroyed to match the new 15188 * configuration. 15189 * @param persistent TODO 15190 */ 15191 boolean updateConfigurationLocked(Configuration values, 15192 ActivityRecord starting, boolean persistent, boolean initLocale) { 15193 int changes = 0; 15194 15195 if (values != null) { 15196 Configuration newConfig = new Configuration(mConfiguration); 15197 changes = newConfig.updateFrom(values); 15198 if (changes != 0) { 15199 if (DEBUG_SWITCH || DEBUG_CONFIGURATION) { 15200 Slog.i(TAG, "Updating configuration to: " + values); 15201 } 15202 15203 EventLog.writeEvent(EventLogTags.CONFIGURATION_CHANGED, changes); 15204 15205 if (values.locale != null && !initLocale) { 15206 saveLocaleLocked(values.locale, 15207 !values.locale.equals(mConfiguration.locale), 15208 values.userSetLocale); 15209 } 15210 15211 mConfigurationSeq++; 15212 if (mConfigurationSeq <= 0) { 15213 mConfigurationSeq = 1; 15214 } 15215 newConfig.seq = mConfigurationSeq; 15216 mConfiguration = newConfig; 15217 Slog.i(TAG, "Config changes=" + Integer.toHexString(changes) + " " + newConfig); 15218 //mUsageStatsService.noteStartConfig(newConfig); 15219 15220 final Configuration configCopy = new Configuration(mConfiguration); 15221 15222 // TODO: If our config changes, should we auto dismiss any currently 15223 // showing dialogs? 15224 mShowDialogs = shouldShowDialogs(newConfig); 15225 15226 AttributeCache ac = AttributeCache.instance(); 15227 if (ac != null) { 15228 ac.updateConfiguration(configCopy); 15229 } 15230 15231 // Make sure all resources in our process are updated 15232 // right now, so that anyone who is going to retrieve 15233 // resource values after we return will be sure to get 15234 // the new ones. This is especially important during 15235 // boot, where the first config change needs to guarantee 15236 // all resources have that config before following boot 15237 // code is executed. 15238 mSystemThread.applyConfigurationToResources(configCopy); 15239 15240 if (persistent && Settings.System.hasInterestingConfigurationChanges(changes)) { 15241 Message msg = mHandler.obtainMessage(UPDATE_CONFIGURATION_MSG); 15242 msg.obj = new Configuration(configCopy); 15243 mHandler.sendMessage(msg); 15244 } 15245 15246 for (int i=mLruProcesses.size()-1; i>=0; i--) { 15247 ProcessRecord app = mLruProcesses.get(i); 15248 try { 15249 if (app.thread != null) { 15250 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Sending to proc " 15251 + app.processName + " new config " + mConfiguration); 15252 app.thread.scheduleConfigurationChanged(configCopy); 15253 } 15254 } catch (Exception e) { 15255 } 15256 } 15257 Intent intent = new Intent(Intent.ACTION_CONFIGURATION_CHANGED); 15258 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 15259 | Intent.FLAG_RECEIVER_REPLACE_PENDING 15260 | Intent.FLAG_RECEIVER_FOREGROUND); 15261 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, 15262 null, AppOpsManager.OP_NONE, false, false, MY_PID, 15263 Process.SYSTEM_UID, UserHandle.USER_ALL); 15264 if ((changes&ActivityInfo.CONFIG_LOCALE) != 0) { 15265 intent = new Intent(Intent.ACTION_LOCALE_CHANGED); 15266 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 15267 broadcastIntentLocked(null, null, intent, 15268 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 15269 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 15270 } 15271 } 15272 } 15273 15274 boolean kept = true; 15275 final ActivityStack mainStack = mStackSupervisor.getFocusedStack(); 15276 // mainStack is null during startup. 15277 if (mainStack != null) { 15278 if (changes != 0 && starting == null) { 15279 // If the configuration changed, and the caller is not already 15280 // in the process of starting an activity, then find the top 15281 // activity to check if its configuration needs to change. 15282 starting = mainStack.topRunningActivityLocked(null); 15283 } 15284 15285 if (starting != null) { 15286 kept = mainStack.ensureActivityConfigurationLocked(starting, changes); 15287 // And we need to make sure at this point that all other activities 15288 // are made visible with the correct configuration. 15289 mStackSupervisor.ensureActivitiesVisibleLocked(starting, changes); 15290 } 15291 } 15292 15293 if (values != null && mWindowManager != null) { 15294 mWindowManager.setNewConfiguration(mConfiguration); 15295 } 15296 15297 return kept; 15298 } 15299 15300 /** 15301 * Decide based on the configuration whether we should shouw the ANR, 15302 * crash, etc dialogs. The idea is that if there is no affordnace to 15303 * press the on-screen buttons, we shouldn't show the dialog. 15304 * 15305 * A thought: SystemUI might also want to get told about this, the Power 15306 * dialog / global actions also might want different behaviors. 15307 */ 15308 private static final boolean shouldShowDialogs(Configuration config) { 15309 return !(config.keyboard == Configuration.KEYBOARD_NOKEYS 15310 && config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH); 15311 } 15312 15313 /** 15314 * Save the locale. You must be inside a synchronized (this) block. 15315 */ 15316 private void saveLocaleLocked(Locale l, boolean isDiff, boolean isPersist) { 15317 if(isDiff) { 15318 SystemProperties.set("user.language", l.getLanguage()); 15319 SystemProperties.set("user.region", l.getCountry()); 15320 } 15321 15322 if(isPersist) { 15323 SystemProperties.set("persist.sys.language", l.getLanguage()); 15324 SystemProperties.set("persist.sys.country", l.getCountry()); 15325 SystemProperties.set("persist.sys.localevar", l.getVariant()); 15326 } 15327 } 15328 15329 @Override 15330 public boolean targetTaskAffinityMatchesActivity(IBinder token, String destAffinity) { 15331 ActivityRecord srec = ActivityRecord.forToken(token); 15332 return srec != null && srec.task.affinity != null && 15333 srec.task.affinity.equals(destAffinity); 15334 } 15335 15336 public boolean navigateUpTo(IBinder token, Intent destIntent, int resultCode, 15337 Intent resultData) { 15338 15339 synchronized (this) { 15340 final ActivityStack stack = ActivityRecord.getStackLocked(token); 15341 if (stack != null) { 15342 return stack.navigateUpToLocked(token, destIntent, resultCode, resultData); 15343 } 15344 return false; 15345 } 15346 } 15347 15348 public int getLaunchedFromUid(IBinder activityToken) { 15349 ActivityRecord srec = ActivityRecord.forToken(activityToken); 15350 if (srec == null) { 15351 return -1; 15352 } 15353 return srec.launchedFromUid; 15354 } 15355 15356 public String getLaunchedFromPackage(IBinder activityToken) { 15357 ActivityRecord srec = ActivityRecord.forToken(activityToken); 15358 if (srec == null) { 15359 return null; 15360 } 15361 return srec.launchedFromPackage; 15362 } 15363 15364 // ========================================================= 15365 // LIFETIME MANAGEMENT 15366 // ========================================================= 15367 15368 // Returns which broadcast queue the app is the current [or imminent] receiver 15369 // on, or 'null' if the app is not an active broadcast recipient. 15370 private BroadcastQueue isReceivingBroadcast(ProcessRecord app) { 15371 BroadcastRecord r = app.curReceiver; 15372 if (r != null) { 15373 return r.queue; 15374 } 15375 15376 // It's not the current receiver, but it might be starting up to become one 15377 synchronized (this) { 15378 for (BroadcastQueue queue : mBroadcastQueues) { 15379 r = queue.mPendingBroadcast; 15380 if (r != null && r.curApp == app) { 15381 // found it; report which queue it's in 15382 return queue; 15383 } 15384 } 15385 } 15386 15387 return null; 15388 } 15389 15390 private final int computeOomAdjLocked(ProcessRecord app, int cachedAdj, ProcessRecord TOP_APP, 15391 boolean doingAll, long now) { 15392 if (mAdjSeq == app.adjSeq) { 15393 // This adjustment has already been computed. 15394 return app.curRawAdj; 15395 } 15396 15397 if (app.thread == null) { 15398 app.adjSeq = mAdjSeq; 15399 app.curSchedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15400 app.curProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15401 return (app.curAdj=app.curRawAdj=ProcessList.CACHED_APP_MAX_ADJ); 15402 } 15403 15404 app.adjTypeCode = ActivityManager.RunningAppProcessInfo.REASON_UNKNOWN; 15405 app.adjSource = null; 15406 app.adjTarget = null; 15407 app.empty = false; 15408 app.cached = false; 15409 15410 final int activitiesSize = app.activities.size(); 15411 15412 if (app.maxAdj <= ProcessList.FOREGROUND_APP_ADJ) { 15413 // The max adjustment doesn't allow this app to be anything 15414 // below foreground, so it is not worth doing work for it. 15415 app.adjType = "fixed"; 15416 app.adjSeq = mAdjSeq; 15417 app.curRawAdj = app.maxAdj; 15418 app.foregroundActivities = false; 15419 app.curSchedGroup = Process.THREAD_GROUP_DEFAULT; 15420 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT; 15421 // System processes can do UI, and when they do we want to have 15422 // them trim their memory after the user leaves the UI. To 15423 // facilitate this, here we need to determine whether or not it 15424 // is currently showing UI. 15425 app.systemNoUi = true; 15426 if (app == TOP_APP) { 15427 app.systemNoUi = false; 15428 } else if (activitiesSize > 0) { 15429 for (int j = 0; j < activitiesSize; j++) { 15430 final ActivityRecord r = app.activities.get(j); 15431 if (r.visible) { 15432 app.systemNoUi = false; 15433 } 15434 } 15435 } 15436 if (!app.systemNoUi) { 15437 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT_UI; 15438 } 15439 return (app.curAdj=app.maxAdj); 15440 } 15441 15442 app.systemNoUi = false; 15443 15444 // Determine the importance of the process, starting with most 15445 // important to least, and assign an appropriate OOM adjustment. 15446 int adj; 15447 int schedGroup; 15448 int procState; 15449 boolean foregroundActivities = false; 15450 BroadcastQueue queue; 15451 if (app == TOP_APP) { 15452 // The last app on the list is the foreground app. 15453 adj = ProcessList.FOREGROUND_APP_ADJ; 15454 schedGroup = Process.THREAD_GROUP_DEFAULT; 15455 app.adjType = "top-activity"; 15456 foregroundActivities = true; 15457 procState = ActivityManager.PROCESS_STATE_TOP; 15458 } else if (app.instrumentationClass != null) { 15459 // Don't want to kill running instrumentation. 15460 adj = ProcessList.FOREGROUND_APP_ADJ; 15461 schedGroup = Process.THREAD_GROUP_DEFAULT; 15462 app.adjType = "instrumentation"; 15463 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15464 } else if ((queue = isReceivingBroadcast(app)) != null) { 15465 // An app that is currently receiving a broadcast also 15466 // counts as being in the foreground for OOM killer purposes. 15467 // It's placed in a sched group based on the nature of the 15468 // broadcast as reflected by which queue it's active in. 15469 adj = ProcessList.FOREGROUND_APP_ADJ; 15470 schedGroup = (queue == mFgBroadcastQueue) 15471 ? Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 15472 app.adjType = "broadcast"; 15473 procState = ActivityManager.PROCESS_STATE_RECEIVER; 15474 } else if (app.executingServices.size() > 0) { 15475 // An app that is currently executing a service callback also 15476 // counts as being in the foreground. 15477 adj = ProcessList.FOREGROUND_APP_ADJ; 15478 schedGroup = app.execServicesFg ? 15479 Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 15480 app.adjType = "exec-service"; 15481 procState = ActivityManager.PROCESS_STATE_SERVICE; 15482 //Slog.i(TAG, "EXEC " + (app.execServicesFg ? "FG" : "BG") + ": " + app); 15483 } else { 15484 // As far as we know the process is empty. We may change our mind later. 15485 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15486 // At this point we don't actually know the adjustment. Use the cached adj 15487 // value that the caller wants us to. 15488 adj = cachedAdj; 15489 procState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15490 app.cached = true; 15491 app.empty = true; 15492 app.adjType = "cch-empty"; 15493 } 15494 15495 // Examine all activities if not already foreground. 15496 if (!foregroundActivities && activitiesSize > 0) { 15497 for (int j = 0; j < activitiesSize; j++) { 15498 final ActivityRecord r = app.activities.get(j); 15499 if (r.app != app) { 15500 Slog.w(TAG, "Wtf, activity " + r + " in proc activity list not using proc " 15501 + app + "?!?"); 15502 continue; 15503 } 15504 if (r.visible) { 15505 // App has a visible activity; only upgrade adjustment. 15506 if (adj > ProcessList.VISIBLE_APP_ADJ) { 15507 adj = ProcessList.VISIBLE_APP_ADJ; 15508 app.adjType = "visible"; 15509 } 15510 if (procState > ActivityManager.PROCESS_STATE_TOP) { 15511 procState = ActivityManager.PROCESS_STATE_TOP; 15512 } 15513 schedGroup = Process.THREAD_GROUP_DEFAULT; 15514 app.cached = false; 15515 app.empty = false; 15516 foregroundActivities = true; 15517 break; 15518 } else if (r.state == ActivityState.PAUSING || r.state == ActivityState.PAUSED) { 15519 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15520 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15521 app.adjType = "pausing"; 15522 } 15523 if (procState > ActivityManager.PROCESS_STATE_TOP) { 15524 procState = ActivityManager.PROCESS_STATE_TOP; 15525 } 15526 schedGroup = Process.THREAD_GROUP_DEFAULT; 15527 app.cached = false; 15528 app.empty = false; 15529 foregroundActivities = true; 15530 } else if (r.state == ActivityState.STOPPING) { 15531 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15532 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15533 app.adjType = "stopping"; 15534 } 15535 // For the process state, we will at this point consider the 15536 // process to be cached. It will be cached either as an activity 15537 // or empty depending on whether the activity is finishing. We do 15538 // this so that we can treat the process as cached for purposes of 15539 // memory trimming (determing current memory level, trim command to 15540 // send to process) since there can be an arbitrary number of stopping 15541 // processes and they should soon all go into the cached state. 15542 if (!r.finishing) { 15543 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15544 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 15545 } 15546 } 15547 app.cached = false; 15548 app.empty = false; 15549 foregroundActivities = true; 15550 } else { 15551 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15552 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 15553 app.adjType = "cch-act"; 15554 } 15555 } 15556 } 15557 } 15558 15559 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15560 if (app.foregroundServices) { 15561 // The user is aware of this app, so make it visible. 15562 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15563 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15564 app.cached = false; 15565 app.adjType = "fg-service"; 15566 schedGroup = Process.THREAD_GROUP_DEFAULT; 15567 } else if (app.forcingToForeground != null) { 15568 // The user is aware of this app, so make it visible. 15569 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15570 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15571 app.cached = false; 15572 app.adjType = "force-fg"; 15573 app.adjSource = app.forcingToForeground; 15574 schedGroup = Process.THREAD_GROUP_DEFAULT; 15575 } 15576 } 15577 15578 if (app == mHeavyWeightProcess) { 15579 if (adj > ProcessList.HEAVY_WEIGHT_APP_ADJ) { 15580 // We don't want to kill the current heavy-weight process. 15581 adj = ProcessList.HEAVY_WEIGHT_APP_ADJ; 15582 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15583 app.cached = false; 15584 app.adjType = "heavy"; 15585 } 15586 if (procState > ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 15587 procState = ActivityManager.PROCESS_STATE_HEAVY_WEIGHT; 15588 } 15589 } 15590 15591 if (app == mHomeProcess) { 15592 if (adj > ProcessList.HOME_APP_ADJ) { 15593 // This process is hosting what we currently consider to be the 15594 // home app, so we don't want to let it go into the background. 15595 adj = ProcessList.HOME_APP_ADJ; 15596 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15597 app.cached = false; 15598 app.adjType = "home"; 15599 } 15600 if (procState > ActivityManager.PROCESS_STATE_HOME) { 15601 procState = ActivityManager.PROCESS_STATE_HOME; 15602 } 15603 } 15604 15605 if (app == mPreviousProcess && app.activities.size() > 0) { 15606 if (adj > ProcessList.PREVIOUS_APP_ADJ) { 15607 // This was the previous process that showed UI to the user. 15608 // We want to try to keep it around more aggressively, to give 15609 // a good experience around switching between two apps. 15610 adj = ProcessList.PREVIOUS_APP_ADJ; 15611 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 15612 app.cached = false; 15613 app.adjType = "previous"; 15614 } 15615 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 15616 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 15617 } 15618 } 15619 15620 if (false) Slog.i(TAG, "OOM " + app + ": initial adj=" + adj 15621 + " reason=" + app.adjType); 15622 15623 // By default, we use the computed adjustment. It may be changed if 15624 // there are applications dependent on our services or providers, but 15625 // this gives us a baseline and makes sure we don't get into an 15626 // infinite recursion. 15627 app.adjSeq = mAdjSeq; 15628 app.curRawAdj = adj; 15629 app.hasStartedServices = false; 15630 15631 if (mBackupTarget != null && app == mBackupTarget.app) { 15632 // If possible we want to avoid killing apps while they're being backed up 15633 if (adj > ProcessList.BACKUP_APP_ADJ) { 15634 if (DEBUG_BACKUP) Slog.v(TAG, "oom BACKUP_APP_ADJ for " + app); 15635 adj = ProcessList.BACKUP_APP_ADJ; 15636 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 15637 procState = ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 15638 } 15639 app.adjType = "backup"; 15640 app.cached = false; 15641 } 15642 if (procState > ActivityManager.PROCESS_STATE_BACKUP) { 15643 procState = ActivityManager.PROCESS_STATE_BACKUP; 15644 } 15645 } 15646 15647 boolean mayBeTop = false; 15648 15649 for (int is = app.services.size()-1; 15650 is >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15651 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15652 || procState > ActivityManager.PROCESS_STATE_TOP); 15653 is--) { 15654 ServiceRecord s = app.services.valueAt(is); 15655 if (s.startRequested) { 15656 app.hasStartedServices = true; 15657 if (procState > ActivityManager.PROCESS_STATE_SERVICE) { 15658 procState = ActivityManager.PROCESS_STATE_SERVICE; 15659 } 15660 if (app.hasShownUi && app != mHomeProcess) { 15661 // If this process has shown some UI, let it immediately 15662 // go to the LRU list because it may be pretty heavy with 15663 // UI stuff. We'll tag it with a label just to help 15664 // debug and understand what is going on. 15665 if (adj > ProcessList.SERVICE_ADJ) { 15666 app.adjType = "cch-started-ui-services"; 15667 } 15668 } else { 15669 if (now < (s.lastActivity + ActiveServices.MAX_SERVICE_INACTIVITY)) { 15670 // This service has seen some activity within 15671 // recent memory, so we will keep its process ahead 15672 // of the background processes. 15673 if (adj > ProcessList.SERVICE_ADJ) { 15674 adj = ProcessList.SERVICE_ADJ; 15675 app.adjType = "started-services"; 15676 app.cached = false; 15677 } 15678 } 15679 // If we have let the service slide into the background 15680 // state, still have some text describing what it is doing 15681 // even though the service no longer has an impact. 15682 if (adj > ProcessList.SERVICE_ADJ) { 15683 app.adjType = "cch-started-services"; 15684 } 15685 } 15686 } 15687 for (int conni = s.connections.size()-1; 15688 conni >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15689 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15690 || procState > ActivityManager.PROCESS_STATE_TOP); 15691 conni--) { 15692 ArrayList<ConnectionRecord> clist = s.connections.valueAt(conni); 15693 for (int i = 0; 15694 i < clist.size() && (adj > ProcessList.FOREGROUND_APP_ADJ 15695 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15696 || procState > ActivityManager.PROCESS_STATE_TOP); 15697 i++) { 15698 // XXX should compute this based on the max of 15699 // all connected clients. 15700 ConnectionRecord cr = clist.get(i); 15701 if (cr.binding.client == app) { 15702 // Binding to ourself is not interesting. 15703 continue; 15704 } 15705 if ((cr.flags&Context.BIND_WAIVE_PRIORITY) == 0) { 15706 ProcessRecord client = cr.binding.client; 15707 int clientAdj = computeOomAdjLocked(client, cachedAdj, 15708 TOP_APP, doingAll, now); 15709 int clientProcState = client.curProcState; 15710 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15711 // If the other app is cached for any reason, for purposes here 15712 // we are going to consider it empty. The specific cached state 15713 // doesn't propagate except under certain conditions. 15714 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15715 } 15716 String adjType = null; 15717 if ((cr.flags&Context.BIND_ALLOW_OOM_MANAGEMENT) != 0) { 15718 // Not doing bind OOM management, so treat 15719 // this guy more like a started service. 15720 if (app.hasShownUi && app != mHomeProcess) { 15721 // If this process has shown some UI, let it immediately 15722 // go to the LRU list because it may be pretty heavy with 15723 // UI stuff. We'll tag it with a label just to help 15724 // debug and understand what is going on. 15725 if (adj > clientAdj) { 15726 adjType = "cch-bound-ui-services"; 15727 } 15728 app.cached = false; 15729 clientAdj = adj; 15730 clientProcState = procState; 15731 } else { 15732 if (now >= (s.lastActivity 15733 + ActiveServices.MAX_SERVICE_INACTIVITY)) { 15734 // This service has not seen activity within 15735 // recent memory, so allow it to drop to the 15736 // LRU list if there is no other reason to keep 15737 // it around. We'll also tag it with a label just 15738 // to help debug and undertand what is going on. 15739 if (adj > clientAdj) { 15740 adjType = "cch-bound-services"; 15741 } 15742 clientAdj = adj; 15743 } 15744 } 15745 } 15746 if (adj > clientAdj) { 15747 // If this process has recently shown UI, and 15748 // the process that is binding to it is less 15749 // important than being visible, then we don't 15750 // care about the binding as much as we care 15751 // about letting this process get into the LRU 15752 // list to be killed and restarted if needed for 15753 // memory. 15754 if (app.hasShownUi && app != mHomeProcess 15755 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15756 adjType = "cch-bound-ui-services"; 15757 } else { 15758 if ((cr.flags&(Context.BIND_ABOVE_CLIENT 15759 |Context.BIND_IMPORTANT)) != 0) { 15760 adj = clientAdj; 15761 } else if ((cr.flags&Context.BIND_NOT_VISIBLE) != 0 15762 && clientAdj < ProcessList.PERCEPTIBLE_APP_ADJ 15763 && adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15764 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 15765 } else if (clientAdj > ProcessList.VISIBLE_APP_ADJ) { 15766 adj = clientAdj; 15767 } else { 15768 if (adj > ProcessList.VISIBLE_APP_ADJ) { 15769 adj = ProcessList.VISIBLE_APP_ADJ; 15770 } 15771 } 15772 if (!client.cached) { 15773 app.cached = false; 15774 } 15775 adjType = "service"; 15776 } 15777 } 15778 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 15779 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 15780 schedGroup = Process.THREAD_GROUP_DEFAULT; 15781 } 15782 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 15783 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 15784 // Special handling of clients who are in the top state. 15785 // We *may* want to consider this process to be in the 15786 // top state as well, but only if there is not another 15787 // reason for it to be running. Being on the top is a 15788 // special state, meaning you are specifically running 15789 // for the current top app. If the process is already 15790 // running in the background for some other reason, it 15791 // is more important to continue considering it to be 15792 // in the background state. 15793 mayBeTop = true; 15794 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15795 } else { 15796 // Special handling for above-top states (persistent 15797 // processes). These should not bring the current process 15798 // into the top state, since they are not on top. Instead 15799 // give them the best state after that. 15800 clientProcState = 15801 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15802 } 15803 } 15804 } else { 15805 if (clientProcState < 15806 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 15807 clientProcState = 15808 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 15809 } 15810 } 15811 if (procState > clientProcState) { 15812 procState = clientProcState; 15813 } 15814 if (procState < ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 15815 && (cr.flags&Context.BIND_SHOWING_UI) != 0) { 15816 app.pendingUiClean = true; 15817 } 15818 if (adjType != null) { 15819 app.adjType = adjType; 15820 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15821 .REASON_SERVICE_IN_USE; 15822 app.adjSource = cr.binding.client; 15823 app.adjSourceProcState = clientProcState; 15824 app.adjTarget = s.name; 15825 } 15826 } 15827 if ((cr.flags&Context.BIND_TREAT_LIKE_ACTIVITY) != 0) { 15828 app.treatLikeActivity = true; 15829 } 15830 final ActivityRecord a = cr.activity; 15831 if ((cr.flags&Context.BIND_ADJUST_WITH_ACTIVITY) != 0) { 15832 if (a != null && adj > ProcessList.FOREGROUND_APP_ADJ && 15833 (a.visible || a.state == ActivityState.RESUMED 15834 || a.state == ActivityState.PAUSING)) { 15835 adj = ProcessList.FOREGROUND_APP_ADJ; 15836 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 15837 schedGroup = Process.THREAD_GROUP_DEFAULT; 15838 } 15839 app.cached = false; 15840 app.adjType = "service"; 15841 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15842 .REASON_SERVICE_IN_USE; 15843 app.adjSource = a; 15844 app.adjSourceProcState = procState; 15845 app.adjTarget = s.name; 15846 } 15847 } 15848 } 15849 } 15850 } 15851 15852 for (int provi = app.pubProviders.size()-1; 15853 provi >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15854 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15855 || procState > ActivityManager.PROCESS_STATE_TOP); 15856 provi--) { 15857 ContentProviderRecord cpr = app.pubProviders.valueAt(provi); 15858 for (int i = cpr.connections.size()-1; 15859 i >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15860 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15861 || procState > ActivityManager.PROCESS_STATE_TOP); 15862 i--) { 15863 ContentProviderConnection conn = cpr.connections.get(i); 15864 ProcessRecord client = conn.client; 15865 if (client == app) { 15866 // Being our own client is not interesting. 15867 continue; 15868 } 15869 int clientAdj = computeOomAdjLocked(client, cachedAdj, TOP_APP, doingAll, now); 15870 int clientProcState = client.curProcState; 15871 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15872 // If the other app is cached for any reason, for purposes here 15873 // we are going to consider it empty. 15874 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15875 } 15876 if (adj > clientAdj) { 15877 if (app.hasShownUi && app != mHomeProcess 15878 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15879 app.adjType = "cch-ui-provider"; 15880 } else { 15881 adj = clientAdj > ProcessList.FOREGROUND_APP_ADJ 15882 ? clientAdj : ProcessList.FOREGROUND_APP_ADJ; 15883 app.adjType = "provider"; 15884 } 15885 app.cached &= client.cached; 15886 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15887 .REASON_PROVIDER_IN_USE; 15888 app.adjSource = client; 15889 app.adjSourceProcState = clientProcState; 15890 app.adjTarget = cpr.name; 15891 } 15892 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 15893 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 15894 // Special handling of clients who are in the top state. 15895 // We *may* want to consider this process to be in the 15896 // top state as well, but only if there is not another 15897 // reason for it to be running. Being on the top is a 15898 // special state, meaning you are specifically running 15899 // for the current top app. If the process is already 15900 // running in the background for some other reason, it 15901 // is more important to continue considering it to be 15902 // in the background state. 15903 mayBeTop = true; 15904 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15905 } else { 15906 // Special handling for above-top states (persistent 15907 // processes). These should not bring the current process 15908 // into the top state, since they are not on top. Instead 15909 // give them the best state after that. 15910 clientProcState = 15911 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15912 } 15913 } 15914 if (procState > clientProcState) { 15915 procState = clientProcState; 15916 } 15917 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 15918 schedGroup = Process.THREAD_GROUP_DEFAULT; 15919 } 15920 } 15921 // If the provider has external (non-framework) process 15922 // dependencies, ensure that its adjustment is at least 15923 // FOREGROUND_APP_ADJ. 15924 if (cpr.hasExternalProcessHandles()) { 15925 if (adj > ProcessList.FOREGROUND_APP_ADJ) { 15926 adj = ProcessList.FOREGROUND_APP_ADJ; 15927 schedGroup = Process.THREAD_GROUP_DEFAULT; 15928 app.cached = false; 15929 app.adjType = "provider"; 15930 app.adjTarget = cpr.name; 15931 } 15932 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) { 15933 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15934 } 15935 } 15936 } 15937 15938 if (mayBeTop && procState > ActivityManager.PROCESS_STATE_TOP) { 15939 // A client of one of our services or providers is in the top state. We 15940 // *may* want to be in the top state, but not if we are already running in 15941 // the background for some other reason. For the decision here, we are going 15942 // to pick out a few specific states that we want to remain in when a client 15943 // is top (states that tend to be longer-term) and otherwise allow it to go 15944 // to the top state. 15945 switch (procState) { 15946 case ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND: 15947 case ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND: 15948 case ActivityManager.PROCESS_STATE_SERVICE: 15949 // These all are longer-term states, so pull them up to the top 15950 // of the background states, but not all the way to the top state. 15951 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15952 break; 15953 default: 15954 // Otherwise, top is a better choice, so take it. 15955 procState = ActivityManager.PROCESS_STATE_TOP; 15956 break; 15957 } 15958 } 15959 15960 if (procState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 15961 if (app.hasClientActivities) { 15962 // This is a cached process, but with client activities. Mark it so. 15963 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT; 15964 app.adjType = "cch-client-act"; 15965 } else if (app.treatLikeActivity) { 15966 // This is a cached process, but somebody wants us to treat it like it has 15967 // an activity, okay! 15968 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 15969 app.adjType = "cch-as-act"; 15970 } 15971 } 15972 15973 if (adj == ProcessList.SERVICE_ADJ) { 15974 if (doingAll) { 15975 app.serviceb = mNewNumAServiceProcs > (mNumServiceProcs/3); 15976 mNewNumServiceProcs++; 15977 //Slog.i(TAG, "ADJ " + app + " serviceb=" + app.serviceb); 15978 if (!app.serviceb) { 15979 // This service isn't far enough down on the LRU list to 15980 // normally be a B service, but if we are low on RAM and it 15981 // is large we want to force it down since we would prefer to 15982 // keep launcher over it. 15983 if (mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 15984 && app.lastPss >= mProcessList.getCachedRestoreThresholdKb()) { 15985 app.serviceHighRam = true; 15986 app.serviceb = true; 15987 //Slog.i(TAG, "ADJ " + app + " high ram!"); 15988 } else { 15989 mNewNumAServiceProcs++; 15990 //Slog.i(TAG, "ADJ " + app + " not high ram!"); 15991 } 15992 } else { 15993 app.serviceHighRam = false; 15994 } 15995 } 15996 if (app.serviceb) { 15997 adj = ProcessList.SERVICE_B_ADJ; 15998 } 15999 } 16000 16001 app.curRawAdj = adj; 16002 16003 //Slog.i(TAG, "OOM ADJ " + app + ": pid=" + app.pid + 16004 // " adj=" + adj + " curAdj=" + app.curAdj + " maxAdj=" + app.maxAdj); 16005 if (adj > app.maxAdj) { 16006 adj = app.maxAdj; 16007 if (app.maxAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 16008 schedGroup = Process.THREAD_GROUP_DEFAULT; 16009 } 16010 } 16011 16012 // Do final modification to adj. Everything we do between here and applying 16013 // the final setAdj must be done in this function, because we will also use 16014 // it when computing the final cached adj later. Note that we don't need to 16015 // worry about this for max adj above, since max adj will always be used to 16016 // keep it out of the cached vaues. 16017 app.curAdj = app.modifyRawOomAdj(adj); 16018 app.curSchedGroup = schedGroup; 16019 app.curProcState = procState; 16020 app.foregroundActivities = foregroundActivities; 16021 16022 return app.curRawAdj; 16023 } 16024 16025 /** 16026 * Schedule PSS collection of a process. 16027 */ 16028 void requestPssLocked(ProcessRecord proc, int procState) { 16029 if (mPendingPssProcesses.contains(proc)) { 16030 return; 16031 } 16032 if (mPendingPssProcesses.size() == 0) { 16033 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 16034 } 16035 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of: " + proc); 16036 proc.pssProcState = procState; 16037 mPendingPssProcesses.add(proc); 16038 } 16039 16040 /** 16041 * Schedule PSS collection of all processes. 16042 */ 16043 void requestPssAllProcsLocked(long now, boolean always, boolean memLowered) { 16044 if (!always) { 16045 if (now < (mLastFullPssTime + 16046 (memLowered ? FULL_PSS_LOWERED_INTERVAL : FULL_PSS_MIN_INTERVAL))) { 16047 return; 16048 } 16049 } 16050 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of all procs! memLowered=" + memLowered); 16051 mLastFullPssTime = now; 16052 mFullPssPending = true; 16053 mPendingPssProcesses.ensureCapacity(mLruProcesses.size()); 16054 mPendingPssProcesses.clear(); 16055 for (int i=mLruProcesses.size()-1; i>=0; i--) { 16056 ProcessRecord app = mLruProcesses.get(i); 16057 if (memLowered || now > (app.lastStateTime+ProcessList.PSS_ALL_INTERVAL)) { 16058 app.pssProcState = app.setProcState; 16059 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 16060 isSleeping(), now); 16061 mPendingPssProcesses.add(app); 16062 } 16063 } 16064 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 16065 } 16066 16067 /** 16068 * Ask a given process to GC right now. 16069 */ 16070 final void performAppGcLocked(ProcessRecord app) { 16071 try { 16072 app.lastRequestedGc = SystemClock.uptimeMillis(); 16073 if (app.thread != null) { 16074 if (app.reportLowMemory) { 16075 app.reportLowMemory = false; 16076 app.thread.scheduleLowMemory(); 16077 } else { 16078 app.thread.processInBackground(); 16079 } 16080 } 16081 } catch (Exception e) { 16082 // whatever. 16083 } 16084 } 16085 16086 /** 16087 * Returns true if things are idle enough to perform GCs. 16088 */ 16089 private final boolean canGcNowLocked() { 16090 boolean processingBroadcasts = false; 16091 for (BroadcastQueue q : mBroadcastQueues) { 16092 if (q.mParallelBroadcasts.size() != 0 || q.mOrderedBroadcasts.size() != 0) { 16093 processingBroadcasts = true; 16094 } 16095 } 16096 return !processingBroadcasts 16097 && (isSleeping() || mStackSupervisor.allResumedActivitiesIdle()); 16098 } 16099 16100 /** 16101 * Perform GCs on all processes that are waiting for it, but only 16102 * if things are idle. 16103 */ 16104 final void performAppGcsLocked() { 16105 final int N = mProcessesToGc.size(); 16106 if (N <= 0) { 16107 return; 16108 } 16109 if (canGcNowLocked()) { 16110 while (mProcessesToGc.size() > 0) { 16111 ProcessRecord proc = mProcessesToGc.remove(0); 16112 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ || proc.reportLowMemory) { 16113 if ((proc.lastRequestedGc+GC_MIN_INTERVAL) 16114 <= SystemClock.uptimeMillis()) { 16115 // To avoid spamming the system, we will GC processes one 16116 // at a time, waiting a few seconds between each. 16117 performAppGcLocked(proc); 16118 scheduleAppGcsLocked(); 16119 return; 16120 } else { 16121 // It hasn't been long enough since we last GCed this 16122 // process... put it in the list to wait for its time. 16123 addProcessToGcListLocked(proc); 16124 break; 16125 } 16126 } 16127 } 16128 16129 scheduleAppGcsLocked(); 16130 } 16131 } 16132 16133 /** 16134 * If all looks good, perform GCs on all processes waiting for them. 16135 */ 16136 final void performAppGcsIfAppropriateLocked() { 16137 if (canGcNowLocked()) { 16138 performAppGcsLocked(); 16139 return; 16140 } 16141 // Still not idle, wait some more. 16142 scheduleAppGcsLocked(); 16143 } 16144 16145 /** 16146 * Schedule the execution of all pending app GCs. 16147 */ 16148 final void scheduleAppGcsLocked() { 16149 mHandler.removeMessages(GC_BACKGROUND_PROCESSES_MSG); 16150 16151 if (mProcessesToGc.size() > 0) { 16152 // Schedule a GC for the time to the next process. 16153 ProcessRecord proc = mProcessesToGc.get(0); 16154 Message msg = mHandler.obtainMessage(GC_BACKGROUND_PROCESSES_MSG); 16155 16156 long when = proc.lastRequestedGc + GC_MIN_INTERVAL; 16157 long now = SystemClock.uptimeMillis(); 16158 if (when < (now+GC_TIMEOUT)) { 16159 when = now + GC_TIMEOUT; 16160 } 16161 mHandler.sendMessageAtTime(msg, when); 16162 } 16163 } 16164 16165 /** 16166 * Add a process to the array of processes waiting to be GCed. Keeps the 16167 * list in sorted order by the last GC time. The process can't already be 16168 * on the list. 16169 */ 16170 final void addProcessToGcListLocked(ProcessRecord proc) { 16171 boolean added = false; 16172 for (int i=mProcessesToGc.size()-1; i>=0; i--) { 16173 if (mProcessesToGc.get(i).lastRequestedGc < 16174 proc.lastRequestedGc) { 16175 added = true; 16176 mProcessesToGc.add(i+1, proc); 16177 break; 16178 } 16179 } 16180 if (!added) { 16181 mProcessesToGc.add(0, proc); 16182 } 16183 } 16184 16185 /** 16186 * Set up to ask a process to GC itself. This will either do it 16187 * immediately, or put it on the list of processes to gc the next 16188 * time things are idle. 16189 */ 16190 final void scheduleAppGcLocked(ProcessRecord app) { 16191 long now = SystemClock.uptimeMillis(); 16192 if ((app.lastRequestedGc+GC_MIN_INTERVAL) > now) { 16193 return; 16194 } 16195 if (!mProcessesToGc.contains(app)) { 16196 addProcessToGcListLocked(app); 16197 scheduleAppGcsLocked(); 16198 } 16199 } 16200 16201 final void checkExcessivePowerUsageLocked(boolean doKills) { 16202 updateCpuStatsNow(); 16203 16204 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 16205 boolean doWakeKills = doKills; 16206 boolean doCpuKills = doKills; 16207 if (mLastPowerCheckRealtime == 0) { 16208 doWakeKills = false; 16209 } 16210 if (mLastPowerCheckUptime == 0) { 16211 doCpuKills = false; 16212 } 16213 if (stats.isScreenOn()) { 16214 doWakeKills = false; 16215 } 16216 final long curRealtime = SystemClock.elapsedRealtime(); 16217 final long realtimeSince = curRealtime - mLastPowerCheckRealtime; 16218 final long curUptime = SystemClock.uptimeMillis(); 16219 final long uptimeSince = curUptime - mLastPowerCheckUptime; 16220 mLastPowerCheckRealtime = curRealtime; 16221 mLastPowerCheckUptime = curUptime; 16222 if (realtimeSince < WAKE_LOCK_MIN_CHECK_DURATION) { 16223 doWakeKills = false; 16224 } 16225 if (uptimeSince < CPU_MIN_CHECK_DURATION) { 16226 doCpuKills = false; 16227 } 16228 int i = mLruProcesses.size(); 16229 while (i > 0) { 16230 i--; 16231 ProcessRecord app = mLruProcesses.get(i); 16232 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 16233 long wtime; 16234 synchronized (stats) { 16235 wtime = stats.getProcessWakeTime(app.info.uid, 16236 app.pid, curRealtime); 16237 } 16238 long wtimeUsed = wtime - app.lastWakeTime; 16239 long cputimeUsed = app.curCpuTime - app.lastCpuTime; 16240 if (DEBUG_POWER) { 16241 StringBuilder sb = new StringBuilder(128); 16242 sb.append("Wake for "); 16243 app.toShortString(sb); 16244 sb.append(": over "); 16245 TimeUtils.formatDuration(realtimeSince, sb); 16246 sb.append(" used "); 16247 TimeUtils.formatDuration(wtimeUsed, sb); 16248 sb.append(" ("); 16249 sb.append((wtimeUsed*100)/realtimeSince); 16250 sb.append("%)"); 16251 Slog.i(TAG, sb.toString()); 16252 sb.setLength(0); 16253 sb.append("CPU for "); 16254 app.toShortString(sb); 16255 sb.append(": over "); 16256 TimeUtils.formatDuration(uptimeSince, sb); 16257 sb.append(" used "); 16258 TimeUtils.formatDuration(cputimeUsed, sb); 16259 sb.append(" ("); 16260 sb.append((cputimeUsed*100)/uptimeSince); 16261 sb.append("%)"); 16262 Slog.i(TAG, sb.toString()); 16263 } 16264 // If a process has held a wake lock for more 16265 // than 50% of the time during this period, 16266 // that sounds bad. Kill! 16267 if (doWakeKills && realtimeSince > 0 16268 && ((wtimeUsed*100)/realtimeSince) >= 50) { 16269 synchronized (stats) { 16270 stats.reportExcessiveWakeLocked(app.info.uid, app.processName, 16271 realtimeSince, wtimeUsed); 16272 } 16273 killUnneededProcessLocked(app, "excessive wake held " + wtimeUsed 16274 + " during " + realtimeSince); 16275 app.baseProcessTracker.reportExcessiveWake(app.pkgList); 16276 } else if (doCpuKills && uptimeSince > 0 16277 && ((cputimeUsed*100)/uptimeSince) >= 25) { 16278 synchronized (stats) { 16279 stats.reportExcessiveCpuLocked(app.info.uid, app.processName, 16280 uptimeSince, cputimeUsed); 16281 } 16282 killUnneededProcessLocked(app, "excessive cpu " + cputimeUsed 16283 + " during " + uptimeSince); 16284 app.baseProcessTracker.reportExcessiveCpu(app.pkgList); 16285 } else { 16286 app.lastWakeTime = wtime; 16287 app.lastCpuTime = app.curCpuTime; 16288 } 16289 } 16290 } 16291 } 16292 16293 private final boolean applyOomAdjLocked(ProcessRecord app, 16294 ProcessRecord TOP_APP, boolean doingAll, long now) { 16295 boolean success = true; 16296 16297 if (app.curRawAdj != app.setRawAdj) { 16298 app.setRawAdj = app.curRawAdj; 16299 } 16300 16301 int changes = 0; 16302 16303 if (app.curAdj != app.setAdj) { 16304 ProcessList.setOomAdj(app.pid, app.info.uid, app.curAdj); 16305 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v( 16306 TAG, "Set " + app.pid + " " + app.processName + 16307 " adj " + app.curAdj + ": " + app.adjType); 16308 app.setAdj = app.curAdj; 16309 } 16310 16311 if (app.setSchedGroup != app.curSchedGroup) { 16312 app.setSchedGroup = app.curSchedGroup; 16313 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16314 "Setting process group of " + app.processName 16315 + " to " + app.curSchedGroup); 16316 if (app.waitingToKill != null && 16317 app.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 16318 killUnneededProcessLocked(app, app.waitingToKill); 16319 success = false; 16320 } else { 16321 if (true) { 16322 long oldId = Binder.clearCallingIdentity(); 16323 try { 16324 Process.setProcessGroup(app.pid, app.curSchedGroup); 16325 } catch (Exception e) { 16326 Slog.w(TAG, "Failed setting process group of " + app.pid 16327 + " to " + app.curSchedGroup); 16328 e.printStackTrace(); 16329 } finally { 16330 Binder.restoreCallingIdentity(oldId); 16331 } 16332 } else { 16333 if (app.thread != null) { 16334 try { 16335 app.thread.setSchedulingGroup(app.curSchedGroup); 16336 } catch (RemoteException e) { 16337 } 16338 } 16339 } 16340 Process.setSwappiness(app.pid, 16341 app.curSchedGroup <= Process.THREAD_GROUP_BG_NONINTERACTIVE); 16342 } 16343 } 16344 if (app.repForegroundActivities != app.foregroundActivities) { 16345 app.repForegroundActivities = app.foregroundActivities; 16346 changes |= ProcessChangeItem.CHANGE_ACTIVITIES; 16347 } 16348 if (app.repProcState != app.curProcState) { 16349 app.repProcState = app.curProcState; 16350 changes |= ProcessChangeItem.CHANGE_PROCESS_STATE; 16351 if (app.thread != null) { 16352 try { 16353 if (false) { 16354 //RuntimeException h = new RuntimeException("here"); 16355 Slog.i(TAG, "Sending new process state " + app.repProcState 16356 + " to " + app /*, h*/); 16357 } 16358 app.thread.setProcessState(app.repProcState); 16359 } catch (RemoteException e) { 16360 } 16361 } 16362 } 16363 if (app.setProcState < 0 || ProcessList.procStatesDifferForMem(app.curProcState, 16364 app.setProcState)) { 16365 app.lastStateTime = now; 16366 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 16367 isSleeping(), now); 16368 if (DEBUG_PSS) Slog.d(TAG, "Process state change from " 16369 + ProcessList.makeProcStateString(app.setProcState) + " to " 16370 + ProcessList.makeProcStateString(app.curProcState) + " next pss in " 16371 + (app.nextPssTime-now) + ": " + app); 16372 } else { 16373 if (now > app.nextPssTime || (now > (app.lastPssTime+ProcessList.PSS_MAX_INTERVAL) 16374 && now > (app.lastStateTime+ProcessList.PSS_MIN_TIME_FROM_STATE_CHANGE))) { 16375 requestPssLocked(app, app.setProcState); 16376 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, false, 16377 isSleeping(), now); 16378 } else if (false && DEBUG_PSS) { 16379 Slog.d(TAG, "Not requesting PSS of " + app + ": next=" + (app.nextPssTime-now)); 16380 } 16381 } 16382 if (app.setProcState != app.curProcState) { 16383 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16384 "Proc state change of " + app.processName 16385 + " to " + app.curProcState); 16386 boolean setImportant = app.setProcState < ActivityManager.PROCESS_STATE_SERVICE; 16387 boolean curImportant = app.curProcState < ActivityManager.PROCESS_STATE_SERVICE; 16388 if (setImportant && !curImportant) { 16389 // This app is no longer something we consider important enough to allow to 16390 // use arbitrary amounts of battery power. Note 16391 // its current wake lock time to later know to kill it if 16392 // it is not behaving well. 16393 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 16394 synchronized (stats) { 16395 app.lastWakeTime = stats.getProcessWakeTime(app.info.uid, 16396 app.pid, SystemClock.elapsedRealtime()); 16397 } 16398 app.lastCpuTime = app.curCpuTime; 16399 16400 } 16401 app.setProcState = app.curProcState; 16402 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 16403 app.notCachedSinceIdle = false; 16404 } 16405 if (!doingAll) { 16406 setProcessTrackerStateLocked(app, mProcessStats.getMemFactorLocked(), now); 16407 } else { 16408 app.procStateChanged = true; 16409 } 16410 } 16411 16412 if (changes != 0) { 16413 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Changes in " + app + ": " + changes); 16414 int i = mPendingProcessChanges.size()-1; 16415 ProcessChangeItem item = null; 16416 while (i >= 0) { 16417 item = mPendingProcessChanges.get(i); 16418 if (item.pid == app.pid) { 16419 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Re-using existing item: " + item); 16420 break; 16421 } 16422 i--; 16423 } 16424 if (i < 0) { 16425 // No existing item in pending changes; need a new one. 16426 final int NA = mAvailProcessChanges.size(); 16427 if (NA > 0) { 16428 item = mAvailProcessChanges.remove(NA-1); 16429 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Retreiving available item: " + item); 16430 } else { 16431 item = new ProcessChangeItem(); 16432 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Allocating new item: " + item); 16433 } 16434 item.changes = 0; 16435 item.pid = app.pid; 16436 item.uid = app.info.uid; 16437 if (mPendingProcessChanges.size() == 0) { 16438 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, 16439 "*** Enqueueing dispatch processes changed!"); 16440 mHandler.obtainMessage(DISPATCH_PROCESSES_CHANGED).sendToTarget(); 16441 } 16442 mPendingProcessChanges.add(item); 16443 } 16444 item.changes |= changes; 16445 item.processState = app.repProcState; 16446 item.foregroundActivities = app.repForegroundActivities; 16447 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Item " 16448 + Integer.toHexString(System.identityHashCode(item)) 16449 + " " + app.toShortString() + ": changes=" + item.changes 16450 + " procState=" + item.processState 16451 + " foreground=" + item.foregroundActivities 16452 + " type=" + app.adjType + " source=" + app.adjSource 16453 + " target=" + app.adjTarget); 16454 } 16455 16456 return success; 16457 } 16458 16459 private final void setProcessTrackerStateLocked(ProcessRecord proc, int memFactor, long now) { 16460 if (proc.thread != null) { 16461 if (proc.baseProcessTracker != null) { 16462 proc.baseProcessTracker.setState(proc.repProcState, memFactor, now, proc.pkgList); 16463 } 16464 if (proc.repProcState >= 0) { 16465 mBatteryStatsService.noteProcessState(proc.processName, proc.info.uid, 16466 proc.repProcState); 16467 } 16468 } 16469 } 16470 16471 private final boolean updateOomAdjLocked(ProcessRecord app, int cachedAdj, 16472 ProcessRecord TOP_APP, boolean doingAll, long now) { 16473 if (app.thread == null) { 16474 return false; 16475 } 16476 16477 computeOomAdjLocked(app, cachedAdj, TOP_APP, doingAll, now); 16478 16479 return applyOomAdjLocked(app, TOP_APP, doingAll, now); 16480 } 16481 16482 final void updateProcessForegroundLocked(ProcessRecord proc, boolean isForeground, 16483 boolean oomAdj) { 16484 if (isForeground != proc.foregroundServices) { 16485 proc.foregroundServices = isForeground; 16486 ArrayList<ProcessRecord> curProcs = mForegroundPackages.get(proc.info.packageName, 16487 proc.info.uid); 16488 if (isForeground) { 16489 if (curProcs == null) { 16490 curProcs = new ArrayList<ProcessRecord>(); 16491 mForegroundPackages.put(proc.info.packageName, proc.info.uid, curProcs); 16492 } 16493 if (!curProcs.contains(proc)) { 16494 curProcs.add(proc); 16495 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_FOREGROUND_START, 16496 proc.info.packageName, proc.info.uid); 16497 } 16498 } else { 16499 if (curProcs != null) { 16500 if (curProcs.remove(proc)) { 16501 mBatteryStatsService.noteEvent( 16502 BatteryStats.HistoryItem.EVENT_FOREGROUND_FINISH, 16503 proc.info.packageName, proc.info.uid); 16504 if (curProcs.size() <= 0) { 16505 mForegroundPackages.remove(proc.info.packageName, proc.info.uid); 16506 } 16507 } 16508 } 16509 } 16510 if (oomAdj) { 16511 updateOomAdjLocked(); 16512 } 16513 } 16514 } 16515 16516 private final ActivityRecord resumedAppLocked() { 16517 ActivityRecord act = mStackSupervisor.resumedAppLocked(); 16518 String pkg; 16519 int uid; 16520 if (act != null) { 16521 pkg = act.packageName; 16522 uid = act.info.applicationInfo.uid; 16523 } else { 16524 pkg = null; 16525 uid = -1; 16526 } 16527 // Has the UID or resumed package name changed? 16528 if (uid != mCurResumedUid || (pkg != mCurResumedPackage 16529 && (pkg == null || !pkg.equals(mCurResumedPackage)))) { 16530 if (mCurResumedPackage != null) { 16531 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_FINISH, 16532 mCurResumedPackage, mCurResumedUid); 16533 } 16534 mCurResumedPackage = pkg; 16535 mCurResumedUid = uid; 16536 if (mCurResumedPackage != null) { 16537 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_START, 16538 mCurResumedPackage, mCurResumedUid); 16539 } 16540 } 16541 return act; 16542 } 16543 16544 final boolean updateOomAdjLocked(ProcessRecord app) { 16545 final ActivityRecord TOP_ACT = resumedAppLocked(); 16546 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 16547 final boolean wasCached = app.cached; 16548 16549 mAdjSeq++; 16550 16551 // This is the desired cached adjusment we want to tell it to use. 16552 // If our app is currently cached, we know it, and that is it. Otherwise, 16553 // we don't know it yet, and it needs to now be cached we will then 16554 // need to do a complete oom adj. 16555 final int cachedAdj = app.curRawAdj >= ProcessList.CACHED_APP_MIN_ADJ 16556 ? app.curRawAdj : ProcessList.UNKNOWN_ADJ; 16557 boolean success = updateOomAdjLocked(app, cachedAdj, TOP_APP, false, 16558 SystemClock.uptimeMillis()); 16559 if (wasCached != app.cached || app.curRawAdj == ProcessList.UNKNOWN_ADJ) { 16560 // Changed to/from cached state, so apps after it in the LRU 16561 // list may also be changed. 16562 updateOomAdjLocked(); 16563 } 16564 return success; 16565 } 16566 16567 final void updateOomAdjLocked() { 16568 final ActivityRecord TOP_ACT = resumedAppLocked(); 16569 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 16570 final long now = SystemClock.uptimeMillis(); 16571 final long oldTime = now - ProcessList.MAX_EMPTY_TIME; 16572 final int N = mLruProcesses.size(); 16573 16574 if (false) { 16575 RuntimeException e = new RuntimeException(); 16576 e.fillInStackTrace(); 16577 Slog.i(TAG, "updateOomAdj: top=" + TOP_ACT, e); 16578 } 16579 16580 mAdjSeq++; 16581 mNewNumServiceProcs = 0; 16582 mNewNumAServiceProcs = 0; 16583 16584 final int emptyProcessLimit; 16585 final int cachedProcessLimit; 16586 if (mProcessLimit <= 0) { 16587 emptyProcessLimit = cachedProcessLimit = 0; 16588 } else if (mProcessLimit == 1) { 16589 emptyProcessLimit = 1; 16590 cachedProcessLimit = 0; 16591 } else { 16592 emptyProcessLimit = ProcessList.computeEmptyProcessLimit(mProcessLimit); 16593 cachedProcessLimit = mProcessLimit - emptyProcessLimit; 16594 } 16595 16596 // Let's determine how many processes we have running vs. 16597 // how many slots we have for background processes; we may want 16598 // to put multiple processes in a slot of there are enough of 16599 // them. 16600 int numSlots = (ProcessList.CACHED_APP_MAX_ADJ 16601 - ProcessList.CACHED_APP_MIN_ADJ + 1) / 2; 16602 int numEmptyProcs = N - mNumNonCachedProcs - mNumCachedHiddenProcs; 16603 if (numEmptyProcs > cachedProcessLimit) { 16604 // If there are more empty processes than our limit on cached 16605 // processes, then use the cached process limit for the factor. 16606 // This ensures that the really old empty processes get pushed 16607 // down to the bottom, so if we are running low on memory we will 16608 // have a better chance at keeping around more cached processes 16609 // instead of a gazillion empty processes. 16610 numEmptyProcs = cachedProcessLimit; 16611 } 16612 int emptyFactor = numEmptyProcs/numSlots; 16613 if (emptyFactor < 1) emptyFactor = 1; 16614 int cachedFactor = (mNumCachedHiddenProcs > 0 ? mNumCachedHiddenProcs : 1)/numSlots; 16615 if (cachedFactor < 1) cachedFactor = 1; 16616 int stepCached = 0; 16617 int stepEmpty = 0; 16618 int numCached = 0; 16619 int numEmpty = 0; 16620 int numTrimming = 0; 16621 16622 mNumNonCachedProcs = 0; 16623 mNumCachedHiddenProcs = 0; 16624 16625 // First update the OOM adjustment for each of the 16626 // application processes based on their current state. 16627 int curCachedAdj = ProcessList.CACHED_APP_MIN_ADJ; 16628 int nextCachedAdj = curCachedAdj+1; 16629 int curEmptyAdj = ProcessList.CACHED_APP_MIN_ADJ; 16630 int nextEmptyAdj = curEmptyAdj+2; 16631 for (int i=N-1; i>=0; i--) { 16632 ProcessRecord app = mLruProcesses.get(i); 16633 if (!app.killedByAm && app.thread != null) { 16634 app.procStateChanged = false; 16635 computeOomAdjLocked(app, ProcessList.UNKNOWN_ADJ, TOP_APP, true, now); 16636 16637 // If we haven't yet assigned the final cached adj 16638 // to the process, do that now. 16639 if (app.curAdj >= ProcessList.UNKNOWN_ADJ) { 16640 switch (app.curProcState) { 16641 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 16642 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 16643 // This process is a cached process holding activities... 16644 // assign it the next cached value for that type, and then 16645 // step that cached level. 16646 app.curRawAdj = curCachedAdj; 16647 app.curAdj = app.modifyRawOomAdj(curCachedAdj); 16648 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning activity LRU #" + i 16649 + " adj: " + app.curAdj + " (curCachedAdj=" + curCachedAdj 16650 + ")"); 16651 if (curCachedAdj != nextCachedAdj) { 16652 stepCached++; 16653 if (stepCached >= cachedFactor) { 16654 stepCached = 0; 16655 curCachedAdj = nextCachedAdj; 16656 nextCachedAdj += 2; 16657 if (nextCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) { 16658 nextCachedAdj = ProcessList.CACHED_APP_MAX_ADJ; 16659 } 16660 } 16661 } 16662 break; 16663 default: 16664 // For everything else, assign next empty cached process 16665 // level and bump that up. Note that this means that 16666 // long-running services that have dropped down to the 16667 // cached level will be treated as empty (since their process 16668 // state is still as a service), which is what we want. 16669 app.curRawAdj = curEmptyAdj; 16670 app.curAdj = app.modifyRawOomAdj(curEmptyAdj); 16671 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning empty LRU #" + i 16672 + " adj: " + app.curAdj + " (curEmptyAdj=" + curEmptyAdj 16673 + ")"); 16674 if (curEmptyAdj != nextEmptyAdj) { 16675 stepEmpty++; 16676 if (stepEmpty >= emptyFactor) { 16677 stepEmpty = 0; 16678 curEmptyAdj = nextEmptyAdj; 16679 nextEmptyAdj += 2; 16680 if (nextEmptyAdj > ProcessList.CACHED_APP_MAX_ADJ) { 16681 nextEmptyAdj = ProcessList.CACHED_APP_MAX_ADJ; 16682 } 16683 } 16684 } 16685 break; 16686 } 16687 } 16688 16689 applyOomAdjLocked(app, TOP_APP, true, now); 16690 16691 // Count the number of process types. 16692 switch (app.curProcState) { 16693 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 16694 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 16695 mNumCachedHiddenProcs++; 16696 numCached++; 16697 if (numCached > cachedProcessLimit) { 16698 killUnneededProcessLocked(app, "cached #" + numCached); 16699 } 16700 break; 16701 case ActivityManager.PROCESS_STATE_CACHED_EMPTY: 16702 if (numEmpty > ProcessList.TRIM_EMPTY_APPS 16703 && app.lastActivityTime < oldTime) { 16704 killUnneededProcessLocked(app, "empty for " 16705 + ((oldTime + ProcessList.MAX_EMPTY_TIME - app.lastActivityTime) 16706 / 1000) + "s"); 16707 } else { 16708 numEmpty++; 16709 if (numEmpty > emptyProcessLimit) { 16710 killUnneededProcessLocked(app, "empty #" + numEmpty); 16711 } 16712 } 16713 break; 16714 default: 16715 mNumNonCachedProcs++; 16716 break; 16717 } 16718 16719 if (app.isolated && app.services.size() <= 0) { 16720 // If this is an isolated process, and there are no 16721 // services running in it, then the process is no longer 16722 // needed. We agressively kill these because we can by 16723 // definition not re-use the same process again, and it is 16724 // good to avoid having whatever code was running in them 16725 // left sitting around after no longer needed. 16726 killUnneededProcessLocked(app, "isolated not needed"); 16727 } 16728 16729 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 16730 && !app.killedByAm) { 16731 numTrimming++; 16732 } 16733 } 16734 } 16735 16736 mNumServiceProcs = mNewNumServiceProcs; 16737 16738 // Now determine the memory trimming level of background processes. 16739 // Unfortunately we need to start at the back of the list to do this 16740 // properly. We only do this if the number of background apps we 16741 // are managing to keep around is less than half the maximum we desire; 16742 // if we are keeping a good number around, we'll let them use whatever 16743 // memory they want. 16744 final int numCachedAndEmpty = numCached + numEmpty; 16745 int memFactor; 16746 if (numCached <= ProcessList.TRIM_CACHED_APPS 16747 && numEmpty <= ProcessList.TRIM_EMPTY_APPS) { 16748 if (numCachedAndEmpty <= ProcessList.TRIM_CRITICAL_THRESHOLD) { 16749 memFactor = ProcessStats.ADJ_MEM_FACTOR_CRITICAL; 16750 } else if (numCachedAndEmpty <= ProcessList.TRIM_LOW_THRESHOLD) { 16751 memFactor = ProcessStats.ADJ_MEM_FACTOR_LOW; 16752 } else { 16753 memFactor = ProcessStats.ADJ_MEM_FACTOR_MODERATE; 16754 } 16755 } else { 16756 memFactor = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 16757 } 16758 // We always allow the memory level to go up (better). We only allow it to go 16759 // down if we are in a state where that is allowed, *and* the total number of processes 16760 // has gone down since last time. 16761 if (DEBUG_OOM_ADJ) Slog.d(TAG, "oom: memFactor=" + memFactor + " last=" + mLastMemoryLevel 16762 + " allowLow=" + mAllowLowerMemLevel + " numProcs=" + mLruProcesses.size() 16763 + " last=" + mLastNumProcesses); 16764 if (memFactor > mLastMemoryLevel) { 16765 if (!mAllowLowerMemLevel || mLruProcesses.size() >= mLastNumProcesses) { 16766 memFactor = mLastMemoryLevel; 16767 if (DEBUG_OOM_ADJ) Slog.d(TAG, "Keeping last mem factor!"); 16768 } 16769 } 16770 mLastMemoryLevel = memFactor; 16771 mLastNumProcesses = mLruProcesses.size(); 16772 boolean allChanged = mProcessStats.setMemFactorLocked(memFactor, !isSleeping(), now); 16773 final int trackerMemFactor = mProcessStats.getMemFactorLocked(); 16774 if (memFactor != ProcessStats.ADJ_MEM_FACTOR_NORMAL) { 16775 if (mLowRamStartTime == 0) { 16776 mLowRamStartTime = now; 16777 } 16778 int step = 0; 16779 int fgTrimLevel; 16780 switch (memFactor) { 16781 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 16782 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_CRITICAL; 16783 break; 16784 case ProcessStats.ADJ_MEM_FACTOR_LOW: 16785 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_LOW; 16786 break; 16787 default: 16788 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_MODERATE; 16789 break; 16790 } 16791 int factor = numTrimming/3; 16792 int minFactor = 2; 16793 if (mHomeProcess != null) minFactor++; 16794 if (mPreviousProcess != null) minFactor++; 16795 if (factor < minFactor) factor = minFactor; 16796 int curLevel = ComponentCallbacks2.TRIM_MEMORY_COMPLETE; 16797 for (int i=N-1; i>=0; i--) { 16798 ProcessRecord app = mLruProcesses.get(i); 16799 if (allChanged || app.procStateChanged) { 16800 setProcessTrackerStateLocked(app, trackerMemFactor, now); 16801 app.procStateChanged = false; 16802 } 16803 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 16804 && !app.killedByAm) { 16805 if (app.trimMemoryLevel < curLevel && app.thread != null) { 16806 try { 16807 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16808 "Trimming memory of " + app.processName 16809 + " to " + curLevel); 16810 app.thread.scheduleTrimMemory(curLevel); 16811 } catch (RemoteException e) { 16812 } 16813 if (false) { 16814 // For now we won't do this; our memory trimming seems 16815 // to be good enough at this point that destroying 16816 // activities causes more harm than good. 16817 if (curLevel >= ComponentCallbacks2.TRIM_MEMORY_COMPLETE 16818 && app != mHomeProcess && app != mPreviousProcess) { 16819 // Need to do this on its own message because the stack may not 16820 // be in a consistent state at this point. 16821 // For these apps we will also finish their activities 16822 // to help them free memory. 16823 mStackSupervisor.scheduleDestroyAllActivities(app, "trim"); 16824 } 16825 } 16826 } 16827 app.trimMemoryLevel = curLevel; 16828 step++; 16829 if (step >= factor) { 16830 step = 0; 16831 switch (curLevel) { 16832 case ComponentCallbacks2.TRIM_MEMORY_COMPLETE: 16833 curLevel = ComponentCallbacks2.TRIM_MEMORY_MODERATE; 16834 break; 16835 case ComponentCallbacks2.TRIM_MEMORY_MODERATE: 16836 curLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 16837 break; 16838 } 16839 } 16840 } else if (app.curProcState == ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 16841 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_BACKGROUND 16842 && app.thread != null) { 16843 try { 16844 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16845 "Trimming memory of heavy-weight " + app.processName 16846 + " to " + ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 16847 app.thread.scheduleTrimMemory( 16848 ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 16849 } catch (RemoteException e) { 16850 } 16851 } 16852 app.trimMemoryLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 16853 } else { 16854 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 16855 || app.systemNoUi) && app.pendingUiClean) { 16856 // If this application is now in the background and it 16857 // had done UI, then give it the special trim level to 16858 // have it free UI resources. 16859 final int level = ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN; 16860 if (app.trimMemoryLevel < level && app.thread != null) { 16861 try { 16862 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16863 "Trimming memory of bg-ui " + app.processName 16864 + " to " + level); 16865 app.thread.scheduleTrimMemory(level); 16866 } catch (RemoteException e) { 16867 } 16868 } 16869 app.pendingUiClean = false; 16870 } 16871 if (app.trimMemoryLevel < fgTrimLevel && app.thread != null) { 16872 try { 16873 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16874 "Trimming memory of fg " + app.processName 16875 + " to " + fgTrimLevel); 16876 app.thread.scheduleTrimMemory(fgTrimLevel); 16877 } catch (RemoteException e) { 16878 } 16879 } 16880 app.trimMemoryLevel = fgTrimLevel; 16881 } 16882 } 16883 } else { 16884 if (mLowRamStartTime != 0) { 16885 mLowRamTimeSinceLastIdle += now - mLowRamStartTime; 16886 mLowRamStartTime = 0; 16887 } 16888 for (int i=N-1; i>=0; i--) { 16889 ProcessRecord app = mLruProcesses.get(i); 16890 if (allChanged || app.procStateChanged) { 16891 setProcessTrackerStateLocked(app, trackerMemFactor, now); 16892 app.procStateChanged = false; 16893 } 16894 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 16895 || app.systemNoUi) && app.pendingUiClean) { 16896 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN 16897 && app.thread != null) { 16898 try { 16899 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16900 "Trimming memory of ui hidden " + app.processName 16901 + " to " + ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 16902 app.thread.scheduleTrimMemory( 16903 ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 16904 } catch (RemoteException e) { 16905 } 16906 } 16907 app.pendingUiClean = false; 16908 } 16909 app.trimMemoryLevel = 0; 16910 } 16911 } 16912 16913 if (mAlwaysFinishActivities) { 16914 // Need to do this on its own message because the stack may not 16915 // be in a consistent state at this point. 16916 mStackSupervisor.scheduleDestroyAllActivities(null, "always-finish"); 16917 } 16918 16919 if (allChanged) { 16920 requestPssAllProcsLocked(now, false, mProcessStats.isMemFactorLowered()); 16921 } 16922 16923 if (mProcessStats.shouldWriteNowLocked(now)) { 16924 mHandler.post(new Runnable() { 16925 @Override public void run() { 16926 synchronized (ActivityManagerService.this) { 16927 mProcessStats.writeStateAsyncLocked(); 16928 } 16929 } 16930 }); 16931 } 16932 16933 if (DEBUG_OOM_ADJ) { 16934 Slog.d(TAG, "Did OOM ADJ in " + (SystemClock.uptimeMillis()-now) + "ms"); 16935 } 16936 } 16937 16938 final void trimApplications() { 16939 synchronized (this) { 16940 int i; 16941 16942 // First remove any unused application processes whose package 16943 // has been removed. 16944 for (i=mRemovedProcesses.size()-1; i>=0; i--) { 16945 final ProcessRecord app = mRemovedProcesses.get(i); 16946 if (app.activities.size() == 0 16947 && app.curReceiver == null && app.services.size() == 0) { 16948 Slog.i( 16949 TAG, "Exiting empty application process " 16950 + app.processName + " (" 16951 + (app.thread != null ? app.thread.asBinder() : null) 16952 + ")\n"); 16953 if (app.pid > 0 && app.pid != MY_PID) { 16954 EventLog.writeEvent(EventLogTags.AM_KILL, app.userId, app.pid, 16955 app.processName, app.setAdj, "empty"); 16956 app.killedByAm = true; 16957 Process.killProcessQuiet(app.pid); 16958 Process.killProcessGroup(app.info.uid, app.pid); 16959 } else { 16960 try { 16961 app.thread.scheduleExit(); 16962 } catch (Exception e) { 16963 // Ignore exceptions. 16964 } 16965 } 16966 cleanUpApplicationRecordLocked(app, false, true, -1); 16967 mRemovedProcesses.remove(i); 16968 16969 if (app.persistent) { 16970 addAppLocked(app.info, false, null /* ABI override */); 16971 } 16972 } 16973 } 16974 16975 // Now update the oom adj for all processes. 16976 updateOomAdjLocked(); 16977 } 16978 } 16979 16980 /** This method sends the specified signal to each of the persistent apps */ 16981 public void signalPersistentProcesses(int sig) throws RemoteException { 16982 if (sig != Process.SIGNAL_USR1) { 16983 throw new SecurityException("Only SIGNAL_USR1 is allowed"); 16984 } 16985 16986 synchronized (this) { 16987 if (checkCallingPermission(android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES) 16988 != PackageManager.PERMISSION_GRANTED) { 16989 throw new SecurityException("Requires permission " 16990 + android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES); 16991 } 16992 16993 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 16994 ProcessRecord r = mLruProcesses.get(i); 16995 if (r.thread != null && r.persistent) { 16996 Process.sendSignal(r.pid, sig); 16997 } 16998 } 16999 } 17000 } 17001 17002 private void stopProfilerLocked(ProcessRecord proc, String path, int profileType) { 17003 if (proc == null || proc == mProfileProc) { 17004 proc = mProfileProc; 17005 path = mProfileFile; 17006 profileType = mProfileType; 17007 clearProfilerLocked(); 17008 } 17009 if (proc == null) { 17010 return; 17011 } 17012 try { 17013 proc.thread.profilerControl(false, path, null, profileType); 17014 } catch (RemoteException e) { 17015 throw new IllegalStateException("Process disappeared"); 17016 } 17017 } 17018 17019 private void clearProfilerLocked() { 17020 if (mProfileFd != null) { 17021 try { 17022 mProfileFd.close(); 17023 } catch (IOException e) { 17024 } 17025 } 17026 mProfileApp = null; 17027 mProfileProc = null; 17028 mProfileFile = null; 17029 mProfileType = 0; 17030 mAutoStopProfiler = false; 17031 } 17032 17033 public boolean profileControl(String process, int userId, boolean start, 17034 String path, ParcelFileDescriptor fd, int profileType) throws RemoteException { 17035 17036 try { 17037 synchronized (this) { 17038 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 17039 // its own permission. 17040 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 17041 != PackageManager.PERMISSION_GRANTED) { 17042 throw new SecurityException("Requires permission " 17043 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 17044 } 17045 17046 if (start && fd == null) { 17047 throw new IllegalArgumentException("null fd"); 17048 } 17049 17050 ProcessRecord proc = null; 17051 if (process != null) { 17052 proc = findProcessLocked(process, userId, "profileControl"); 17053 } 17054 17055 if (start && (proc == null || proc.thread == null)) { 17056 throw new IllegalArgumentException("Unknown process: " + process); 17057 } 17058 17059 if (start) { 17060 stopProfilerLocked(null, null, 0); 17061 setProfileApp(proc.info, proc.processName, path, fd, false); 17062 mProfileProc = proc; 17063 mProfileType = profileType; 17064 try { 17065 fd = fd.dup(); 17066 } catch (IOException e) { 17067 fd = null; 17068 } 17069 proc.thread.profilerControl(start, path, fd, profileType); 17070 fd = null; 17071 mProfileFd = null; 17072 } else { 17073 stopProfilerLocked(proc, path, profileType); 17074 if (fd != null) { 17075 try { 17076 fd.close(); 17077 } catch (IOException e) { 17078 } 17079 } 17080 } 17081 17082 return true; 17083 } 17084 } catch (RemoteException e) { 17085 throw new IllegalStateException("Process disappeared"); 17086 } finally { 17087 if (fd != null) { 17088 try { 17089 fd.close(); 17090 } catch (IOException e) { 17091 } 17092 } 17093 } 17094 } 17095 17096 private ProcessRecord findProcessLocked(String process, int userId, String callName) { 17097 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 17098 userId, true, ALLOW_FULL_ONLY, callName, null); 17099 ProcessRecord proc = null; 17100 try { 17101 int pid = Integer.parseInt(process); 17102 synchronized (mPidsSelfLocked) { 17103 proc = mPidsSelfLocked.get(pid); 17104 } 17105 } catch (NumberFormatException e) { 17106 } 17107 17108 if (proc == null) { 17109 ArrayMap<String, SparseArray<ProcessRecord>> all 17110 = mProcessNames.getMap(); 17111 SparseArray<ProcessRecord> procs = all.get(process); 17112 if (procs != null && procs.size() > 0) { 17113 proc = procs.valueAt(0); 17114 if (userId != UserHandle.USER_ALL && proc.userId != userId) { 17115 for (int i=1; i<procs.size(); i++) { 17116 ProcessRecord thisProc = procs.valueAt(i); 17117 if (thisProc.userId == userId) { 17118 proc = thisProc; 17119 break; 17120 } 17121 } 17122 } 17123 } 17124 } 17125 17126 return proc; 17127 } 17128 17129 public boolean dumpHeap(String process, int userId, boolean managed, 17130 String path, ParcelFileDescriptor fd) throws RemoteException { 17131 17132 try { 17133 synchronized (this) { 17134 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 17135 // its own permission (same as profileControl). 17136 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 17137 != PackageManager.PERMISSION_GRANTED) { 17138 throw new SecurityException("Requires permission " 17139 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 17140 } 17141 17142 if (fd == null) { 17143 throw new IllegalArgumentException("null fd"); 17144 } 17145 17146 ProcessRecord proc = findProcessLocked(process, userId, "dumpHeap"); 17147 if (proc == null || proc.thread == null) { 17148 throw new IllegalArgumentException("Unknown process: " + process); 17149 } 17150 17151 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 17152 if (!isDebuggable) { 17153 if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 17154 throw new SecurityException("Process not debuggable: " + proc); 17155 } 17156 } 17157 17158 proc.thread.dumpHeap(managed, path, fd); 17159 fd = null; 17160 return true; 17161 } 17162 } catch (RemoteException e) { 17163 throw new IllegalStateException("Process disappeared"); 17164 } finally { 17165 if (fd != null) { 17166 try { 17167 fd.close(); 17168 } catch (IOException e) { 17169 } 17170 } 17171 } 17172 } 17173 17174 /** In this method we try to acquire our lock to make sure that we have not deadlocked */ 17175 public void monitor() { 17176 synchronized (this) { } 17177 } 17178 17179 void onCoreSettingsChange(Bundle settings) { 17180 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 17181 ProcessRecord processRecord = mLruProcesses.get(i); 17182 try { 17183 if (processRecord.thread != null) { 17184 processRecord.thread.setCoreSettings(settings); 17185 } 17186 } catch (RemoteException re) { 17187 /* ignore */ 17188 } 17189 } 17190 } 17191 17192 // Multi-user methods 17193 17194 /** 17195 * Start user, if its not already running, but don't bring it to foreground. 17196 */ 17197 @Override 17198 public boolean startUserInBackground(final int userId) { 17199 return startUser(userId, /* foreground */ false); 17200 } 17201 17202 /** 17203 * Refreshes the list of users related to the current user when either a 17204 * user switch happens or when a new related user is started in the 17205 * background. 17206 */ 17207 private void updateCurrentProfileIdsLocked() { 17208 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17209 mCurrentUserId, false /* enabledOnly */); 17210 int[] currentProfileIds = new int[profiles.size()]; // profiles will not be null 17211 for (int i = 0; i < currentProfileIds.length; i++) { 17212 currentProfileIds[i] = profiles.get(i).id; 17213 } 17214 mCurrentProfileIds = currentProfileIds; 17215 17216 synchronized (mUserProfileGroupIdsSelfLocked) { 17217 mUserProfileGroupIdsSelfLocked.clear(); 17218 final List<UserInfo> users = getUserManagerLocked().getUsers(false); 17219 for (int i = 0; i < users.size(); i++) { 17220 UserInfo user = users.get(i); 17221 if (user.profileGroupId != UserInfo.NO_PROFILE_GROUP_ID) { 17222 mUserProfileGroupIdsSelfLocked.put(user.id, user.profileGroupId); 17223 } 17224 } 17225 } 17226 } 17227 17228 private Set getProfileIdsLocked(int userId) { 17229 Set userIds = new HashSet<Integer>(); 17230 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17231 userId, false /* enabledOnly */); 17232 for (UserInfo user : profiles) { 17233 userIds.add(Integer.valueOf(user.id)); 17234 } 17235 return userIds; 17236 } 17237 17238 @Override 17239 public boolean switchUser(final int userId) { 17240 return startUser(userId, /* foregound */ true); 17241 } 17242 17243 private boolean startUser(final int userId, boolean foreground) { 17244 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17245 != PackageManager.PERMISSION_GRANTED) { 17246 String msg = "Permission Denial: switchUser() from pid=" 17247 + Binder.getCallingPid() 17248 + ", uid=" + Binder.getCallingUid() 17249 + " requires " + INTERACT_ACROSS_USERS_FULL; 17250 Slog.w(TAG, msg); 17251 throw new SecurityException(msg); 17252 } 17253 17254 if (DEBUG_MU) Slog.i(TAG_MU, "starting userid:" + userId + " fore:" + foreground); 17255 17256 final long ident = Binder.clearCallingIdentity(); 17257 try { 17258 synchronized (this) { 17259 final int oldUserId = mCurrentUserId; 17260 if (oldUserId == userId) { 17261 return true; 17262 } 17263 17264 mStackSupervisor.setLockTaskModeLocked(null, false); 17265 17266 final UserInfo userInfo = getUserManagerLocked().getUserInfo(userId); 17267 if (userInfo == null) { 17268 Slog.w(TAG, "No user info for user #" + userId); 17269 return false; 17270 } 17271 if (foreground && userInfo.isManagedProfile()) { 17272 Slog.w(TAG, "Cannot switch to User #" + userId + ": not a full user"); 17273 return false; 17274 } 17275 17276 if (foreground) { 17277 mWindowManager.startFreezingScreen(R.anim.screen_user_exit, 17278 R.anim.screen_user_enter); 17279 } 17280 17281 boolean needStart = false; 17282 17283 // If the user we are switching to is not currently started, then 17284 // we need to start it now. 17285 if (mStartedUsers.get(userId) == null) { 17286 mStartedUsers.put(userId, new UserStartedState(new UserHandle(userId), false)); 17287 updateStartedUserArrayLocked(); 17288 needStart = true; 17289 } 17290 17291 final Integer userIdInt = Integer.valueOf(userId); 17292 mUserLru.remove(userIdInt); 17293 mUserLru.add(userIdInt); 17294 17295 if (foreground) { 17296 mCurrentUserId = userId; 17297 updateCurrentProfileIdsLocked(); 17298 mWindowManager.setCurrentUser(userId, mCurrentProfileIds); 17299 // Once the internal notion of the active user has switched, we lock the device 17300 // with the option to show the user switcher on the keyguard. 17301 mWindowManager.lockNow(null); 17302 } else { 17303 final Integer currentUserIdInt = Integer.valueOf(mCurrentUserId); 17304 updateCurrentProfileIdsLocked(); 17305 mWindowManager.setCurrentProfileIds(mCurrentProfileIds); 17306 mUserLru.remove(currentUserIdInt); 17307 mUserLru.add(currentUserIdInt); 17308 } 17309 17310 final UserStartedState uss = mStartedUsers.get(userId); 17311 17312 // Make sure user is in the started state. If it is currently 17313 // stopping, we need to knock that off. 17314 if (uss.mState == UserStartedState.STATE_STOPPING) { 17315 // If we are stopping, we haven't sent ACTION_SHUTDOWN, 17316 // so we can just fairly silently bring the user back from 17317 // the almost-dead. 17318 uss.mState = UserStartedState.STATE_RUNNING; 17319 updateStartedUserArrayLocked(); 17320 needStart = true; 17321 } else if (uss.mState == UserStartedState.STATE_SHUTDOWN) { 17322 // This means ACTION_SHUTDOWN has been sent, so we will 17323 // need to treat this as a new boot of the user. 17324 uss.mState = UserStartedState.STATE_BOOTING; 17325 updateStartedUserArrayLocked(); 17326 needStart = true; 17327 } 17328 17329 if (uss.mState == UserStartedState.STATE_BOOTING) { 17330 // Booting up a new user, need to tell system services about it. 17331 // Note that this is on the same handler as scheduling of broadcasts, 17332 // which is important because it needs to go first. 17333 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_START_MSG, userId, 0)); 17334 } 17335 17336 if (foreground) { 17337 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_CURRENT_MSG, userId, 17338 oldUserId)); 17339 mHandler.removeMessages(REPORT_USER_SWITCH_MSG); 17340 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 17341 mHandler.sendMessage(mHandler.obtainMessage(REPORT_USER_SWITCH_MSG, 17342 oldUserId, userId, uss)); 17343 mHandler.sendMessageDelayed(mHandler.obtainMessage(USER_SWITCH_TIMEOUT_MSG, 17344 oldUserId, userId, uss), USER_SWITCH_TIMEOUT); 17345 } 17346 17347 if (needStart) { 17348 // Send USER_STARTED broadcast 17349 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 17350 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 17351 | Intent.FLAG_RECEIVER_FOREGROUND); 17352 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17353 broadcastIntentLocked(null, null, intent, 17354 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 17355 false, false, MY_PID, Process.SYSTEM_UID, userId); 17356 } 17357 17358 if ((userInfo.flags&UserInfo.FLAG_INITIALIZED) == 0) { 17359 if (userId != UserHandle.USER_OWNER) { 17360 Intent intent = new Intent(Intent.ACTION_USER_INITIALIZE); 17361 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 17362 broadcastIntentLocked(null, null, intent, null, 17363 new IIntentReceiver.Stub() { 17364 public void performReceive(Intent intent, int resultCode, 17365 String data, Bundle extras, boolean ordered, 17366 boolean sticky, int sendingUser) { 17367 userInitialized(uss, userId); 17368 } 17369 }, 0, null, null, null, AppOpsManager.OP_NONE, 17370 true, false, MY_PID, Process.SYSTEM_UID, 17371 userId); 17372 uss.initializing = true; 17373 } else { 17374 getUserManagerLocked().makeInitialized(userInfo.id); 17375 } 17376 } 17377 17378 if (foreground) { 17379 boolean homeInFront = mStackSupervisor.switchUserLocked(userId, uss); 17380 if (homeInFront) { 17381 startHomeActivityLocked(userId); 17382 } else { 17383 mStackSupervisor.resumeTopActivitiesLocked(); 17384 } 17385 EventLogTags.writeAmSwitchUser(userId); 17386 getUserManagerLocked().userForeground(userId); 17387 sendUserSwitchBroadcastsLocked(oldUserId, userId); 17388 } else { 17389 mStackSupervisor.startBackgroundUserLocked(userId, uss); 17390 } 17391 17392 if (needStart) { 17393 Intent intent = new Intent(Intent.ACTION_USER_STARTING); 17394 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 17395 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17396 broadcastIntentLocked(null, null, intent, 17397 null, new IIntentReceiver.Stub() { 17398 @Override 17399 public void performReceive(Intent intent, int resultCode, String data, 17400 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 17401 throws RemoteException { 17402 } 17403 }, 0, null, null, 17404 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 17405 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 17406 } 17407 } 17408 } finally { 17409 Binder.restoreCallingIdentity(ident); 17410 } 17411 17412 return true; 17413 } 17414 17415 void sendUserSwitchBroadcastsLocked(int oldUserId, int newUserId) { 17416 long ident = Binder.clearCallingIdentity(); 17417 try { 17418 Intent intent; 17419 if (oldUserId >= 0) { 17420 // Send USER_BACKGROUND broadcast to all profiles of the outgoing user 17421 List<UserInfo> profiles = mUserManager.getProfiles(oldUserId, false); 17422 int count = profiles.size(); 17423 for (int i = 0; i < count; i++) { 17424 int profileUserId = profiles.get(i).id; 17425 intent = new Intent(Intent.ACTION_USER_BACKGROUND); 17426 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 17427 | Intent.FLAG_RECEIVER_FOREGROUND); 17428 intent.putExtra(Intent.EXTRA_USER_HANDLE, profileUserId); 17429 broadcastIntentLocked(null, null, intent, 17430 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 17431 false, false, MY_PID, Process.SYSTEM_UID, profileUserId); 17432 } 17433 } 17434 if (newUserId >= 0) { 17435 // Send USER_FOREGROUND broadcast to all profiles of the incoming user 17436 List<UserInfo> profiles = mUserManager.getProfiles(newUserId, false); 17437 int count = profiles.size(); 17438 for (int i = 0; i < count; i++) { 17439 int profileUserId = profiles.get(i).id; 17440 intent = new Intent(Intent.ACTION_USER_FOREGROUND); 17441 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 17442 | Intent.FLAG_RECEIVER_FOREGROUND); 17443 intent.putExtra(Intent.EXTRA_USER_HANDLE, profileUserId); 17444 broadcastIntentLocked(null, null, intent, 17445 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 17446 false, false, MY_PID, Process.SYSTEM_UID, profileUserId); 17447 } 17448 intent = new Intent(Intent.ACTION_USER_SWITCHED); 17449 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 17450 | Intent.FLAG_RECEIVER_FOREGROUND); 17451 intent.putExtra(Intent.EXTRA_USER_HANDLE, newUserId); 17452 broadcastIntentLocked(null, null, intent, 17453 null, null, 0, null, null, 17454 android.Manifest.permission.MANAGE_USERS, AppOpsManager.OP_NONE, 17455 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 17456 } 17457 } finally { 17458 Binder.restoreCallingIdentity(ident); 17459 } 17460 } 17461 17462 void dispatchUserSwitch(final UserStartedState uss, final int oldUserId, 17463 final int newUserId) { 17464 final int N = mUserSwitchObservers.beginBroadcast(); 17465 if (N > 0) { 17466 final IRemoteCallback callback = new IRemoteCallback.Stub() { 17467 int mCount = 0; 17468 @Override 17469 public void sendResult(Bundle data) throws RemoteException { 17470 synchronized (ActivityManagerService.this) { 17471 if (mCurUserSwitchCallback == this) { 17472 mCount++; 17473 if (mCount == N) { 17474 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 17475 } 17476 } 17477 } 17478 } 17479 }; 17480 synchronized (this) { 17481 uss.switching = true; 17482 mCurUserSwitchCallback = callback; 17483 } 17484 for (int i=0; i<N; i++) { 17485 try { 17486 mUserSwitchObservers.getBroadcastItem(i).onUserSwitching( 17487 newUserId, callback); 17488 } catch (RemoteException e) { 17489 } 17490 } 17491 } else { 17492 synchronized (this) { 17493 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 17494 } 17495 } 17496 mUserSwitchObservers.finishBroadcast(); 17497 } 17498 17499 void timeoutUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 17500 synchronized (this) { 17501 Slog.w(TAG, "User switch timeout: from " + oldUserId + " to " + newUserId); 17502 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 17503 } 17504 } 17505 17506 void sendContinueUserSwitchLocked(UserStartedState uss, int oldUserId, int newUserId) { 17507 mCurUserSwitchCallback = null; 17508 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 17509 mHandler.sendMessage(mHandler.obtainMessage(CONTINUE_USER_SWITCH_MSG, 17510 oldUserId, newUserId, uss)); 17511 } 17512 17513 void userInitialized(UserStartedState uss, int newUserId) { 17514 completeSwitchAndInitalize(uss, newUserId, true, false); 17515 } 17516 17517 void continueUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 17518 completeSwitchAndInitalize(uss, newUserId, false, true); 17519 } 17520 17521 void completeSwitchAndInitalize(UserStartedState uss, int newUserId, 17522 boolean clearInitializing, boolean clearSwitching) { 17523 boolean unfrozen = false; 17524 synchronized (this) { 17525 if (clearInitializing) { 17526 uss.initializing = false; 17527 getUserManagerLocked().makeInitialized(uss.mHandle.getIdentifier()); 17528 } 17529 if (clearSwitching) { 17530 uss.switching = false; 17531 } 17532 if (!uss.switching && !uss.initializing) { 17533 mWindowManager.stopFreezingScreen(); 17534 unfrozen = true; 17535 } 17536 } 17537 if (unfrozen) { 17538 final int N = mUserSwitchObservers.beginBroadcast(); 17539 for (int i=0; i<N; i++) { 17540 try { 17541 mUserSwitchObservers.getBroadcastItem(i).onUserSwitchComplete(newUserId); 17542 } catch (RemoteException e) { 17543 } 17544 } 17545 mUserSwitchObservers.finishBroadcast(); 17546 } 17547 } 17548 17549 void scheduleStartProfilesLocked() { 17550 if (!mHandler.hasMessages(START_PROFILES_MSG)) { 17551 mHandler.sendMessageDelayed(mHandler.obtainMessage(START_PROFILES_MSG), 17552 DateUtils.SECOND_IN_MILLIS); 17553 } 17554 } 17555 17556 void startProfilesLocked() { 17557 if (DEBUG_MU) Slog.i(TAG_MU, "startProfilesLocked"); 17558 List<UserInfo> profiles = getUserManagerLocked().getProfiles( 17559 mCurrentUserId, false /* enabledOnly */); 17560 List<UserInfo> toStart = new ArrayList<UserInfo>(profiles.size()); 17561 for (UserInfo user : profiles) { 17562 if ((user.flags & UserInfo.FLAG_INITIALIZED) == UserInfo.FLAG_INITIALIZED 17563 && user.id != mCurrentUserId) { 17564 toStart.add(user); 17565 } 17566 } 17567 final int n = toStart.size(); 17568 int i = 0; 17569 for (; i < n && i < (MAX_RUNNING_USERS - 1); ++i) { 17570 startUserInBackground(toStart.get(i).id); 17571 } 17572 if (i < n) { 17573 Slog.w(TAG_MU, "More profiles than MAX_RUNNING_USERS"); 17574 } 17575 } 17576 17577 void finishUserBoot(UserStartedState uss) { 17578 synchronized (this) { 17579 if (uss.mState == UserStartedState.STATE_BOOTING 17580 && mStartedUsers.get(uss.mHandle.getIdentifier()) == uss) { 17581 uss.mState = UserStartedState.STATE_RUNNING; 17582 final int userId = uss.mHandle.getIdentifier(); 17583 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 17584 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17585 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 17586 broadcastIntentLocked(null, null, intent, 17587 null, null, 0, null, null, 17588 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, AppOpsManager.OP_NONE, 17589 true, false, MY_PID, Process.SYSTEM_UID, userId); 17590 } 17591 } 17592 } 17593 17594 void finishUserSwitch(UserStartedState uss) { 17595 synchronized (this) { 17596 finishUserBoot(uss); 17597 17598 startProfilesLocked(); 17599 17600 int num = mUserLru.size(); 17601 int i = 0; 17602 while (num > MAX_RUNNING_USERS && i < mUserLru.size()) { 17603 Integer oldUserId = mUserLru.get(i); 17604 UserStartedState oldUss = mStartedUsers.get(oldUserId); 17605 if (oldUss == null) { 17606 // Shouldn't happen, but be sane if it does. 17607 mUserLru.remove(i); 17608 num--; 17609 continue; 17610 } 17611 if (oldUss.mState == UserStartedState.STATE_STOPPING 17612 || oldUss.mState == UserStartedState.STATE_SHUTDOWN) { 17613 // This user is already stopping, doesn't count. 17614 num--; 17615 i++; 17616 continue; 17617 } 17618 if (oldUserId == UserHandle.USER_OWNER || oldUserId == mCurrentUserId) { 17619 // Owner and current can't be stopped, but count as running. 17620 i++; 17621 continue; 17622 } 17623 // This is a user to be stopped. 17624 stopUserLocked(oldUserId, null); 17625 num--; 17626 i++; 17627 } 17628 } 17629 } 17630 17631 @Override 17632 public int stopUser(final int userId, final IStopUserCallback callback) { 17633 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17634 != PackageManager.PERMISSION_GRANTED) { 17635 String msg = "Permission Denial: switchUser() from pid=" 17636 + Binder.getCallingPid() 17637 + ", uid=" + Binder.getCallingUid() 17638 + " requires " + INTERACT_ACROSS_USERS_FULL; 17639 Slog.w(TAG, msg); 17640 throw new SecurityException(msg); 17641 } 17642 if (userId <= 0) { 17643 throw new IllegalArgumentException("Can't stop primary user " + userId); 17644 } 17645 synchronized (this) { 17646 return stopUserLocked(userId, callback); 17647 } 17648 } 17649 17650 private int stopUserLocked(final int userId, final IStopUserCallback callback) { 17651 if (DEBUG_MU) Slog.i(TAG_MU, "stopUserLocked userId=" + userId); 17652 if (mCurrentUserId == userId) { 17653 return ActivityManager.USER_OP_IS_CURRENT; 17654 } 17655 17656 final UserStartedState uss = mStartedUsers.get(userId); 17657 if (uss == null) { 17658 // User is not started, nothing to do... but we do need to 17659 // callback if requested. 17660 if (callback != null) { 17661 mHandler.post(new Runnable() { 17662 @Override 17663 public void run() { 17664 try { 17665 callback.userStopped(userId); 17666 } catch (RemoteException e) { 17667 } 17668 } 17669 }); 17670 } 17671 return ActivityManager.USER_OP_SUCCESS; 17672 } 17673 17674 if (callback != null) { 17675 uss.mStopCallbacks.add(callback); 17676 } 17677 17678 if (uss.mState != UserStartedState.STATE_STOPPING 17679 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17680 uss.mState = UserStartedState.STATE_STOPPING; 17681 updateStartedUserArrayLocked(); 17682 17683 long ident = Binder.clearCallingIdentity(); 17684 try { 17685 // We are going to broadcast ACTION_USER_STOPPING and then 17686 // once that is done send a final ACTION_SHUTDOWN and then 17687 // stop the user. 17688 final Intent stoppingIntent = new Intent(Intent.ACTION_USER_STOPPING); 17689 stoppingIntent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 17690 stoppingIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 17691 stoppingIntent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 17692 final Intent shutdownIntent = new Intent(Intent.ACTION_SHUTDOWN); 17693 // This is the result receiver for the final shutdown broadcast. 17694 final IIntentReceiver shutdownReceiver = new IIntentReceiver.Stub() { 17695 @Override 17696 public void performReceive(Intent intent, int resultCode, String data, 17697 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 17698 finishUserStop(uss); 17699 } 17700 }; 17701 // This is the result receiver for the initial stopping broadcast. 17702 final IIntentReceiver stoppingReceiver = new IIntentReceiver.Stub() { 17703 @Override 17704 public void performReceive(Intent intent, int resultCode, String data, 17705 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 17706 // On to the next. 17707 synchronized (ActivityManagerService.this) { 17708 if (uss.mState != UserStartedState.STATE_STOPPING) { 17709 // Whoops, we are being started back up. Abort, abort! 17710 return; 17711 } 17712 uss.mState = UserStartedState.STATE_SHUTDOWN; 17713 } 17714 mBatteryStatsService.noteEvent( 17715 BatteryStats.HistoryItem.EVENT_USER_RUNNING_FINISH, 17716 Integer.toString(userId), userId); 17717 mSystemServiceManager.stopUser(userId); 17718 broadcastIntentLocked(null, null, shutdownIntent, 17719 null, shutdownReceiver, 0, null, null, null, AppOpsManager.OP_NONE, 17720 true, false, MY_PID, Process.SYSTEM_UID, userId); 17721 } 17722 }; 17723 // Kick things off. 17724 broadcastIntentLocked(null, null, stoppingIntent, 17725 null, stoppingReceiver, 0, null, null, 17726 INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 17727 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 17728 } finally { 17729 Binder.restoreCallingIdentity(ident); 17730 } 17731 } 17732 17733 return ActivityManager.USER_OP_SUCCESS; 17734 } 17735 17736 void finishUserStop(UserStartedState uss) { 17737 final int userId = uss.mHandle.getIdentifier(); 17738 boolean stopped; 17739 ArrayList<IStopUserCallback> callbacks; 17740 synchronized (this) { 17741 callbacks = new ArrayList<IStopUserCallback>(uss.mStopCallbacks); 17742 if (mStartedUsers.get(userId) != uss) { 17743 stopped = false; 17744 } else if (uss.mState != UserStartedState.STATE_SHUTDOWN) { 17745 stopped = false; 17746 } else { 17747 stopped = true; 17748 // User can no longer run. 17749 mStartedUsers.remove(userId); 17750 mUserLru.remove(Integer.valueOf(userId)); 17751 updateStartedUserArrayLocked(); 17752 17753 // Clean up all state and processes associated with the user. 17754 // Kill all the processes for the user. 17755 forceStopUserLocked(userId, "finish user"); 17756 } 17757 17758 // Explicitly remove the old information in mRecentTasks. 17759 removeRecentTasksForUserLocked(userId); 17760 } 17761 17762 for (int i=0; i<callbacks.size(); i++) { 17763 try { 17764 if (stopped) callbacks.get(i).userStopped(userId); 17765 else callbacks.get(i).userStopAborted(userId); 17766 } catch (RemoteException e) { 17767 } 17768 } 17769 17770 if (stopped) { 17771 mSystemServiceManager.cleanupUser(userId); 17772 synchronized (this) { 17773 mStackSupervisor.removeUserLocked(userId); 17774 } 17775 } 17776 } 17777 17778 @Override 17779 public UserInfo getCurrentUser() { 17780 if ((checkCallingPermission(INTERACT_ACROSS_USERS) 17781 != PackageManager.PERMISSION_GRANTED) && ( 17782 checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17783 != PackageManager.PERMISSION_GRANTED)) { 17784 String msg = "Permission Denial: getCurrentUser() from pid=" 17785 + Binder.getCallingPid() 17786 + ", uid=" + Binder.getCallingUid() 17787 + " requires " + INTERACT_ACROSS_USERS; 17788 Slog.w(TAG, msg); 17789 throw new SecurityException(msg); 17790 } 17791 synchronized (this) { 17792 return getUserManagerLocked().getUserInfo(mCurrentUserId); 17793 } 17794 } 17795 17796 int getCurrentUserIdLocked() { 17797 return mCurrentUserId; 17798 } 17799 17800 @Override 17801 public boolean isUserRunning(int userId, boolean orStopped) { 17802 if (checkCallingPermission(INTERACT_ACROSS_USERS) 17803 != PackageManager.PERMISSION_GRANTED) { 17804 String msg = "Permission Denial: isUserRunning() from pid=" 17805 + Binder.getCallingPid() 17806 + ", uid=" + Binder.getCallingUid() 17807 + " requires " + INTERACT_ACROSS_USERS; 17808 Slog.w(TAG, msg); 17809 throw new SecurityException(msg); 17810 } 17811 synchronized (this) { 17812 return isUserRunningLocked(userId, orStopped); 17813 } 17814 } 17815 17816 boolean isUserRunningLocked(int userId, boolean orStopped) { 17817 UserStartedState state = mStartedUsers.get(userId); 17818 if (state == null) { 17819 return false; 17820 } 17821 if (orStopped) { 17822 return true; 17823 } 17824 return state.mState != UserStartedState.STATE_STOPPING 17825 && state.mState != UserStartedState.STATE_SHUTDOWN; 17826 } 17827 17828 @Override 17829 public int[] getRunningUserIds() { 17830 if (checkCallingPermission(INTERACT_ACROSS_USERS) 17831 != PackageManager.PERMISSION_GRANTED) { 17832 String msg = "Permission Denial: isUserRunning() from pid=" 17833 + Binder.getCallingPid() 17834 + ", uid=" + Binder.getCallingUid() 17835 + " requires " + INTERACT_ACROSS_USERS; 17836 Slog.w(TAG, msg); 17837 throw new SecurityException(msg); 17838 } 17839 synchronized (this) { 17840 return mStartedUserArray; 17841 } 17842 } 17843 17844 private void updateStartedUserArrayLocked() { 17845 int num = 0; 17846 for (int i=0; i<mStartedUsers.size(); i++) { 17847 UserStartedState uss = mStartedUsers.valueAt(i); 17848 // This list does not include stopping users. 17849 if (uss.mState != UserStartedState.STATE_STOPPING 17850 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17851 num++; 17852 } 17853 } 17854 mStartedUserArray = new int[num]; 17855 num = 0; 17856 for (int i=0; i<mStartedUsers.size(); i++) { 17857 UserStartedState uss = mStartedUsers.valueAt(i); 17858 if (uss.mState != UserStartedState.STATE_STOPPING 17859 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 17860 mStartedUserArray[num] = mStartedUsers.keyAt(i); 17861 num++; 17862 } 17863 } 17864 } 17865 17866 @Override 17867 public void registerUserSwitchObserver(IUserSwitchObserver observer) { 17868 if (checkCallingPermission(INTERACT_ACROSS_USERS_FULL) 17869 != PackageManager.PERMISSION_GRANTED) { 17870 String msg = "Permission Denial: registerUserSwitchObserver() from pid=" 17871 + Binder.getCallingPid() 17872 + ", uid=" + Binder.getCallingUid() 17873 + " requires " + INTERACT_ACROSS_USERS_FULL; 17874 Slog.w(TAG, msg); 17875 throw new SecurityException(msg); 17876 } 17877 17878 mUserSwitchObservers.register(observer); 17879 } 17880 17881 @Override 17882 public void unregisterUserSwitchObserver(IUserSwitchObserver observer) { 17883 mUserSwitchObservers.unregister(observer); 17884 } 17885 17886 private boolean userExists(int userId) { 17887 if (userId == 0) { 17888 return true; 17889 } 17890 UserManagerService ums = getUserManagerLocked(); 17891 return ums != null ? (ums.getUserInfo(userId) != null) : false; 17892 } 17893 17894 int[] getUsersLocked() { 17895 UserManagerService ums = getUserManagerLocked(); 17896 return ums != null ? ums.getUserIds() : new int[] { 0 }; 17897 } 17898 17899 UserManagerService getUserManagerLocked() { 17900 if (mUserManager == null) { 17901 IBinder b = ServiceManager.getService(Context.USER_SERVICE); 17902 mUserManager = (UserManagerService)IUserManager.Stub.asInterface(b); 17903 } 17904 return mUserManager; 17905 } 17906 17907 private int applyUserId(int uid, int userId) { 17908 return UserHandle.getUid(userId, uid); 17909 } 17910 17911 ApplicationInfo getAppInfoForUser(ApplicationInfo info, int userId) { 17912 if (info == null) return null; 17913 ApplicationInfo newInfo = new ApplicationInfo(info); 17914 newInfo.uid = applyUserId(info.uid, userId); 17915 newInfo.dataDir = USER_DATA_DIR + userId + "/" 17916 + info.packageName; 17917 return newInfo; 17918 } 17919 17920 ActivityInfo getActivityInfoForUser(ActivityInfo aInfo, int userId) { 17921 if (aInfo == null 17922 || (userId < 1 && aInfo.applicationInfo.uid < UserHandle.PER_USER_RANGE)) { 17923 return aInfo; 17924 } 17925 17926 ActivityInfo info = new ActivityInfo(aInfo); 17927 info.applicationInfo = getAppInfoForUser(info.applicationInfo, userId); 17928 return info; 17929 } 17930 17931 private final class LocalService extends ActivityManagerInternal { 17932 @Override 17933 public void goingToSleep() { 17934 ActivityManagerService.this.goingToSleep(); 17935 } 17936 17937 @Override 17938 public void wakingUp() { 17939 ActivityManagerService.this.wakingUp(); 17940 } 17941 17942 @Override 17943 public int startIsolatedProcess(String entryPoint, String[] entryPointArgs, 17944 String processName, String abiOverride, int uid, Runnable crashHandler) { 17945 return ActivityManagerService.this.startIsolatedProcess(entryPoint, entryPointArgs, 17946 processName, abiOverride, uid, crashHandler); 17947 } 17948 } 17949 17950 /** 17951 * An implementation of IAppTask, that allows an app to manage its own tasks via 17952 * {@link android.app.ActivityManager.AppTask}. We keep track of the callingUid to ensure that 17953 * only the process that calls getAppTasks() can call the AppTask methods. 17954 */ 17955 class AppTaskImpl extends IAppTask.Stub { 17956 private int mTaskId; 17957 private int mCallingUid; 17958 17959 public AppTaskImpl(int taskId, int callingUid) { 17960 mTaskId = taskId; 17961 mCallingUid = callingUid; 17962 } 17963 17964 @Override 17965 public void finishAndRemoveTask() { 17966 // Ensure that we are called from the same process that created this AppTask 17967 if (mCallingUid != Binder.getCallingUid()) { 17968 Slog.w(TAG, "finishAndRemoveTask: caller " + mCallingUid 17969 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 17970 return; 17971 } 17972 17973 synchronized (ActivityManagerService.this) { 17974 long origId = Binder.clearCallingIdentity(); 17975 try { 17976 TaskRecord tr = recentTaskForIdLocked(mTaskId); 17977 if (tr != null) { 17978 // Only kill the process if we are not a new document 17979 int flags = tr.getBaseIntent().getFlags(); 17980 boolean isDocument = (flags & Intent.FLAG_ACTIVITY_NEW_DOCUMENT) == 17981 Intent.FLAG_ACTIVITY_NEW_DOCUMENT; 17982 removeTaskByIdLocked(mTaskId, 17983 !isDocument ? ActivityManager.REMOVE_TASK_KILL_PROCESS : 0); 17984 } 17985 } finally { 17986 Binder.restoreCallingIdentity(origId); 17987 } 17988 } 17989 } 17990 17991 @Override 17992 public ActivityManager.RecentTaskInfo getTaskInfo() { 17993 // Ensure that we are called from the same process that created this AppTask 17994 if (mCallingUid != Binder.getCallingUid()) { 17995 Slog.w(TAG, "finishAndRemoveTask: caller " + mCallingUid 17996 + " does not match caller of getAppTasks(): " + Binder.getCallingUid()); 17997 return null; 17998 } 17999 18000 synchronized (ActivityManagerService.this) { 18001 long origId = Binder.clearCallingIdentity(); 18002 try { 18003 TaskRecord tr = recentTaskForIdLocked(mTaskId); 18004 if (tr != null) { 18005 return createRecentTaskInfoFromTaskRecord(tr); 18006 } 18007 } finally { 18008 Binder.restoreCallingIdentity(origId); 18009 } 18010 return null; 18011 } 18012 } 18013 } 18014} 18015