ActivityManagerService.java revision 5d84bce12204072bc7ab296ce0cdea7efb5cf17c
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.content.pm.PackageManager.PERMISSION_GRANTED; 20import static com.android.internal.util.XmlUtils.readBooleanAttribute; 21import static com.android.internal.util.XmlUtils.readIntAttribute; 22import static com.android.internal.util.XmlUtils.readLongAttribute; 23import static com.android.internal.util.XmlUtils.writeBooleanAttribute; 24import static com.android.internal.util.XmlUtils.writeIntAttribute; 25import static com.android.internal.util.XmlUtils.writeLongAttribute; 26import static com.android.server.Watchdog.NATIVE_STACKS_OF_INTEREST; 27import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT; 28import static org.xmlpull.v1.XmlPullParser.START_TAG; 29import static com.android.server.am.ActivityStackSupervisor.HOME_STACK_ID; 30 31import android.Manifest; 32import android.app.AppOpsManager; 33import android.app.IActivityContainer; 34import android.app.IActivityContainerCallback; 35import android.appwidget.AppWidgetManager; 36import android.graphics.Rect; 37import android.os.BatteryStats; 38import android.service.voice.IVoiceInteractionSession; 39import android.util.ArrayMap; 40 41import com.android.internal.R; 42import com.android.internal.annotations.GuardedBy; 43import com.android.internal.app.IAppOpsService; 44import com.android.internal.app.IVoiceInteractor; 45import com.android.internal.app.ProcessMap; 46import com.android.internal.app.ProcessStats; 47import com.android.internal.content.PackageMonitor; 48import com.android.internal.os.BackgroundThread; 49import com.android.internal.os.BatteryStatsImpl; 50import com.android.internal.os.ProcessCpuTracker; 51import com.android.internal.os.TransferPipe; 52import com.android.internal.os.Zygote; 53import com.android.internal.util.FastPrintWriter; 54import com.android.internal.util.FastXmlSerializer; 55import com.android.internal.util.MemInfoReader; 56import com.android.internal.util.Preconditions; 57import com.android.server.AppOpsService; 58import com.android.server.AttributeCache; 59import com.android.server.IntentResolver; 60import com.android.server.LocalServices; 61import com.android.server.ServiceThread; 62import com.android.server.SystemService; 63import com.android.server.SystemServiceManager; 64import com.android.server.Watchdog; 65import com.android.server.am.ActivityStack.ActivityState; 66import com.android.server.firewall.IntentFirewall; 67import com.android.server.pm.UserManagerService; 68import com.android.server.wm.AppTransition; 69import com.android.server.wm.WindowManagerService; 70import com.google.android.collect.Lists; 71import com.google.android.collect.Maps; 72 73import libcore.io.IoUtils; 74 75import org.xmlpull.v1.XmlPullParser; 76import org.xmlpull.v1.XmlPullParserException; 77import org.xmlpull.v1.XmlSerializer; 78 79import android.app.Activity; 80import android.app.ActivityManager; 81import android.app.ActivityManager.RunningTaskInfo; 82import android.app.ActivityManager.StackInfo; 83import android.app.ActivityManagerInternal; 84import android.app.ActivityManagerNative; 85import android.app.ActivityOptions; 86import android.app.ActivityThread; 87import android.app.AlertDialog; 88import android.app.AppGlobals; 89import android.app.ApplicationErrorReport; 90import android.app.Dialog; 91import android.app.IActivityController; 92import android.app.IApplicationThread; 93import android.app.IInstrumentationWatcher; 94import android.app.INotificationManager; 95import android.app.IProcessObserver; 96import android.app.IServiceConnection; 97import android.app.IStopUserCallback; 98import android.app.IUiAutomationConnection; 99import android.app.IUserSwitchObserver; 100import android.app.Instrumentation; 101import android.app.Notification; 102import android.app.NotificationManager; 103import android.app.PendingIntent; 104import android.app.backup.IBackupManager; 105import android.content.ActivityNotFoundException; 106import android.content.BroadcastReceiver; 107import android.content.ClipData; 108import android.content.ComponentCallbacks2; 109import android.content.ComponentName; 110import android.content.ContentProvider; 111import android.content.ContentResolver; 112import android.content.Context; 113import android.content.DialogInterface; 114import android.content.IContentProvider; 115import android.content.IIntentReceiver; 116import android.content.IIntentSender; 117import android.content.Intent; 118import android.content.IntentFilter; 119import android.content.IntentSender; 120import android.content.pm.ActivityInfo; 121import android.content.pm.ApplicationInfo; 122import android.content.pm.ConfigurationInfo; 123import android.content.pm.IPackageDataObserver; 124import android.content.pm.IPackageManager; 125import android.content.pm.InstrumentationInfo; 126import android.content.pm.PackageInfo; 127import android.content.pm.PackageManager; 128import android.content.pm.ParceledListSlice; 129import android.content.pm.UserInfo; 130import android.content.pm.PackageManager.NameNotFoundException; 131import android.content.pm.PathPermission; 132import android.content.pm.ProviderInfo; 133import android.content.pm.ResolveInfo; 134import android.content.pm.ServiceInfo; 135import android.content.res.CompatibilityInfo; 136import android.content.res.Configuration; 137import android.graphics.Bitmap; 138import android.net.Proxy; 139import android.net.ProxyProperties; 140import android.net.Uri; 141import android.os.Binder; 142import android.os.Build; 143import android.os.Bundle; 144import android.os.Debug; 145import android.os.DropBoxManager; 146import android.os.Environment; 147import android.os.FactoryTest; 148import android.os.FileObserver; 149import android.os.FileUtils; 150import android.os.Handler; 151import android.os.IBinder; 152import android.os.IPermissionController; 153import android.os.IRemoteCallback; 154import android.os.IUserManager; 155import android.os.Looper; 156import android.os.Message; 157import android.os.Parcel; 158import android.os.ParcelFileDescriptor; 159import android.os.Process; 160import android.os.RemoteCallbackList; 161import android.os.RemoteException; 162import android.os.SELinux; 163import android.os.ServiceManager; 164import android.os.StrictMode; 165import android.os.SystemClock; 166import android.os.SystemProperties; 167import android.os.UpdateLock; 168import android.os.UserHandle; 169import android.provider.Settings; 170import android.text.format.DateUtils; 171import android.text.format.Time; 172import android.util.AtomicFile; 173import android.util.EventLog; 174import android.util.Log; 175import android.util.Pair; 176import android.util.PrintWriterPrinter; 177import android.util.Slog; 178import android.util.SparseArray; 179import android.util.TimeUtils; 180import android.util.Xml; 181import android.view.Gravity; 182import android.view.LayoutInflater; 183import android.view.View; 184import android.view.WindowManager; 185 186import java.io.BufferedInputStream; 187import java.io.BufferedOutputStream; 188import java.io.DataInputStream; 189import java.io.DataOutputStream; 190import java.io.File; 191import java.io.FileDescriptor; 192import java.io.FileInputStream; 193import java.io.FileNotFoundException; 194import java.io.FileOutputStream; 195import java.io.IOException; 196import java.io.InputStreamReader; 197import java.io.PrintWriter; 198import java.io.StringWriter; 199import java.lang.ref.WeakReference; 200import java.util.ArrayList; 201import java.util.Arrays; 202import java.util.Collections; 203import java.util.Comparator; 204import java.util.HashMap; 205import java.util.HashSet; 206import java.util.Iterator; 207import java.util.List; 208import java.util.Locale; 209import java.util.Map; 210import java.util.Set; 211import java.util.concurrent.atomic.AtomicBoolean; 212import java.util.concurrent.atomic.AtomicLong; 213 214public final class ActivityManagerService extends ActivityManagerNative 215 implements Watchdog.Monitor, BatteryStatsImpl.BatteryCallback { 216 private static final String USER_DATA_DIR = "/data/user/"; 217 static final String TAG = "ActivityManager"; 218 static final String TAG_MU = "ActivityManagerServiceMU"; 219 static final boolean DEBUG = false; 220 static final boolean localLOGV = DEBUG; 221 static final boolean DEBUG_BACKUP = localLOGV || false; 222 static final boolean DEBUG_BROADCAST = localLOGV || false; 223 static final boolean DEBUG_BROADCAST_LIGHT = DEBUG_BROADCAST || false; 224 static final boolean DEBUG_BACKGROUND_BROADCAST = DEBUG_BROADCAST || false; 225 static final boolean DEBUG_CLEANUP = localLOGV || false; 226 static final boolean DEBUG_CONFIGURATION = localLOGV || false; 227 static final boolean DEBUG_FOCUS = false; 228 static final boolean DEBUG_IMMERSIVE = localLOGV || false; 229 static final boolean DEBUG_MU = localLOGV || false; 230 static final boolean DEBUG_OOM_ADJ = localLOGV || false; 231 static final boolean DEBUG_LRU = localLOGV || false; 232 static final boolean DEBUG_PAUSE = localLOGV || false; 233 static final boolean DEBUG_POWER = localLOGV || false; 234 static final boolean DEBUG_POWER_QUICK = DEBUG_POWER || false; 235 static final boolean DEBUG_PROCESS_OBSERVERS = localLOGV || false; 236 static final boolean DEBUG_PROCESSES = localLOGV || false; 237 static final boolean DEBUG_PROVIDER = localLOGV || false; 238 static final boolean DEBUG_RESULTS = localLOGV || false; 239 static final boolean DEBUG_SERVICE = localLOGV || false; 240 static final boolean DEBUG_SERVICE_EXECUTING = localLOGV || false; 241 static final boolean DEBUG_STACK = localLOGV || false; 242 static final boolean DEBUG_SWITCH = localLOGV || false; 243 static final boolean DEBUG_TASKS = localLOGV || false; 244 static final boolean DEBUG_THUMBNAILS = localLOGV || false; 245 static final boolean DEBUG_TRANSITION = localLOGV || false; 246 static final boolean DEBUG_URI_PERMISSION = localLOGV || false; 247 static final boolean DEBUG_USER_LEAVING = localLOGV || false; 248 static final boolean DEBUG_VISBILITY = localLOGV || false; 249 static final boolean DEBUG_PSS = localLOGV || false; 250 static final boolean DEBUG_LOCKSCREEN = localLOGV || false; 251 static final boolean VALIDATE_TOKENS = false; 252 static final boolean SHOW_ACTIVITY_START_TIME = true; 253 254 // Control over CPU and battery monitoring. 255 static final long BATTERY_STATS_TIME = 30*60*1000; // write battery stats every 30 minutes. 256 static final boolean MONITOR_CPU_USAGE = true; 257 static final long MONITOR_CPU_MIN_TIME = 5*1000; // don't sample cpu less than every 5 seconds. 258 static final long MONITOR_CPU_MAX_TIME = 0x0fffffff; // wait possibly forever for next cpu sample. 259 static final boolean MONITOR_THREAD_CPU_USAGE = false; 260 261 // The flags that are set for all calls we make to the package manager. 262 static final int STOCK_PM_FLAGS = PackageManager.GET_SHARED_LIBRARY_FILES; 263 264 private static final String SYSTEM_DEBUGGABLE = "ro.debuggable"; 265 266 static final boolean IS_USER_BUILD = "user".equals(Build.TYPE); 267 268 // Maximum number of recent tasks that we can remember. 269 static final int MAX_RECENT_TASKS = ActivityManager.isLowRamDeviceStatic() ? 10 : 20; 270 271 // Amount of time after a call to stopAppSwitches() during which we will 272 // prevent further untrusted switches from happening. 273 static final long APP_SWITCH_DELAY_TIME = 5*1000; 274 275 // How long we wait for a launched process to attach to the activity manager 276 // before we decide it's never going to come up for real. 277 static final int PROC_START_TIMEOUT = 10*1000; 278 279 // How long we wait for a launched process to attach to the activity manager 280 // before we decide it's never going to come up for real, when the process was 281 // started with a wrapper for instrumentation (such as Valgrind) because it 282 // could take much longer than usual. 283 static final int PROC_START_TIMEOUT_WITH_WRAPPER = 300*1000; 284 285 // How long to wait after going idle before forcing apps to GC. 286 static final int GC_TIMEOUT = 5*1000; 287 288 // The minimum amount of time between successive GC requests for a process. 289 static final int GC_MIN_INTERVAL = 60*1000; 290 291 // The minimum amount of time between successive PSS requests for a process. 292 static final int FULL_PSS_MIN_INTERVAL = 10*60*1000; 293 294 // The minimum amount of time between successive PSS requests for a process 295 // when the request is due to the memory state being lowered. 296 static final int FULL_PSS_LOWERED_INTERVAL = 2*60*1000; 297 298 // The rate at which we check for apps using excessive power -- 15 mins. 299 static final int POWER_CHECK_DELAY = (DEBUG_POWER_QUICK ? 2 : 15) * 60*1000; 300 301 // The minimum sample duration we will allow before deciding we have 302 // enough data on wake locks to start killing things. 303 static final int WAKE_LOCK_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 304 305 // The minimum sample duration we will allow before deciding we have 306 // enough data on CPU usage to start killing things. 307 static final int CPU_MIN_CHECK_DURATION = (DEBUG_POWER_QUICK ? 1 : 5) * 60*1000; 308 309 // How long we allow a receiver to run before giving up on it. 310 static final int BROADCAST_FG_TIMEOUT = 10*1000; 311 static final int BROADCAST_BG_TIMEOUT = 60*1000; 312 313 // How long we wait until we timeout on key dispatching. 314 static final int KEY_DISPATCHING_TIMEOUT = 5*1000; 315 316 // How long we wait until we timeout on key dispatching during instrumentation. 317 static final int INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT = 60*1000; 318 319 // Amount of time we wait for observers to handle a user switch before 320 // giving up on them and unfreezing the screen. 321 static final int USER_SWITCH_TIMEOUT = 2*1000; 322 323 // Maximum number of users we allow to be running at a time. 324 static final int MAX_RUNNING_USERS = 3; 325 326 // How long to wait in getAssistContextExtras for the activity and foreground services 327 // to respond with the result. 328 static final int PENDING_ASSIST_EXTRAS_TIMEOUT = 500; 329 330 // Maximum number of persisted Uri grants a package is allowed 331 static final int MAX_PERSISTED_URI_GRANTS = 128; 332 333 static final int MY_PID = Process.myPid(); 334 335 static final String[] EMPTY_STRING_ARRAY = new String[0]; 336 337 // How many bytes to write into the dropbox log before truncating 338 static final int DROPBOX_MAX_SIZE = 256 * 1024; 339 340 /** All system services */ 341 SystemServiceManager mSystemServiceManager; 342 343 /** Run all ActivityStacks through this */ 344 ActivityStackSupervisor mStackSupervisor; 345 346 public IntentFirewall mIntentFirewall; 347 348 // Whether we should show our dialogs (ANR, crash, etc) or just perform their 349 // default actuion automatically. Important for devices without direct input 350 // devices. 351 private boolean mShowDialogs = true; 352 353 /** 354 * Description of a request to start a new activity, which has been held 355 * due to app switches being disabled. 356 */ 357 static class PendingActivityLaunch { 358 final ActivityRecord r; 359 final ActivityRecord sourceRecord; 360 final int startFlags; 361 final ActivityStack stack; 362 363 PendingActivityLaunch(ActivityRecord _r, ActivityRecord _sourceRecord, 364 int _startFlags, ActivityStack _stack) { 365 r = _r; 366 sourceRecord = _sourceRecord; 367 startFlags = _startFlags; 368 stack = _stack; 369 } 370 } 371 372 final ArrayList<PendingActivityLaunch> mPendingActivityLaunches 373 = new ArrayList<PendingActivityLaunch>(); 374 375 BroadcastQueue mFgBroadcastQueue; 376 BroadcastQueue mBgBroadcastQueue; 377 // Convenient for easy iteration over the queues. Foreground is first 378 // so that dispatch of foreground broadcasts gets precedence. 379 final BroadcastQueue[] mBroadcastQueues = new BroadcastQueue[2]; 380 381 BroadcastQueue broadcastQueueForIntent(Intent intent) { 382 final boolean isFg = (intent.getFlags() & Intent.FLAG_RECEIVER_FOREGROUND) != 0; 383 if (DEBUG_BACKGROUND_BROADCAST) { 384 Slog.i(TAG, "Broadcast intent " + intent + " on " 385 + (isFg ? "foreground" : "background") 386 + " queue"); 387 } 388 return (isFg) ? mFgBroadcastQueue : mBgBroadcastQueue; 389 } 390 391 BroadcastRecord broadcastRecordForReceiverLocked(IBinder receiver) { 392 for (BroadcastQueue queue : mBroadcastQueues) { 393 BroadcastRecord r = queue.getMatchingOrderedReceiver(receiver); 394 if (r != null) { 395 return r; 396 } 397 } 398 return null; 399 } 400 401 /** 402 * Activity we have told the window manager to have key focus. 403 */ 404 ActivityRecord mFocusedActivity = null; 405 406 /** 407 * List of intents that were used to start the most recent tasks. 408 */ 409 final ArrayList<TaskRecord> mRecentTasks = new ArrayList<TaskRecord>(); 410 411 public class PendingAssistExtras extends Binder implements Runnable { 412 public final ActivityRecord activity; 413 public boolean haveResult = false; 414 public Bundle result = null; 415 public PendingAssistExtras(ActivityRecord _activity) { 416 activity = _activity; 417 } 418 @Override 419 public void run() { 420 Slog.w(TAG, "getAssistContextExtras failed: timeout retrieving from " + activity); 421 synchronized (this) { 422 haveResult = true; 423 notifyAll(); 424 } 425 } 426 } 427 428 final ArrayList<PendingAssistExtras> mPendingAssistExtras 429 = new ArrayList<PendingAssistExtras>(); 430 431 /** 432 * Process management. 433 */ 434 final ProcessList mProcessList = new ProcessList(); 435 436 /** 437 * All of the applications we currently have running organized by name. 438 * The keys are strings of the application package name (as 439 * returned by the package manager), and the keys are ApplicationRecord 440 * objects. 441 */ 442 final ProcessMap<ProcessRecord> mProcessNames = new ProcessMap<ProcessRecord>(); 443 444 /** 445 * Tracking long-term execution of processes to look for abuse and other 446 * bad app behavior. 447 */ 448 final ProcessStatsService mProcessStats; 449 450 /** 451 * The currently running isolated processes. 452 */ 453 final SparseArray<ProcessRecord> mIsolatedProcesses = new SparseArray<ProcessRecord>(); 454 455 /** 456 * Counter for assigning isolated process uids, to avoid frequently reusing the 457 * same ones. 458 */ 459 int mNextIsolatedProcessUid = 0; 460 461 /** 462 * The currently running heavy-weight process, if any. 463 */ 464 ProcessRecord mHeavyWeightProcess = null; 465 466 /** 467 * The last time that various processes have crashed. 468 */ 469 final ProcessMap<Long> mProcessCrashTimes = new ProcessMap<Long>(); 470 471 /** 472 * Information about a process that is currently marked as bad. 473 */ 474 static final class BadProcessInfo { 475 BadProcessInfo(long time, String shortMsg, String longMsg, String stack) { 476 this.time = time; 477 this.shortMsg = shortMsg; 478 this.longMsg = longMsg; 479 this.stack = stack; 480 } 481 482 final long time; 483 final String shortMsg; 484 final String longMsg; 485 final String stack; 486 } 487 488 /** 489 * Set of applications that we consider to be bad, and will reject 490 * incoming broadcasts from (which the user has no control over). 491 * Processes are added to this set when they have crashed twice within 492 * a minimum amount of time; they are removed from it when they are 493 * later restarted (hopefully due to some user action). The value is the 494 * time it was added to the list. 495 */ 496 final ProcessMap<BadProcessInfo> mBadProcesses = new ProcessMap<BadProcessInfo>(); 497 498 /** 499 * All of the processes we currently have running organized by pid. 500 * The keys are the pid running the application. 501 * 502 * <p>NOTE: This object is protected by its own lock, NOT the global 503 * activity manager lock! 504 */ 505 final SparseArray<ProcessRecord> mPidsSelfLocked = new SparseArray<ProcessRecord>(); 506 507 /** 508 * All of the processes that have been forced to be foreground. The key 509 * is the pid of the caller who requested it (we hold a death 510 * link on it). 511 */ 512 abstract class ForegroundToken implements IBinder.DeathRecipient { 513 int pid; 514 IBinder token; 515 } 516 final SparseArray<ForegroundToken> mForegroundProcesses = new SparseArray<ForegroundToken>(); 517 518 /** 519 * List of records for processes that someone had tried to start before the 520 * system was ready. We don't start them at that point, but ensure they 521 * are started by the time booting is complete. 522 */ 523 final ArrayList<ProcessRecord> mProcessesOnHold = new ArrayList<ProcessRecord>(); 524 525 /** 526 * List of persistent applications that are in the process 527 * of being started. 528 */ 529 final ArrayList<ProcessRecord> mPersistentStartingProcesses = new ArrayList<ProcessRecord>(); 530 531 /** 532 * Processes that are being forcibly torn down. 533 */ 534 final ArrayList<ProcessRecord> mRemovedProcesses = new ArrayList<ProcessRecord>(); 535 536 /** 537 * List of running applications, sorted by recent usage. 538 * The first entry in the list is the least recently used. 539 */ 540 final ArrayList<ProcessRecord> mLruProcesses = new ArrayList<ProcessRecord>(); 541 542 /** 543 * Where in mLruProcesses that the processes hosting activities start. 544 */ 545 int mLruProcessActivityStart = 0; 546 547 /** 548 * Where in mLruProcesses that the processes hosting services start. 549 * This is after (lower index) than mLruProcessesActivityStart. 550 */ 551 int mLruProcessServiceStart = 0; 552 553 /** 554 * List of processes that should gc as soon as things are idle. 555 */ 556 final ArrayList<ProcessRecord> mProcessesToGc = new ArrayList<ProcessRecord>(); 557 558 /** 559 * Processes we want to collect PSS data from. 560 */ 561 final ArrayList<ProcessRecord> mPendingPssProcesses = new ArrayList<ProcessRecord>(); 562 563 /** 564 * Last time we requested PSS data of all processes. 565 */ 566 long mLastFullPssTime = SystemClock.uptimeMillis(); 567 568 /** 569 * This is the process holding what we currently consider to be 570 * the "home" activity. 571 */ 572 ProcessRecord mHomeProcess; 573 574 /** 575 * This is the process holding the activity the user last visited that 576 * is in a different process from the one they are currently in. 577 */ 578 ProcessRecord mPreviousProcess; 579 580 /** 581 * The time at which the previous process was last visible. 582 */ 583 long mPreviousProcessVisibleTime; 584 585 /** 586 * Which uses have been started, so are allowed to run code. 587 */ 588 final SparseArray<UserStartedState> mStartedUsers = new SparseArray<UserStartedState>(); 589 590 /** 591 * LRU list of history of current users. Most recently current is at the end. 592 */ 593 final ArrayList<Integer> mUserLru = new ArrayList<Integer>(); 594 595 /** 596 * Constant array of the users that are currently started. 597 */ 598 int[] mStartedUserArray = new int[] { 0 }; 599 600 /** 601 * Registered observers of the user switching mechanics. 602 */ 603 final RemoteCallbackList<IUserSwitchObserver> mUserSwitchObservers 604 = new RemoteCallbackList<IUserSwitchObserver>(); 605 606 /** 607 * Currently active user switch. 608 */ 609 Object mCurUserSwitchCallback; 610 611 /** 612 * Packages that the user has asked to have run in screen size 613 * compatibility mode instead of filling the screen. 614 */ 615 final CompatModePackages mCompatModePackages; 616 617 /** 618 * Set of IntentSenderRecord objects that are currently active. 619 */ 620 final HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>> mIntentSenderRecords 621 = new HashMap<PendingIntentRecord.Key, WeakReference<PendingIntentRecord>>(); 622 623 /** 624 * Fingerprints (hashCode()) of stack traces that we've 625 * already logged DropBox entries for. Guarded by itself. If 626 * something (rogue user app) forces this over 627 * MAX_DUP_SUPPRESSED_STACKS entries, the contents are cleared. 628 */ 629 private final HashSet<Integer> mAlreadyLoggedViolatedStacks = new HashSet<Integer>(); 630 private static final int MAX_DUP_SUPPRESSED_STACKS = 5000; 631 632 /** 633 * Strict Mode background batched logging state. 634 * 635 * The string buffer is guarded by itself, and its lock is also 636 * used to determine if another batched write is already 637 * in-flight. 638 */ 639 private final StringBuilder mStrictModeBuffer = new StringBuilder(); 640 641 /** 642 * Keeps track of all IIntentReceivers that have been registered for 643 * broadcasts. Hash keys are the receiver IBinder, hash value is 644 * a ReceiverList. 645 */ 646 final HashMap<IBinder, ReceiverList> mRegisteredReceivers = 647 new HashMap<IBinder, ReceiverList>(); 648 649 /** 650 * Resolver for broadcast intents to registered receivers. 651 * Holds BroadcastFilter (subclass of IntentFilter). 652 */ 653 final IntentResolver<BroadcastFilter, BroadcastFilter> mReceiverResolver 654 = new IntentResolver<BroadcastFilter, BroadcastFilter>() { 655 @Override 656 protected boolean allowFilterResult( 657 BroadcastFilter filter, List<BroadcastFilter> dest) { 658 IBinder target = filter.receiverList.receiver.asBinder(); 659 for (int i=dest.size()-1; i>=0; i--) { 660 if (dest.get(i).receiverList.receiver.asBinder() == target) { 661 return false; 662 } 663 } 664 return true; 665 } 666 667 @Override 668 protected BroadcastFilter newResult(BroadcastFilter filter, int match, int userId) { 669 if (userId == UserHandle.USER_ALL || filter.owningUserId == UserHandle.USER_ALL 670 || userId == filter.owningUserId) { 671 return super.newResult(filter, match, userId); 672 } 673 return null; 674 } 675 676 @Override 677 protected BroadcastFilter[] newArray(int size) { 678 return new BroadcastFilter[size]; 679 } 680 681 @Override 682 protected boolean isPackageForFilter(String packageName, BroadcastFilter filter) { 683 return packageName.equals(filter.packageName); 684 } 685 }; 686 687 /** 688 * State of all active sticky broadcasts per user. Keys are the action of the 689 * sticky Intent, values are an ArrayList of all broadcasted intents with 690 * that action (which should usually be one). The SparseArray is keyed 691 * by the user ID the sticky is for, and can include UserHandle.USER_ALL 692 * for stickies that are sent to all users. 693 */ 694 final SparseArray<ArrayMap<String, ArrayList<Intent>>> mStickyBroadcasts = 695 new SparseArray<ArrayMap<String, ArrayList<Intent>>>(); 696 697 final ActiveServices mServices; 698 699 /** 700 * Backup/restore process management 701 */ 702 String mBackupAppName = null; 703 BackupRecord mBackupTarget = null; 704 705 final ProviderMap mProviderMap; 706 707 /** 708 * List of content providers who have clients waiting for them. The 709 * application is currently being launched and the provider will be 710 * removed from this list once it is published. 711 */ 712 final ArrayList<ContentProviderRecord> mLaunchingProviders 713 = new ArrayList<ContentProviderRecord>(); 714 715 /** 716 * File storing persisted {@link #mGrantedUriPermissions}. 717 */ 718 private final AtomicFile mGrantFile; 719 720 /** XML constants used in {@link #mGrantFile} */ 721 private static final String TAG_URI_GRANTS = "uri-grants"; 722 private static final String TAG_URI_GRANT = "uri-grant"; 723 private static final String ATTR_USER_HANDLE = "userHandle"; 724 private static final String ATTR_SOURCE_PKG = "sourcePkg"; 725 private static final String ATTR_TARGET_PKG = "targetPkg"; 726 private static final String ATTR_URI = "uri"; 727 private static final String ATTR_MODE_FLAGS = "modeFlags"; 728 private static final String ATTR_CREATED_TIME = "createdTime"; 729 private static final String ATTR_PREFIX = "prefix"; 730 731 /** 732 * Global set of specific {@link Uri} permissions that have been granted. 733 * This optimized lookup structure maps from {@link UriPermission#targetUid} 734 * to {@link UriPermission#uri} to {@link UriPermission}. 735 */ 736 @GuardedBy("this") 737 private final SparseArray<ArrayMap<GrantUri, UriPermission>> 738 mGrantedUriPermissions = new SparseArray<ArrayMap<GrantUri, UriPermission>>(); 739 740 public static class GrantUri { 741 public final Uri uri; 742 public final boolean prefix; 743 744 public GrantUri(Uri uri, boolean prefix) { 745 this.uri = uri; 746 this.prefix = prefix; 747 } 748 749 @Override 750 public int hashCode() { 751 return toString().hashCode(); 752 } 753 754 @Override 755 public boolean equals(Object o) { 756 if (o instanceof GrantUri) { 757 GrantUri other = (GrantUri) o; 758 return uri.equals(other.uri) && prefix == other.prefix; 759 } 760 return false; 761 } 762 763 @Override 764 public String toString() { 765 if (prefix) { 766 return uri.toString() + " [prefix]"; 767 } else { 768 return uri.toString(); 769 } 770 } 771 } 772 773 CoreSettingsObserver mCoreSettingsObserver; 774 775 /** 776 * Thread-local storage used to carry caller permissions over through 777 * indirect content-provider access. 778 */ 779 private class Identity { 780 public int pid; 781 public int uid; 782 783 Identity(int _pid, int _uid) { 784 pid = _pid; 785 uid = _uid; 786 } 787 } 788 789 private static final ThreadLocal<Identity> sCallerIdentity = new ThreadLocal<Identity>(); 790 791 /** 792 * All information we have collected about the runtime performance of 793 * any user id that can impact battery performance. 794 */ 795 final BatteryStatsService mBatteryStatsService; 796 797 /** 798 * Information about component usage 799 */ 800 final UsageStatsService mUsageStatsService; 801 802 /** 803 * Information about and control over application operations 804 */ 805 final AppOpsService mAppOpsService; 806 807 /** 808 * Current configuration information. HistoryRecord objects are given 809 * a reference to this object to indicate which configuration they are 810 * currently running in, so this object must be kept immutable. 811 */ 812 Configuration mConfiguration = new Configuration(); 813 814 /** 815 * Current sequencing integer of the configuration, for skipping old 816 * configurations. 817 */ 818 int mConfigurationSeq = 0; 819 820 /** 821 * Hardware-reported OpenGLES version. 822 */ 823 final int GL_ES_VERSION; 824 825 /** 826 * List of initialization arguments to pass to all processes when binding applications to them. 827 * For example, references to the commonly used services. 828 */ 829 HashMap<String, IBinder> mAppBindArgs; 830 831 /** 832 * Temporary to avoid allocations. Protected by main lock. 833 */ 834 final StringBuilder mStringBuilder = new StringBuilder(256); 835 836 /** 837 * Used to control how we initialize the service. 838 */ 839 ComponentName mTopComponent; 840 String mTopAction = Intent.ACTION_MAIN; 841 String mTopData; 842 boolean mProcessesReady = false; 843 boolean mSystemReady = false; 844 boolean mBooting = false; 845 boolean mWaitingUpdate = false; 846 boolean mDidUpdate = false; 847 boolean mOnBattery = false; 848 boolean mLaunchWarningShown = false; 849 850 Context mContext; 851 852 int mFactoryTest; 853 854 boolean mCheckedForSetup; 855 856 /** 857 * The time at which we will allow normal application switches again, 858 * after a call to {@link #stopAppSwitches()}. 859 */ 860 long mAppSwitchesAllowedTime; 861 862 /** 863 * This is set to true after the first switch after mAppSwitchesAllowedTime 864 * is set; any switches after that will clear the time. 865 */ 866 boolean mDidAppSwitch; 867 868 /** 869 * Last time (in realtime) at which we checked for power usage. 870 */ 871 long mLastPowerCheckRealtime; 872 873 /** 874 * Last time (in uptime) at which we checked for power usage. 875 */ 876 long mLastPowerCheckUptime; 877 878 /** 879 * Set while we are wanting to sleep, to prevent any 880 * activities from being started/resumed. 881 */ 882 private boolean mSleeping = false; 883 884 /** 885 * Set while we are running a voice interaction. This overrides 886 * sleeping while it is active. 887 */ 888 private boolean mRunningVoice = false; 889 890 /** 891 * State of external calls telling us if the device is asleep. 892 */ 893 private boolean mWentToSleep = false; 894 895 /** 896 * State of external call telling us if the lock screen is shown. 897 */ 898 private boolean mLockScreenShown = false; 899 900 /** 901 * Set if we are shutting down the system, similar to sleeping. 902 */ 903 boolean mShuttingDown = false; 904 905 /** 906 * Current sequence id for oom_adj computation traversal. 907 */ 908 int mAdjSeq = 0; 909 910 /** 911 * Current sequence id for process LRU updating. 912 */ 913 int mLruSeq = 0; 914 915 /** 916 * Keep track of the non-cached/empty process we last found, to help 917 * determine how to distribute cached/empty processes next time. 918 */ 919 int mNumNonCachedProcs = 0; 920 921 /** 922 * Keep track of the number of cached hidden procs, to balance oom adj 923 * distribution between those and empty procs. 924 */ 925 int mNumCachedHiddenProcs = 0; 926 927 /** 928 * Keep track of the number of service processes we last found, to 929 * determine on the next iteration which should be B services. 930 */ 931 int mNumServiceProcs = 0; 932 int mNewNumAServiceProcs = 0; 933 int mNewNumServiceProcs = 0; 934 935 /** 936 * Allow the current computed overall memory level of the system to go down? 937 * This is set to false when we are killing processes for reasons other than 938 * memory management, so that the now smaller process list will not be taken as 939 * an indication that memory is tighter. 940 */ 941 boolean mAllowLowerMemLevel = false; 942 943 /** 944 * The last computed memory level, for holding when we are in a state that 945 * processes are going away for other reasons. 946 */ 947 int mLastMemoryLevel = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 948 949 /** 950 * The last total number of process we have, to determine if changes actually look 951 * like a shrinking number of process due to lower RAM. 952 */ 953 int mLastNumProcesses; 954 955 /** 956 * The uptime of the last time we performed idle maintenance. 957 */ 958 long mLastIdleTime = SystemClock.uptimeMillis(); 959 960 /** 961 * Total time spent with RAM that has been added in the past since the last idle time. 962 */ 963 long mLowRamTimeSinceLastIdle = 0; 964 965 /** 966 * If RAM is currently low, when that horrible situation started. 967 */ 968 long mLowRamStartTime = 0; 969 970 /** 971 * For reporting to battery stats the current top application. 972 */ 973 private String mCurResumedPackage = null; 974 private int mCurResumedUid = -1; 975 976 /** 977 * For reporting to battery stats the apps currently running foreground 978 * service. The ProcessMap is package/uid tuples; each of these contain 979 * an array of the currently foreground processes. 980 */ 981 final ProcessMap<ArrayList<ProcessRecord>> mForegroundPackages 982 = new ProcessMap<ArrayList<ProcessRecord>>(); 983 984 /** 985 * This is set if we had to do a delayed dexopt of an app before launching 986 * it, to increasing the ANR timeouts in that case. 987 */ 988 boolean mDidDexOpt; 989 990 /** 991 * Set if the systemServer made a call to enterSafeMode. 992 */ 993 boolean mSafeMode; 994 995 String mDebugApp = null; 996 boolean mWaitForDebugger = false; 997 boolean mDebugTransient = false; 998 String mOrigDebugApp = null; 999 boolean mOrigWaitForDebugger = false; 1000 boolean mAlwaysFinishActivities = false; 1001 IActivityController mController = null; 1002 String mProfileApp = null; 1003 ProcessRecord mProfileProc = null; 1004 String mProfileFile; 1005 ParcelFileDescriptor mProfileFd; 1006 int mProfileType = 0; 1007 boolean mAutoStopProfiler = false; 1008 String mOpenGlTraceApp = null; 1009 1010 static class ProcessChangeItem { 1011 static final int CHANGE_ACTIVITIES = 1<<0; 1012 static final int CHANGE_PROCESS_STATE = 1<<1; 1013 int changes; 1014 int uid; 1015 int pid; 1016 int processState; 1017 boolean foregroundActivities; 1018 } 1019 1020 final RemoteCallbackList<IProcessObserver> mProcessObservers 1021 = new RemoteCallbackList<IProcessObserver>(); 1022 ProcessChangeItem[] mActiveProcessChanges = new ProcessChangeItem[5]; 1023 1024 final ArrayList<ProcessChangeItem> mPendingProcessChanges 1025 = new ArrayList<ProcessChangeItem>(); 1026 final ArrayList<ProcessChangeItem> mAvailProcessChanges 1027 = new ArrayList<ProcessChangeItem>(); 1028 1029 /** 1030 * Runtime CPU use collection thread. This object's lock is used to 1031 * protect all related state. 1032 */ 1033 final Thread mProcessCpuThread; 1034 1035 /** 1036 * Used to collect process stats when showing not responding dialog. 1037 * Protected by mProcessCpuThread. 1038 */ 1039 final ProcessCpuTracker mProcessCpuTracker = new ProcessCpuTracker( 1040 MONITOR_THREAD_CPU_USAGE); 1041 final AtomicLong mLastCpuTime = new AtomicLong(0); 1042 final AtomicBoolean mProcessCpuMutexFree = new AtomicBoolean(true); 1043 1044 long mLastWriteTime = 0; 1045 1046 /** 1047 * Used to retain an update lock when the foreground activity is in 1048 * immersive mode. 1049 */ 1050 final UpdateLock mUpdateLock = new UpdateLock("immersive"); 1051 1052 /** 1053 * Set to true after the system has finished booting. 1054 */ 1055 boolean mBooted = false; 1056 1057 int mProcessLimit = ProcessList.MAX_CACHED_APPS; 1058 int mProcessLimitOverride = -1; 1059 1060 WindowManagerService mWindowManager; 1061 1062 final ActivityThread mSystemThread; 1063 1064 int mCurrentUserId = 0; 1065 int[] mCurrentProfileIds = new int[] {UserHandle.USER_OWNER}; // Accessed by ActivityStack 1066 private UserManagerService mUserManager; 1067 1068 private final class AppDeathRecipient implements IBinder.DeathRecipient { 1069 final ProcessRecord mApp; 1070 final int mPid; 1071 final IApplicationThread mAppThread; 1072 1073 AppDeathRecipient(ProcessRecord app, int pid, 1074 IApplicationThread thread) { 1075 if (localLOGV) Slog.v( 1076 TAG, "New death recipient " + this 1077 + " for thread " + thread.asBinder()); 1078 mApp = app; 1079 mPid = pid; 1080 mAppThread = thread; 1081 } 1082 1083 @Override 1084 public void binderDied() { 1085 if (localLOGV) Slog.v( 1086 TAG, "Death received in " + this 1087 + " for thread " + mAppThread.asBinder()); 1088 synchronized(ActivityManagerService.this) { 1089 appDiedLocked(mApp, mPid, mAppThread); 1090 } 1091 } 1092 } 1093 1094 static final int SHOW_ERROR_MSG = 1; 1095 static final int SHOW_NOT_RESPONDING_MSG = 2; 1096 static final int SHOW_FACTORY_ERROR_MSG = 3; 1097 static final int UPDATE_CONFIGURATION_MSG = 4; 1098 static final int GC_BACKGROUND_PROCESSES_MSG = 5; 1099 static final int WAIT_FOR_DEBUGGER_MSG = 6; 1100 static final int SERVICE_TIMEOUT_MSG = 12; 1101 static final int UPDATE_TIME_ZONE = 13; 1102 static final int SHOW_UID_ERROR_MSG = 14; 1103 static final int IM_FEELING_LUCKY_MSG = 15; 1104 static final int PROC_START_TIMEOUT_MSG = 20; 1105 static final int DO_PENDING_ACTIVITY_LAUNCHES_MSG = 21; 1106 static final int KILL_APPLICATION_MSG = 22; 1107 static final int FINALIZE_PENDING_INTENT_MSG = 23; 1108 static final int POST_HEAVY_NOTIFICATION_MSG = 24; 1109 static final int CANCEL_HEAVY_NOTIFICATION_MSG = 25; 1110 static final int SHOW_STRICT_MODE_VIOLATION_MSG = 26; 1111 static final int CHECK_EXCESSIVE_WAKE_LOCKS_MSG = 27; 1112 static final int CLEAR_DNS_CACHE_MSG = 28; 1113 static final int UPDATE_HTTP_PROXY_MSG = 29; 1114 static final int SHOW_COMPAT_MODE_DIALOG_MSG = 30; 1115 static final int DISPATCH_PROCESSES_CHANGED = 31; 1116 static final int DISPATCH_PROCESS_DIED = 32; 1117 static final int REPORT_MEM_USAGE_MSG = 33; 1118 static final int REPORT_USER_SWITCH_MSG = 34; 1119 static final int CONTINUE_USER_SWITCH_MSG = 35; 1120 static final int USER_SWITCH_TIMEOUT_MSG = 36; 1121 static final int IMMERSIVE_MODE_LOCK_MSG = 37; 1122 static final int PERSIST_URI_GRANTS_MSG = 38; 1123 static final int REQUEST_ALL_PSS_MSG = 39; 1124 static final int START_PROFILES_MSG = 40; 1125 static final int UPDATE_TIME = 41; 1126 static final int SYSTEM_USER_START_MSG = 42; 1127 static final int SYSTEM_USER_CURRENT_MSG = 43; 1128 1129 static final int FIRST_ACTIVITY_STACK_MSG = 100; 1130 static final int FIRST_BROADCAST_QUEUE_MSG = 200; 1131 static final int FIRST_COMPAT_MODE_MSG = 300; 1132 static final int FIRST_SUPERVISOR_STACK_MSG = 100; 1133 1134 AlertDialog mUidAlert; 1135 CompatModeDialog mCompatModeDialog; 1136 long mLastMemUsageReportTime = 0; 1137 1138 /** 1139 * Flag whether the current user is a "monkey", i.e. whether 1140 * the UI is driven by a UI automation tool. 1141 */ 1142 private boolean mUserIsMonkey; 1143 1144 final ServiceThread mHandlerThread; 1145 final MainHandler mHandler; 1146 1147 final class MainHandler extends Handler { 1148 public MainHandler(Looper looper) { 1149 super(looper, null, true); 1150 } 1151 1152 @Override 1153 public void handleMessage(Message msg) { 1154 switch (msg.what) { 1155 case SHOW_ERROR_MSG: { 1156 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1157 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 1158 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 1159 synchronized (ActivityManagerService.this) { 1160 ProcessRecord proc = (ProcessRecord)data.get("app"); 1161 AppErrorResult res = (AppErrorResult) data.get("result"); 1162 if (proc != null && proc.crashDialog != null) { 1163 Slog.e(TAG, "App already has crash dialog: " + proc); 1164 if (res != null) { 1165 res.set(0); 1166 } 1167 return; 1168 } 1169 if (!showBackground && UserHandle.getAppId(proc.uid) 1170 >= Process.FIRST_APPLICATION_UID && proc.userId != mCurrentUserId 1171 && proc.pid != MY_PID) { 1172 Slog.w(TAG, "Skipping crash dialog of " + proc + ": background"); 1173 if (res != null) { 1174 res.set(0); 1175 } 1176 return; 1177 } 1178 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1179 Dialog d = new AppErrorDialog(mContext, 1180 ActivityManagerService.this, res, proc); 1181 d.show(); 1182 proc.crashDialog = d; 1183 } else { 1184 // The device is asleep, so just pretend that the user 1185 // saw a crash dialog and hit "force quit". 1186 if (res != null) { 1187 res.set(0); 1188 } 1189 } 1190 } 1191 1192 ensureBootCompleted(); 1193 } break; 1194 case SHOW_NOT_RESPONDING_MSG: { 1195 synchronized (ActivityManagerService.this) { 1196 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1197 ProcessRecord proc = (ProcessRecord)data.get("app"); 1198 if (proc != null && proc.anrDialog != null) { 1199 Slog.e(TAG, "App already has anr dialog: " + proc); 1200 return; 1201 } 1202 1203 Intent intent = new Intent("android.intent.action.ANR"); 1204 if (!mProcessesReady) { 1205 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 1206 | Intent.FLAG_RECEIVER_FOREGROUND); 1207 } 1208 broadcastIntentLocked(null, null, intent, 1209 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 1210 false, false, MY_PID, Process.SYSTEM_UID, 0 /* TODO: Verify */); 1211 1212 if (mShowDialogs) { 1213 Dialog d = new AppNotRespondingDialog(ActivityManagerService.this, 1214 mContext, proc, (ActivityRecord)data.get("activity"), 1215 msg.arg1 != 0); 1216 d.show(); 1217 proc.anrDialog = d; 1218 } else { 1219 // Just kill the app if there is no dialog to be shown. 1220 killAppAtUsersRequest(proc, null); 1221 } 1222 } 1223 1224 ensureBootCompleted(); 1225 } break; 1226 case SHOW_STRICT_MODE_VIOLATION_MSG: { 1227 HashMap<String, Object> data = (HashMap<String, Object>) msg.obj; 1228 synchronized (ActivityManagerService.this) { 1229 ProcessRecord proc = (ProcessRecord) data.get("app"); 1230 if (proc == null) { 1231 Slog.e(TAG, "App not found when showing strict mode dialog."); 1232 break; 1233 } 1234 if (proc.crashDialog != null) { 1235 Slog.e(TAG, "App already has strict mode dialog: " + proc); 1236 return; 1237 } 1238 AppErrorResult res = (AppErrorResult) data.get("result"); 1239 if (mShowDialogs && !mSleeping && !mShuttingDown) { 1240 Dialog d = new StrictModeViolationDialog(mContext, 1241 ActivityManagerService.this, res, proc); 1242 d.show(); 1243 proc.crashDialog = d; 1244 } else { 1245 // The device is asleep, so just pretend that the user 1246 // saw a crash dialog and hit "force quit". 1247 res.set(0); 1248 } 1249 } 1250 ensureBootCompleted(); 1251 } break; 1252 case SHOW_FACTORY_ERROR_MSG: { 1253 Dialog d = new FactoryErrorDialog( 1254 mContext, msg.getData().getCharSequence("msg")); 1255 d.show(); 1256 ensureBootCompleted(); 1257 } break; 1258 case UPDATE_CONFIGURATION_MSG: { 1259 final ContentResolver resolver = mContext.getContentResolver(); 1260 Settings.System.putConfiguration(resolver, (Configuration)msg.obj); 1261 } break; 1262 case GC_BACKGROUND_PROCESSES_MSG: { 1263 synchronized (ActivityManagerService.this) { 1264 performAppGcsIfAppropriateLocked(); 1265 } 1266 } break; 1267 case WAIT_FOR_DEBUGGER_MSG: { 1268 synchronized (ActivityManagerService.this) { 1269 ProcessRecord app = (ProcessRecord)msg.obj; 1270 if (msg.arg1 != 0) { 1271 if (!app.waitedForDebugger) { 1272 Dialog d = new AppWaitingForDebuggerDialog( 1273 ActivityManagerService.this, 1274 mContext, app); 1275 app.waitDialog = d; 1276 app.waitedForDebugger = true; 1277 d.show(); 1278 } 1279 } else { 1280 if (app.waitDialog != null) { 1281 app.waitDialog.dismiss(); 1282 app.waitDialog = null; 1283 } 1284 } 1285 } 1286 } break; 1287 case SERVICE_TIMEOUT_MSG: { 1288 if (mDidDexOpt) { 1289 mDidDexOpt = false; 1290 Message nmsg = mHandler.obtainMessage(SERVICE_TIMEOUT_MSG); 1291 nmsg.obj = msg.obj; 1292 mHandler.sendMessageDelayed(nmsg, ActiveServices.SERVICE_TIMEOUT); 1293 return; 1294 } 1295 mServices.serviceTimeout((ProcessRecord)msg.obj); 1296 } break; 1297 case UPDATE_TIME_ZONE: { 1298 synchronized (ActivityManagerService.this) { 1299 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1300 ProcessRecord r = mLruProcesses.get(i); 1301 if (r.thread != null) { 1302 try { 1303 r.thread.updateTimeZone(); 1304 } catch (RemoteException ex) { 1305 Slog.w(TAG, "Failed to update time zone for: " + r.info.processName); 1306 } 1307 } 1308 } 1309 } 1310 } break; 1311 case CLEAR_DNS_CACHE_MSG: { 1312 synchronized (ActivityManagerService.this) { 1313 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1314 ProcessRecord r = mLruProcesses.get(i); 1315 if (r.thread != null) { 1316 try { 1317 r.thread.clearDnsCache(); 1318 } catch (RemoteException ex) { 1319 Slog.w(TAG, "Failed to clear dns cache for: " + r.info.processName); 1320 } 1321 } 1322 } 1323 } 1324 } break; 1325 case UPDATE_HTTP_PROXY_MSG: { 1326 ProxyProperties proxy = (ProxyProperties)msg.obj; 1327 String host = ""; 1328 String port = ""; 1329 String exclList = ""; 1330 String pacFileUrl = null; 1331 if (proxy != null) { 1332 host = proxy.getHost(); 1333 port = Integer.toString(proxy.getPort()); 1334 exclList = proxy.getExclusionList(); 1335 pacFileUrl = proxy.getPacFileUrl(); 1336 } 1337 synchronized (ActivityManagerService.this) { 1338 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1339 ProcessRecord r = mLruProcesses.get(i); 1340 if (r.thread != null) { 1341 try { 1342 r.thread.setHttpProxy(host, port, exclList, pacFileUrl); 1343 } catch (RemoteException ex) { 1344 Slog.w(TAG, "Failed to update http proxy for: " + 1345 r.info.processName); 1346 } 1347 } 1348 } 1349 } 1350 } break; 1351 case SHOW_UID_ERROR_MSG: { 1352 String title = "System UIDs Inconsistent"; 1353 String text = "UIDs on the system are inconsistent, you need to wipe your" 1354 + " data partition or your device will be unstable."; 1355 Log.e(TAG, title + ": " + text); 1356 if (mShowDialogs) { 1357 // XXX This is a temporary dialog, no need to localize. 1358 AlertDialog d = new BaseErrorDialog(mContext); 1359 d.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ERROR); 1360 d.setCancelable(false); 1361 d.setTitle(title); 1362 d.setMessage(text); 1363 d.setButton(DialogInterface.BUTTON_POSITIVE, "I'm Feeling Lucky", 1364 mHandler.obtainMessage(IM_FEELING_LUCKY_MSG)); 1365 mUidAlert = d; 1366 d.show(); 1367 } 1368 } break; 1369 case IM_FEELING_LUCKY_MSG: { 1370 if (mUidAlert != null) { 1371 mUidAlert.dismiss(); 1372 mUidAlert = null; 1373 } 1374 } break; 1375 case PROC_START_TIMEOUT_MSG: { 1376 if (mDidDexOpt) { 1377 mDidDexOpt = false; 1378 Message nmsg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 1379 nmsg.obj = msg.obj; 1380 mHandler.sendMessageDelayed(nmsg, PROC_START_TIMEOUT); 1381 return; 1382 } 1383 ProcessRecord app = (ProcessRecord)msg.obj; 1384 synchronized (ActivityManagerService.this) { 1385 processStartTimedOutLocked(app); 1386 } 1387 } break; 1388 case DO_PENDING_ACTIVITY_LAUNCHES_MSG: { 1389 synchronized (ActivityManagerService.this) { 1390 doPendingActivityLaunchesLocked(true); 1391 } 1392 } break; 1393 case KILL_APPLICATION_MSG: { 1394 synchronized (ActivityManagerService.this) { 1395 int appid = msg.arg1; 1396 boolean restart = (msg.arg2 == 1); 1397 Bundle bundle = (Bundle)msg.obj; 1398 String pkg = bundle.getString("pkg"); 1399 String reason = bundle.getString("reason"); 1400 forceStopPackageLocked(pkg, appid, restart, false, true, false, 1401 false, UserHandle.USER_ALL, reason); 1402 } 1403 } break; 1404 case FINALIZE_PENDING_INTENT_MSG: { 1405 ((PendingIntentRecord)msg.obj).completeFinalize(); 1406 } break; 1407 case POST_HEAVY_NOTIFICATION_MSG: { 1408 INotificationManager inm = NotificationManager.getService(); 1409 if (inm == null) { 1410 return; 1411 } 1412 1413 ActivityRecord root = (ActivityRecord)msg.obj; 1414 ProcessRecord process = root.app; 1415 if (process == null) { 1416 return; 1417 } 1418 1419 try { 1420 Context context = mContext.createPackageContext(process.info.packageName, 0); 1421 String text = mContext.getString(R.string.heavy_weight_notification, 1422 context.getApplicationInfo().loadLabel(context.getPackageManager())); 1423 Notification notification = new Notification(); 1424 notification.icon = com.android.internal.R.drawable.stat_sys_adb; //context.getApplicationInfo().icon; 1425 notification.when = 0; 1426 notification.flags = Notification.FLAG_ONGOING_EVENT; 1427 notification.tickerText = text; 1428 notification.defaults = 0; // please be quiet 1429 notification.sound = null; 1430 notification.vibrate = null; 1431 notification.setLatestEventInfo(context, text, 1432 mContext.getText(R.string.heavy_weight_notification_detail), 1433 PendingIntent.getActivityAsUser(mContext, 0, root.intent, 1434 PendingIntent.FLAG_CANCEL_CURRENT, null, 1435 new UserHandle(root.userId))); 1436 1437 try { 1438 int[] outId = new int[1]; 1439 inm.enqueueNotificationWithTag("android", "android", null, 1440 R.string.heavy_weight_notification, 1441 notification, outId, root.userId); 1442 } catch (RuntimeException e) { 1443 Slog.w(ActivityManagerService.TAG, 1444 "Error showing notification for heavy-weight app", e); 1445 } catch (RemoteException e) { 1446 } 1447 } catch (NameNotFoundException e) { 1448 Slog.w(TAG, "Unable to create context for heavy notification", e); 1449 } 1450 } break; 1451 case CANCEL_HEAVY_NOTIFICATION_MSG: { 1452 INotificationManager inm = NotificationManager.getService(); 1453 if (inm == null) { 1454 return; 1455 } 1456 try { 1457 inm.cancelNotificationWithTag("android", null, 1458 R.string.heavy_weight_notification, msg.arg1); 1459 } catch (RuntimeException e) { 1460 Slog.w(ActivityManagerService.TAG, 1461 "Error canceling notification for service", e); 1462 } catch (RemoteException e) { 1463 } 1464 } break; 1465 case CHECK_EXCESSIVE_WAKE_LOCKS_MSG: { 1466 synchronized (ActivityManagerService.this) { 1467 checkExcessivePowerUsageLocked(true); 1468 removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1469 Message nmsg = obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 1470 sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 1471 } 1472 } break; 1473 case SHOW_COMPAT_MODE_DIALOG_MSG: { 1474 synchronized (ActivityManagerService.this) { 1475 ActivityRecord ar = (ActivityRecord)msg.obj; 1476 if (mCompatModeDialog != null) { 1477 if (mCompatModeDialog.mAppInfo.packageName.equals( 1478 ar.info.applicationInfo.packageName)) { 1479 return; 1480 } 1481 mCompatModeDialog.dismiss(); 1482 mCompatModeDialog = null; 1483 } 1484 if (ar != null && false) { 1485 if (mCompatModePackages.getPackageAskCompatModeLocked( 1486 ar.packageName)) { 1487 int mode = mCompatModePackages.computeCompatModeLocked( 1488 ar.info.applicationInfo); 1489 if (mode == ActivityManager.COMPAT_MODE_DISABLED 1490 || mode == ActivityManager.COMPAT_MODE_ENABLED) { 1491 mCompatModeDialog = new CompatModeDialog( 1492 ActivityManagerService.this, mContext, 1493 ar.info.applicationInfo); 1494 mCompatModeDialog.show(); 1495 } 1496 } 1497 } 1498 } 1499 break; 1500 } 1501 case DISPATCH_PROCESSES_CHANGED: { 1502 dispatchProcessesChanged(); 1503 break; 1504 } 1505 case DISPATCH_PROCESS_DIED: { 1506 final int pid = msg.arg1; 1507 final int uid = msg.arg2; 1508 dispatchProcessDied(pid, uid); 1509 break; 1510 } 1511 case REPORT_MEM_USAGE_MSG: { 1512 final ArrayList<ProcessMemInfo> memInfos = (ArrayList<ProcessMemInfo>)msg.obj; 1513 Thread thread = new Thread() { 1514 @Override public void run() { 1515 final SparseArray<ProcessMemInfo> infoMap 1516 = new SparseArray<ProcessMemInfo>(memInfos.size()); 1517 for (int i=0, N=memInfos.size(); i<N; i++) { 1518 ProcessMemInfo mi = memInfos.get(i); 1519 infoMap.put(mi.pid, mi); 1520 } 1521 updateCpuStatsNow(); 1522 synchronized (mProcessCpuThread) { 1523 final int N = mProcessCpuTracker.countStats(); 1524 for (int i=0; i<N; i++) { 1525 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 1526 if (st.vsize > 0) { 1527 long pss = Debug.getPss(st.pid, null); 1528 if (pss > 0) { 1529 if (infoMap.indexOfKey(st.pid) < 0) { 1530 ProcessMemInfo mi = new ProcessMemInfo(st.name, st.pid, 1531 ProcessList.NATIVE_ADJ, -1, "native", null); 1532 mi.pss = pss; 1533 memInfos.add(mi); 1534 } 1535 } 1536 } 1537 } 1538 } 1539 1540 long totalPss = 0; 1541 for (int i=0, N=memInfos.size(); i<N; i++) { 1542 ProcessMemInfo mi = memInfos.get(i); 1543 if (mi.pss == 0) { 1544 mi.pss = Debug.getPss(mi.pid, null); 1545 } 1546 totalPss += mi.pss; 1547 } 1548 Collections.sort(memInfos, new Comparator<ProcessMemInfo>() { 1549 @Override public int compare(ProcessMemInfo lhs, ProcessMemInfo rhs) { 1550 if (lhs.oomAdj != rhs.oomAdj) { 1551 return lhs.oomAdj < rhs.oomAdj ? -1 : 1; 1552 } 1553 if (lhs.pss != rhs.pss) { 1554 return lhs.pss < rhs.pss ? 1 : -1; 1555 } 1556 return 0; 1557 } 1558 }); 1559 1560 StringBuilder tag = new StringBuilder(128); 1561 StringBuilder stack = new StringBuilder(128); 1562 tag.append("Low on memory -- "); 1563 appendMemBucket(tag, totalPss, "total", false); 1564 appendMemBucket(stack, totalPss, "total", true); 1565 1566 StringBuilder logBuilder = new StringBuilder(1024); 1567 logBuilder.append("Low on memory:\n"); 1568 1569 boolean firstLine = true; 1570 int lastOomAdj = Integer.MIN_VALUE; 1571 for (int i=0, N=memInfos.size(); i<N; i++) { 1572 ProcessMemInfo mi = memInfos.get(i); 1573 1574 if (mi.oomAdj != ProcessList.NATIVE_ADJ 1575 && (mi.oomAdj < ProcessList.SERVICE_ADJ 1576 || mi.oomAdj == ProcessList.HOME_APP_ADJ 1577 || mi.oomAdj == ProcessList.PREVIOUS_APP_ADJ)) { 1578 if (lastOomAdj != mi.oomAdj) { 1579 lastOomAdj = mi.oomAdj; 1580 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1581 tag.append(" / "); 1582 } 1583 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ) { 1584 if (firstLine) { 1585 stack.append(":"); 1586 firstLine = false; 1587 } 1588 stack.append("\n\t at "); 1589 } else { 1590 stack.append("$"); 1591 } 1592 } else { 1593 tag.append(" "); 1594 stack.append("$"); 1595 } 1596 if (mi.oomAdj <= ProcessList.FOREGROUND_APP_ADJ) { 1597 appendMemBucket(tag, mi.pss, mi.name, false); 1598 } 1599 appendMemBucket(stack, mi.pss, mi.name, true); 1600 if (mi.oomAdj >= ProcessList.FOREGROUND_APP_ADJ 1601 && ((i+1) >= N || memInfos.get(i+1).oomAdj != lastOomAdj)) { 1602 stack.append("("); 1603 for (int k=0; k<DUMP_MEM_OOM_ADJ.length; k++) { 1604 if (DUMP_MEM_OOM_ADJ[k] == mi.oomAdj) { 1605 stack.append(DUMP_MEM_OOM_LABEL[k]); 1606 stack.append(":"); 1607 stack.append(DUMP_MEM_OOM_ADJ[k]); 1608 } 1609 } 1610 stack.append(")"); 1611 } 1612 } 1613 1614 logBuilder.append(" "); 1615 logBuilder.append(ProcessList.makeOomAdjString(mi.oomAdj)); 1616 logBuilder.append(' '); 1617 logBuilder.append(ProcessList.makeProcStateString(mi.procState)); 1618 logBuilder.append(' '); 1619 ProcessList.appendRamKb(logBuilder, mi.pss); 1620 logBuilder.append(" kB: "); 1621 logBuilder.append(mi.name); 1622 logBuilder.append(" ("); 1623 logBuilder.append(mi.pid); 1624 logBuilder.append(") "); 1625 logBuilder.append(mi.adjType); 1626 logBuilder.append('\n'); 1627 if (mi.adjReason != null) { 1628 logBuilder.append(" "); 1629 logBuilder.append(mi.adjReason); 1630 logBuilder.append('\n'); 1631 } 1632 } 1633 1634 logBuilder.append(" "); 1635 ProcessList.appendRamKb(logBuilder, totalPss); 1636 logBuilder.append(" kB: TOTAL\n"); 1637 1638 long[] infos = new long[Debug.MEMINFO_COUNT]; 1639 Debug.getMemInfo(infos); 1640 logBuilder.append(" MemInfo: "); 1641 logBuilder.append(infos[Debug.MEMINFO_SLAB]).append(" kB slab, "); 1642 logBuilder.append(infos[Debug.MEMINFO_SHMEM]).append(" kB shmem, "); 1643 logBuilder.append(infos[Debug.MEMINFO_BUFFERS]).append(" kB buffers, "); 1644 logBuilder.append(infos[Debug.MEMINFO_CACHED]).append(" kB cached, "); 1645 logBuilder.append(infos[Debug.MEMINFO_FREE]).append(" kB free\n"); 1646 if (infos[Debug.MEMINFO_ZRAM_TOTAL] != 0) { 1647 logBuilder.append(" ZRAM: "); 1648 logBuilder.append(infos[Debug.MEMINFO_ZRAM_TOTAL]); 1649 logBuilder.append(" kB RAM, "); 1650 logBuilder.append(infos[Debug.MEMINFO_SWAP_TOTAL]); 1651 logBuilder.append(" kB swap total, "); 1652 logBuilder.append(infos[Debug.MEMINFO_SWAP_FREE]); 1653 logBuilder.append(" kB swap free\n"); 1654 } 1655 Slog.i(TAG, logBuilder.toString()); 1656 1657 StringBuilder dropBuilder = new StringBuilder(1024); 1658 /* 1659 StringWriter oomSw = new StringWriter(); 1660 PrintWriter oomPw = new FastPrintWriter(oomSw, false, 256); 1661 StringWriter catSw = new StringWriter(); 1662 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1663 String[] emptyArgs = new String[] { }; 1664 dumpApplicationMemoryUsage(null, oomPw, " ", emptyArgs, true, catPw); 1665 oomPw.flush(); 1666 String oomString = oomSw.toString(); 1667 */ 1668 dropBuilder.append(stack); 1669 dropBuilder.append('\n'); 1670 dropBuilder.append('\n'); 1671 dropBuilder.append(logBuilder); 1672 dropBuilder.append('\n'); 1673 /* 1674 dropBuilder.append(oomString); 1675 dropBuilder.append('\n'); 1676 */ 1677 StringWriter catSw = new StringWriter(); 1678 synchronized (ActivityManagerService.this) { 1679 PrintWriter catPw = new FastPrintWriter(catSw, false, 256); 1680 String[] emptyArgs = new String[] { }; 1681 catPw.println(); 1682 dumpProcessesLocked(null, catPw, emptyArgs, 0, false, null); 1683 catPw.println(); 1684 mServices.dumpServicesLocked(null, catPw, emptyArgs, 0, 1685 false, false, null); 1686 catPw.println(); 1687 dumpActivitiesLocked(null, catPw, emptyArgs, 0, false, false, null); 1688 catPw.flush(); 1689 } 1690 dropBuilder.append(catSw.toString()); 1691 addErrorToDropBox("lowmem", null, "system_server", null, 1692 null, tag.toString(), dropBuilder.toString(), null, null); 1693 //Slog.i(TAG, "Sent to dropbox:"); 1694 //Slog.i(TAG, dropBuilder.toString()); 1695 synchronized (ActivityManagerService.this) { 1696 long now = SystemClock.uptimeMillis(); 1697 if (mLastMemUsageReportTime < now) { 1698 mLastMemUsageReportTime = now; 1699 } 1700 } 1701 } 1702 }; 1703 thread.start(); 1704 break; 1705 } 1706 case REPORT_USER_SWITCH_MSG: { 1707 dispatchUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1708 break; 1709 } 1710 case CONTINUE_USER_SWITCH_MSG: { 1711 continueUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1712 break; 1713 } 1714 case USER_SWITCH_TIMEOUT_MSG: { 1715 timeoutUserSwitch((UserStartedState) msg.obj, msg.arg1, msg.arg2); 1716 break; 1717 } 1718 case IMMERSIVE_MODE_LOCK_MSG: { 1719 final boolean nextState = (msg.arg1 != 0); 1720 if (mUpdateLock.isHeld() != nextState) { 1721 if (DEBUG_IMMERSIVE) { 1722 final ActivityRecord r = (ActivityRecord) msg.obj; 1723 Slog.d(TAG, "Applying new update lock state '" + nextState + "' for " + r); 1724 } 1725 if (nextState) { 1726 mUpdateLock.acquire(); 1727 } else { 1728 mUpdateLock.release(); 1729 } 1730 } 1731 break; 1732 } 1733 case PERSIST_URI_GRANTS_MSG: { 1734 writeGrantedUriPermissions(); 1735 break; 1736 } 1737 case REQUEST_ALL_PSS_MSG: { 1738 requestPssAllProcsLocked(SystemClock.uptimeMillis(), true, false); 1739 break; 1740 } 1741 case START_PROFILES_MSG: { 1742 synchronized (ActivityManagerService.this) { 1743 startProfilesLocked(); 1744 } 1745 break; 1746 } 1747 case UPDATE_TIME: { 1748 synchronized (ActivityManagerService.this) { 1749 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 1750 ProcessRecord r = mLruProcesses.get(i); 1751 if (r.thread != null) { 1752 try { 1753 r.thread.updateTimePrefs(msg.arg1 == 0 ? false : true); 1754 } catch (RemoteException ex) { 1755 Slog.w(TAG, "Failed to update preferences for: " + r.info.processName); 1756 } 1757 } 1758 } 1759 } 1760 break; 1761 } 1762 case SYSTEM_USER_START_MSG: { 1763 mSystemServiceManager.startUser(msg.arg1); 1764 break; 1765 } 1766 case SYSTEM_USER_CURRENT_MSG: { 1767 mSystemServiceManager.switchUser(msg.arg1); 1768 break; 1769 } 1770 } 1771 } 1772 }; 1773 1774 static final int COLLECT_PSS_BG_MSG = 1; 1775 1776 final Handler mBgHandler = new Handler(BackgroundThread.getHandler().getLooper()) { 1777 @Override 1778 public void handleMessage(Message msg) { 1779 switch (msg.what) { 1780 case COLLECT_PSS_BG_MSG: { 1781 int i=0, num=0; 1782 long start = SystemClock.uptimeMillis(); 1783 long[] tmp = new long[1]; 1784 do { 1785 ProcessRecord proc; 1786 int procState; 1787 int pid; 1788 synchronized (ActivityManagerService.this) { 1789 if (i >= mPendingPssProcesses.size()) { 1790 if (DEBUG_PSS) Slog.d(TAG, "Collected PSS of " + num + " of " + i 1791 + " processes in " + (SystemClock.uptimeMillis()-start) + "ms"); 1792 mPendingPssProcesses.clear(); 1793 return; 1794 } 1795 proc = mPendingPssProcesses.get(i); 1796 procState = proc.pssProcState; 1797 if (proc.thread != null && procState == proc.setProcState) { 1798 pid = proc.pid; 1799 } else { 1800 proc = null; 1801 pid = 0; 1802 } 1803 i++; 1804 } 1805 if (proc != null) { 1806 long pss = Debug.getPss(pid, tmp); 1807 synchronized (ActivityManagerService.this) { 1808 if (proc.thread != null && proc.setProcState == procState 1809 && proc.pid == pid) { 1810 num++; 1811 proc.lastPssTime = SystemClock.uptimeMillis(); 1812 proc.baseProcessTracker.addPss(pss, tmp[0], true, proc.pkgList); 1813 if (DEBUG_PSS) Slog.d(TAG, "PSS of " + proc.toShortString() 1814 + ": " + pss + " lastPss=" + proc.lastPss 1815 + " state=" + ProcessList.makeProcStateString(procState)); 1816 if (proc.initialIdlePss == 0) { 1817 proc.initialIdlePss = pss; 1818 } 1819 proc.lastPss = pss; 1820 if (procState >= ActivityManager.PROCESS_STATE_HOME) { 1821 proc.lastCachedPss = pss; 1822 } 1823 } 1824 } 1825 } 1826 } while (true); 1827 } 1828 } 1829 } 1830 }; 1831 1832 /** 1833 * Monitor for package changes and update our internal state. 1834 */ 1835 private final PackageMonitor mPackageMonitor = new PackageMonitor() { 1836 @Override 1837 public void onPackageRemoved(String packageName, int uid) { 1838 // Remove all tasks with activities in the specified package from the list of recent tasks 1839 synchronized (ActivityManagerService.this) { 1840 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 1841 TaskRecord tr = mRecentTasks.get(i); 1842 ComponentName cn = tr.intent.getComponent(); 1843 if (cn != null && cn.getPackageName().equals(packageName)) { 1844 // If the package name matches, remove the task and kill the process 1845 removeTaskByIdLocked(tr.taskId, ActivityManager.REMOVE_TASK_KILL_PROCESS); 1846 } 1847 } 1848 } 1849 } 1850 1851 @Override 1852 public boolean onPackageChanged(String packageName, int uid, String[] components) { 1853 final PackageManager pm = mContext.getPackageManager(); 1854 final ArrayList<Pair<Intent, Integer>> recentTaskIntents = 1855 new ArrayList<Pair<Intent, Integer>>(); 1856 final ArrayList<Integer> tasksToRemove = new ArrayList<Integer>(); 1857 // Copy the list of recent tasks so that we don't hold onto the lock on 1858 // ActivityManagerService for long periods while checking if components exist. 1859 synchronized (ActivityManagerService.this) { 1860 for (int i = mRecentTasks.size() - 1; i >= 0; i--) { 1861 TaskRecord tr = mRecentTasks.get(i); 1862 recentTaskIntents.add(new Pair<Intent, Integer>(tr.intent, tr.taskId)); 1863 } 1864 } 1865 // Check the recent tasks and filter out all tasks with components that no longer exist. 1866 Intent tmpI = new Intent(); 1867 for (int i = recentTaskIntents.size() - 1; i >= 0; i--) { 1868 Pair<Intent, Integer> p = recentTaskIntents.get(i); 1869 ComponentName cn = p.first.getComponent(); 1870 if (cn != null && cn.getPackageName().equals(packageName)) { 1871 try { 1872 // Add the task to the list to remove if the component no longer exists 1873 tmpI.setComponent(cn); 1874 if (pm.queryIntentActivities(tmpI, PackageManager.MATCH_DEFAULT_ONLY).isEmpty()) { 1875 tasksToRemove.add(p.second); 1876 } 1877 } catch (Exception e) {} 1878 } 1879 } 1880 // Prune all the tasks with removed components from the list of recent tasks 1881 synchronized (ActivityManagerService.this) { 1882 for (int i = tasksToRemove.size() - 1; i >= 0; i--) { 1883 // Remove the task but don't kill the process (since other components in that 1884 // package may still be running and in the background) 1885 removeTaskByIdLocked(tasksToRemove.get(i), 0); 1886 } 1887 } 1888 return true; 1889 } 1890 1891 @Override 1892 public boolean onHandleForceStop(Intent intent, String[] packages, int uid, boolean doit) { 1893 // Force stop the specified packages 1894 if (packages != null) { 1895 for (String pkg : packages) { 1896 synchronized (ActivityManagerService.this) { 1897 if (forceStopPackageLocked(pkg, -1, false, false, false, false, false, 0, 1898 "finished booting")) { 1899 return true; 1900 } 1901 } 1902 } 1903 } 1904 return false; 1905 } 1906 }; 1907 1908 public void setSystemProcess() { 1909 try { 1910 ServiceManager.addService(Context.ACTIVITY_SERVICE, this, true); 1911 ServiceManager.addService(ProcessStats.SERVICE_NAME, mProcessStats); 1912 ServiceManager.addService("meminfo", new MemBinder(this)); 1913 ServiceManager.addService("gfxinfo", new GraphicsBinder(this)); 1914 ServiceManager.addService("dbinfo", new DbBinder(this)); 1915 if (MONITOR_CPU_USAGE) { 1916 ServiceManager.addService("cpuinfo", new CpuBinder(this)); 1917 } 1918 ServiceManager.addService("permission", new PermissionController(this)); 1919 1920 ApplicationInfo info = mContext.getPackageManager().getApplicationInfo( 1921 "android", STOCK_PM_FLAGS); 1922 mSystemThread.installSystemApplicationInfo(info); 1923 1924 synchronized (this) { 1925 ProcessRecord app = newProcessRecordLocked(info, info.processName, false); 1926 app.persistent = true; 1927 app.pid = MY_PID; 1928 app.maxAdj = ProcessList.SYSTEM_ADJ; 1929 app.makeActive(mSystemThread.getApplicationThread(), mProcessStats); 1930 mProcessNames.put(app.processName, app.uid, app); 1931 synchronized (mPidsSelfLocked) { 1932 mPidsSelfLocked.put(app.pid, app); 1933 } 1934 updateLruProcessLocked(app, false, null); 1935 updateOomAdjLocked(); 1936 } 1937 } catch (PackageManager.NameNotFoundException e) { 1938 throw new RuntimeException( 1939 "Unable to find android system package", e); 1940 } 1941 } 1942 1943 public void setWindowManager(WindowManagerService wm) { 1944 mWindowManager = wm; 1945 mStackSupervisor.setWindowManager(wm); 1946 } 1947 1948 public void startObservingNativeCrashes() { 1949 final NativeCrashListener ncl = new NativeCrashListener(this); 1950 ncl.start(); 1951 } 1952 1953 public IAppOpsService getAppOpsService() { 1954 return mAppOpsService; 1955 } 1956 1957 static class MemBinder extends Binder { 1958 ActivityManagerService mActivityManagerService; 1959 MemBinder(ActivityManagerService activityManagerService) { 1960 mActivityManagerService = activityManagerService; 1961 } 1962 1963 @Override 1964 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 1965 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 1966 != PackageManager.PERMISSION_GRANTED) { 1967 pw.println("Permission Denial: can't dump meminfo from from pid=" 1968 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 1969 + " without permission " + android.Manifest.permission.DUMP); 1970 return; 1971 } 1972 1973 mActivityManagerService.dumpApplicationMemoryUsage(fd, pw, " ", args, false, null); 1974 } 1975 } 1976 1977 static class GraphicsBinder extends Binder { 1978 ActivityManagerService mActivityManagerService; 1979 GraphicsBinder(ActivityManagerService activityManagerService) { 1980 mActivityManagerService = activityManagerService; 1981 } 1982 1983 @Override 1984 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 1985 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 1986 != PackageManager.PERMISSION_GRANTED) { 1987 pw.println("Permission Denial: can't dump gfxinfo from from pid=" 1988 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 1989 + " without permission " + android.Manifest.permission.DUMP); 1990 return; 1991 } 1992 1993 mActivityManagerService.dumpGraphicsHardwareUsage(fd, pw, args); 1994 } 1995 } 1996 1997 static class DbBinder extends Binder { 1998 ActivityManagerService mActivityManagerService; 1999 DbBinder(ActivityManagerService activityManagerService) { 2000 mActivityManagerService = activityManagerService; 2001 } 2002 2003 @Override 2004 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2005 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2006 != PackageManager.PERMISSION_GRANTED) { 2007 pw.println("Permission Denial: can't dump dbinfo from from pid=" 2008 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2009 + " without permission " + android.Manifest.permission.DUMP); 2010 return; 2011 } 2012 2013 mActivityManagerService.dumpDbInfo(fd, pw, args); 2014 } 2015 } 2016 2017 static class CpuBinder extends Binder { 2018 ActivityManagerService mActivityManagerService; 2019 CpuBinder(ActivityManagerService activityManagerService) { 2020 mActivityManagerService = activityManagerService; 2021 } 2022 2023 @Override 2024 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 2025 if (mActivityManagerService.checkCallingPermission(android.Manifest.permission.DUMP) 2026 != PackageManager.PERMISSION_GRANTED) { 2027 pw.println("Permission Denial: can't dump cpuinfo from from pid=" 2028 + Binder.getCallingPid() + ", uid=" + Binder.getCallingUid() 2029 + " without permission " + android.Manifest.permission.DUMP); 2030 return; 2031 } 2032 2033 synchronized (mActivityManagerService.mProcessCpuThread) { 2034 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentLoad()); 2035 pw.print(mActivityManagerService.mProcessCpuTracker.printCurrentState( 2036 SystemClock.uptimeMillis())); 2037 } 2038 } 2039 } 2040 2041 public static final class Lifecycle extends SystemService { 2042 private final ActivityManagerService mService; 2043 2044 public Lifecycle(Context context) { 2045 super(context); 2046 mService = new ActivityManagerService(context); 2047 } 2048 2049 @Override 2050 public void onStart() { 2051 mService.start(); 2052 } 2053 2054 public ActivityManagerService getService() { 2055 return mService; 2056 } 2057 } 2058 2059 // Note: This method is invoked on the main thread but may need to attach various 2060 // handlers to other threads. So take care to be explicit about the looper. 2061 public ActivityManagerService(Context systemContext) { 2062 mContext = systemContext; 2063 mFactoryTest = FactoryTest.getMode(); 2064 mSystemThread = ActivityThread.currentActivityThread(); 2065 2066 Slog.i(TAG, "Memory class: " + ActivityManager.staticGetMemoryClass()); 2067 2068 mHandlerThread = new ServiceThread(TAG, 2069 android.os.Process.THREAD_PRIORITY_FOREGROUND, false /*allowIo*/); 2070 mHandlerThread.start(); 2071 mHandler = new MainHandler(mHandlerThread.getLooper()); 2072 2073 mFgBroadcastQueue = new BroadcastQueue(this, mHandler, 2074 "foreground", BROADCAST_FG_TIMEOUT, false); 2075 mBgBroadcastQueue = new BroadcastQueue(this, mHandler, 2076 "background", BROADCAST_BG_TIMEOUT, true); 2077 mBroadcastQueues[0] = mFgBroadcastQueue; 2078 mBroadcastQueues[1] = mBgBroadcastQueue; 2079 2080 mServices = new ActiveServices(this); 2081 mProviderMap = new ProviderMap(this); 2082 2083 // TODO: Move creation of battery stats service outside of activity manager service. 2084 File dataDir = Environment.getDataDirectory(); 2085 File systemDir = new File(dataDir, "system"); 2086 systemDir.mkdirs(); 2087 mBatteryStatsService = new BatteryStatsService(new File( 2088 systemDir, "batterystats.bin").toString(), mHandler); 2089 mBatteryStatsService.getActiveStatistics().readLocked(); 2090 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2091 mOnBattery = DEBUG_POWER ? true 2092 : mBatteryStatsService.getActiveStatistics().getIsOnBattery(); 2093 mBatteryStatsService.getActiveStatistics().setCallback(this); 2094 2095 mProcessStats = new ProcessStatsService(this, new File(systemDir, "procstats")); 2096 2097 mUsageStatsService = new UsageStatsService(new File(systemDir, "usagestats").toString()); 2098 mAppOpsService = new AppOpsService(new File(systemDir, "appops.xml"), mHandler); 2099 2100 mGrantFile = new AtomicFile(new File(systemDir, "urigrants.xml")); 2101 2102 // User 0 is the first and only user that runs at boot. 2103 mStartedUsers.put(0, new UserStartedState(new UserHandle(0), true)); 2104 mUserLru.add(Integer.valueOf(0)); 2105 updateStartedUserArrayLocked(); 2106 2107 GL_ES_VERSION = SystemProperties.getInt("ro.opengles.version", 2108 ConfigurationInfo.GL_ES_VERSION_UNDEFINED); 2109 2110 mConfiguration.setToDefaults(); 2111 mConfiguration.setLocale(Locale.getDefault()); 2112 2113 mConfigurationSeq = mConfiguration.seq = 1; 2114 mProcessCpuTracker.init(); 2115 2116 mCompatModePackages = new CompatModePackages(this, systemDir, mHandler); 2117 mIntentFirewall = new IntentFirewall(new IntentFirewallInterface(), mHandler); 2118 mStackSupervisor = new ActivityStackSupervisor(this); 2119 2120 mProcessCpuThread = new Thread("CpuTracker") { 2121 @Override 2122 public void run() { 2123 while (true) { 2124 try { 2125 try { 2126 synchronized(this) { 2127 final long now = SystemClock.uptimeMillis(); 2128 long nextCpuDelay = (mLastCpuTime.get()+MONITOR_CPU_MAX_TIME)-now; 2129 long nextWriteDelay = (mLastWriteTime+BATTERY_STATS_TIME)-now; 2130 //Slog.i(TAG, "Cpu delay=" + nextCpuDelay 2131 // + ", write delay=" + nextWriteDelay); 2132 if (nextWriteDelay < nextCpuDelay) { 2133 nextCpuDelay = nextWriteDelay; 2134 } 2135 if (nextCpuDelay > 0) { 2136 mProcessCpuMutexFree.set(true); 2137 this.wait(nextCpuDelay); 2138 } 2139 } 2140 } catch (InterruptedException e) { 2141 } 2142 updateCpuStatsNow(); 2143 } catch (Exception e) { 2144 Slog.e(TAG, "Unexpected exception collecting process stats", e); 2145 } 2146 } 2147 } 2148 }; 2149 2150 Watchdog.getInstance().addMonitor(this); 2151 Watchdog.getInstance().addThread(mHandler); 2152 } 2153 2154 public void setSystemServiceManager(SystemServiceManager mgr) { 2155 mSystemServiceManager = mgr; 2156 } 2157 2158 private void start() { 2159 mProcessCpuThread.start(); 2160 2161 mBatteryStatsService.publish(mContext); 2162 mUsageStatsService.publish(mContext); 2163 mAppOpsService.publish(mContext); 2164 2165 LocalServices.addService(ActivityManagerInternal.class, new LocalService()); 2166 } 2167 2168 @Override 2169 public boolean onTransact(int code, Parcel data, Parcel reply, int flags) 2170 throws RemoteException { 2171 if (code == SYSPROPS_TRANSACTION) { 2172 // We need to tell all apps about the system property change. 2173 ArrayList<IBinder> procs = new ArrayList<IBinder>(); 2174 synchronized(this) { 2175 final int NP = mProcessNames.getMap().size(); 2176 for (int ip=0; ip<NP; ip++) { 2177 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 2178 final int NA = apps.size(); 2179 for (int ia=0; ia<NA; ia++) { 2180 ProcessRecord app = apps.valueAt(ia); 2181 if (app.thread != null) { 2182 procs.add(app.thread.asBinder()); 2183 } 2184 } 2185 } 2186 } 2187 2188 int N = procs.size(); 2189 for (int i=0; i<N; i++) { 2190 Parcel data2 = Parcel.obtain(); 2191 try { 2192 procs.get(i).transact(IBinder.SYSPROPS_TRANSACTION, data2, null, 0); 2193 } catch (RemoteException e) { 2194 } 2195 data2.recycle(); 2196 } 2197 } 2198 try { 2199 return super.onTransact(code, data, reply, flags); 2200 } catch (RuntimeException e) { 2201 // The activity manager only throws security exceptions, so let's 2202 // log all others. 2203 if (!(e instanceof SecurityException)) { 2204 Slog.wtf(TAG, "Activity Manager Crash", e); 2205 } 2206 throw e; 2207 } 2208 } 2209 2210 void updateCpuStats() { 2211 final long now = SystemClock.uptimeMillis(); 2212 if (mLastCpuTime.get() >= now - MONITOR_CPU_MIN_TIME) { 2213 return; 2214 } 2215 if (mProcessCpuMutexFree.compareAndSet(true, false)) { 2216 synchronized (mProcessCpuThread) { 2217 mProcessCpuThread.notify(); 2218 } 2219 } 2220 } 2221 2222 void updateCpuStatsNow() { 2223 synchronized (mProcessCpuThread) { 2224 mProcessCpuMutexFree.set(false); 2225 final long now = SystemClock.uptimeMillis(); 2226 boolean haveNewCpuStats = false; 2227 2228 if (MONITOR_CPU_USAGE && 2229 mLastCpuTime.get() < (now-MONITOR_CPU_MIN_TIME)) { 2230 mLastCpuTime.set(now); 2231 haveNewCpuStats = true; 2232 mProcessCpuTracker.update(); 2233 //Slog.i(TAG, mProcessCpu.printCurrentState()); 2234 //Slog.i(TAG, "Total CPU usage: " 2235 // + mProcessCpu.getTotalCpuPercent() + "%"); 2236 2237 // Slog the cpu usage if the property is set. 2238 if ("true".equals(SystemProperties.get("events.cpu"))) { 2239 int user = mProcessCpuTracker.getLastUserTime(); 2240 int system = mProcessCpuTracker.getLastSystemTime(); 2241 int iowait = mProcessCpuTracker.getLastIoWaitTime(); 2242 int irq = mProcessCpuTracker.getLastIrqTime(); 2243 int softIrq = mProcessCpuTracker.getLastSoftIrqTime(); 2244 int idle = mProcessCpuTracker.getLastIdleTime(); 2245 2246 int total = user + system + iowait + irq + softIrq + idle; 2247 if (total == 0) total = 1; 2248 2249 EventLog.writeEvent(EventLogTags.CPU, 2250 ((user+system+iowait+irq+softIrq) * 100) / total, 2251 (user * 100) / total, 2252 (system * 100) / total, 2253 (iowait * 100) / total, 2254 (irq * 100) / total, 2255 (softIrq * 100) / total); 2256 } 2257 } 2258 2259 long[] cpuSpeedTimes = mProcessCpuTracker.getLastCpuSpeedTimes(); 2260 final BatteryStatsImpl bstats = mBatteryStatsService.getActiveStatistics(); 2261 synchronized(bstats) { 2262 synchronized(mPidsSelfLocked) { 2263 if (haveNewCpuStats) { 2264 if (mOnBattery) { 2265 int perc = bstats.startAddingCpuLocked(); 2266 int totalUTime = 0; 2267 int totalSTime = 0; 2268 final int N = mProcessCpuTracker.countStats(); 2269 for (int i=0; i<N; i++) { 2270 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 2271 if (!st.working) { 2272 continue; 2273 } 2274 ProcessRecord pr = mPidsSelfLocked.get(st.pid); 2275 int otherUTime = (st.rel_utime*perc)/100; 2276 int otherSTime = (st.rel_stime*perc)/100; 2277 totalUTime += otherUTime; 2278 totalSTime += otherSTime; 2279 if (pr != null) { 2280 BatteryStatsImpl.Uid.Proc ps = pr.curProcBatteryStats; 2281 if (ps == null || !ps.isActive()) { 2282 pr.curProcBatteryStats = ps = bstats.getProcessStatsLocked( 2283 pr.info.uid, pr.processName); 2284 } 2285 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2286 st.rel_stime-otherSTime); 2287 ps.addSpeedStepTimes(cpuSpeedTimes); 2288 pr.curCpuTime += (st.rel_utime+st.rel_stime) * 10; 2289 } else { 2290 BatteryStatsImpl.Uid.Proc ps = st.batteryStats; 2291 if (ps == null || !ps.isActive()) { 2292 st.batteryStats = ps = bstats.getProcessStatsLocked( 2293 bstats.mapUid(st.uid), st.name); 2294 } 2295 ps.addCpuTimeLocked(st.rel_utime-otherUTime, 2296 st.rel_stime-otherSTime); 2297 ps.addSpeedStepTimes(cpuSpeedTimes); 2298 } 2299 } 2300 bstats.finishAddingCpuLocked(perc, totalUTime, 2301 totalSTime, cpuSpeedTimes); 2302 } 2303 } 2304 } 2305 2306 if (mLastWriteTime < (now-BATTERY_STATS_TIME)) { 2307 mLastWriteTime = now; 2308 mBatteryStatsService.getActiveStatistics().writeAsyncLocked(); 2309 } 2310 } 2311 } 2312 } 2313 2314 @Override 2315 public void batteryNeedsCpuUpdate() { 2316 updateCpuStatsNow(); 2317 } 2318 2319 @Override 2320 public void batteryPowerChanged(boolean onBattery) { 2321 // When plugging in, update the CPU stats first before changing 2322 // the plug state. 2323 updateCpuStatsNow(); 2324 synchronized (this) { 2325 synchronized(mPidsSelfLocked) { 2326 mOnBattery = DEBUG_POWER ? true : onBattery; 2327 } 2328 } 2329 } 2330 2331 /** 2332 * Initialize the application bind args. These are passed to each 2333 * process when the bindApplication() IPC is sent to the process. They're 2334 * lazily setup to make sure the services are running when they're asked for. 2335 */ 2336 private HashMap<String, IBinder> getCommonServicesLocked() { 2337 if (mAppBindArgs == null) { 2338 mAppBindArgs = new HashMap<String, IBinder>(); 2339 2340 // Setup the application init args 2341 mAppBindArgs.put("package", ServiceManager.getService("package")); 2342 mAppBindArgs.put("window", ServiceManager.getService("window")); 2343 mAppBindArgs.put(Context.ALARM_SERVICE, 2344 ServiceManager.getService(Context.ALARM_SERVICE)); 2345 } 2346 return mAppBindArgs; 2347 } 2348 2349 final void setFocusedActivityLocked(ActivityRecord r) { 2350 if (mFocusedActivity != r) { 2351 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedActivityLocked: r=" + r); 2352 mFocusedActivity = r; 2353 if (r.task != null && r.task.voiceInteractor != null) { 2354 startRunningVoiceLocked(); 2355 } else { 2356 finishRunningVoiceLocked(); 2357 } 2358 mStackSupervisor.setFocusedStack(r); 2359 if (r != null) { 2360 mWindowManager.setFocusedApp(r.appToken, true); 2361 } 2362 applyUpdateLockStateLocked(r); 2363 } 2364 } 2365 2366 final void clearFocusedActivity(ActivityRecord r) { 2367 if (mFocusedActivity == r) { 2368 mFocusedActivity = null; 2369 } 2370 } 2371 2372 @Override 2373 public void setFocusedStack(int stackId) { 2374 if (DEBUG_FOCUS) Slog.d(TAG, "setFocusedStack: stackId=" + stackId); 2375 synchronized (ActivityManagerService.this) { 2376 ActivityStack stack = mStackSupervisor.getStack(stackId); 2377 if (stack != null) { 2378 ActivityRecord r = stack.topRunningActivityLocked(null); 2379 if (r != null) { 2380 setFocusedActivityLocked(r); 2381 } 2382 } 2383 } 2384 } 2385 2386 @Override 2387 public void notifyActivityDrawn(IBinder token) { 2388 if (DEBUG_VISBILITY) Slog.d(TAG, "notifyActivityDrawn: token=" + token); 2389 synchronized (this) { 2390 ActivityRecord r= mStackSupervisor.isInAnyStackLocked(token); 2391 if (r != null) { 2392 r.task.stack.notifyActivityDrawnLocked(r); 2393 } 2394 } 2395 } 2396 2397 final void applyUpdateLockStateLocked(ActivityRecord r) { 2398 // Modifications to the UpdateLock state are done on our handler, outside 2399 // the activity manager's locks. The new state is determined based on the 2400 // state *now* of the relevant activity record. The object is passed to 2401 // the handler solely for logging detail, not to be consulted/modified. 2402 final boolean nextState = r != null && r.immersive; 2403 mHandler.sendMessage( 2404 mHandler.obtainMessage(IMMERSIVE_MODE_LOCK_MSG, (nextState) ? 1 : 0, 0, r)); 2405 } 2406 2407 final void showAskCompatModeDialogLocked(ActivityRecord r) { 2408 Message msg = Message.obtain(); 2409 msg.what = SHOW_COMPAT_MODE_DIALOG_MSG; 2410 msg.obj = r.task.askedCompatMode ? null : r; 2411 mHandler.sendMessage(msg); 2412 } 2413 2414 private final int updateLruProcessInternalLocked(ProcessRecord app, long now, int index, 2415 String what, Object obj, ProcessRecord srcApp) { 2416 app.lastActivityTime = now; 2417 2418 if (app.activities.size() > 0) { 2419 // Don't want to touch dependent processes that are hosting activities. 2420 return index; 2421 } 2422 2423 int lrui = mLruProcesses.lastIndexOf(app); 2424 if (lrui < 0) { 2425 Slog.wtf(TAG, "Adding dependent process " + app + " not on LRU list: " 2426 + what + " " + obj + " from " + srcApp); 2427 return index; 2428 } 2429 2430 if (lrui >= index) { 2431 // Don't want to cause this to move dependent processes *back* in the 2432 // list as if they were less frequently used. 2433 return index; 2434 } 2435 2436 if (lrui >= mLruProcessActivityStart) { 2437 // Don't want to touch dependent processes that are hosting activities. 2438 return index; 2439 } 2440 2441 mLruProcesses.remove(lrui); 2442 if (index > 0) { 2443 index--; 2444 } 2445 if (DEBUG_LRU) Slog.d(TAG, "Moving dep from " + lrui + " to " + index 2446 + " in LRU list: " + app); 2447 mLruProcesses.add(index, app); 2448 return index; 2449 } 2450 2451 final void removeLruProcessLocked(ProcessRecord app) { 2452 int lrui = mLruProcesses.lastIndexOf(app); 2453 if (lrui >= 0) { 2454 if (lrui <= mLruProcessActivityStart) { 2455 mLruProcessActivityStart--; 2456 } 2457 if (lrui <= mLruProcessServiceStart) { 2458 mLruProcessServiceStart--; 2459 } 2460 mLruProcesses.remove(lrui); 2461 } 2462 } 2463 2464 final void updateLruProcessLocked(ProcessRecord app, boolean activityChange, 2465 ProcessRecord client) { 2466 final boolean hasActivity = app.activities.size() > 0 || app.hasClientActivities 2467 || app.treatLikeActivity; 2468 final boolean hasService = false; // not impl yet. app.services.size() > 0; 2469 if (!activityChange && hasActivity) { 2470 // The process has activities, so we are only allowing activity-based adjustments 2471 // to move it. It should be kept in the front of the list with other 2472 // processes that have activities, and we don't want those to change their 2473 // order except due to activity operations. 2474 return; 2475 } 2476 2477 mLruSeq++; 2478 final long now = SystemClock.uptimeMillis(); 2479 app.lastActivityTime = now; 2480 2481 // First a quick reject: if the app is already at the position we will 2482 // put it, then there is nothing to do. 2483 if (hasActivity) { 2484 final int N = mLruProcesses.size(); 2485 if (N > 0 && mLruProcesses.get(N-1) == app) { 2486 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top activity: " + app); 2487 return; 2488 } 2489 } else { 2490 if (mLruProcessServiceStart > 0 2491 && mLruProcesses.get(mLruProcessServiceStart-1) == app) { 2492 if (DEBUG_LRU) Slog.d(TAG, "Not moving, already top other: " + app); 2493 return; 2494 } 2495 } 2496 2497 int lrui = mLruProcesses.lastIndexOf(app); 2498 2499 if (app.persistent && lrui >= 0) { 2500 // We don't care about the position of persistent processes, as long as 2501 // they are in the list. 2502 if (DEBUG_LRU) Slog.d(TAG, "Not moving, persistent: " + app); 2503 return; 2504 } 2505 2506 /* In progress: compute new position first, so we can avoid doing work 2507 if the process is not actually going to move. Not yet working. 2508 int addIndex; 2509 int nextIndex; 2510 boolean inActivity = false, inService = false; 2511 if (hasActivity) { 2512 // Process has activities, put it at the very tipsy-top. 2513 addIndex = mLruProcesses.size(); 2514 nextIndex = mLruProcessServiceStart; 2515 inActivity = true; 2516 } else if (hasService) { 2517 // Process has services, put it at the top of the service list. 2518 addIndex = mLruProcessActivityStart; 2519 nextIndex = mLruProcessServiceStart; 2520 inActivity = true; 2521 inService = true; 2522 } else { 2523 // Process not otherwise of interest, it goes to the top of the non-service area. 2524 addIndex = mLruProcessServiceStart; 2525 if (client != null) { 2526 int clientIndex = mLruProcesses.lastIndexOf(client); 2527 if (clientIndex < 0) Slog.d(TAG, "Unknown client " + client + " when updating " 2528 + app); 2529 if (clientIndex >= 0 && addIndex > clientIndex) { 2530 addIndex = clientIndex; 2531 } 2532 } 2533 nextIndex = addIndex > 0 ? addIndex-1 : addIndex; 2534 } 2535 2536 Slog.d(TAG, "Update LRU at " + lrui + " to " + addIndex + " (act=" 2537 + mLruProcessActivityStart + "): " + app); 2538 */ 2539 2540 if (lrui >= 0) { 2541 if (lrui < mLruProcessActivityStart) { 2542 mLruProcessActivityStart--; 2543 } 2544 if (lrui < mLruProcessServiceStart) { 2545 mLruProcessServiceStart--; 2546 } 2547 /* 2548 if (addIndex > lrui) { 2549 addIndex--; 2550 } 2551 if (nextIndex > lrui) { 2552 nextIndex--; 2553 } 2554 */ 2555 mLruProcesses.remove(lrui); 2556 } 2557 2558 /* 2559 mLruProcesses.add(addIndex, app); 2560 if (inActivity) { 2561 mLruProcessActivityStart++; 2562 } 2563 if (inService) { 2564 mLruProcessActivityStart++; 2565 } 2566 */ 2567 2568 int nextIndex; 2569 if (hasActivity) { 2570 final int N = mLruProcesses.size(); 2571 if (app.activities.size() == 0 && mLruProcessActivityStart < (N-1)) { 2572 // Process doesn't have activities, but has clients with 2573 // activities... move it up, but one below the top (the top 2574 // should always have a real activity). 2575 if (DEBUG_LRU) Slog.d(TAG, "Adding to second-top of LRU activity list: " + app); 2576 mLruProcesses.add(N-1, app); 2577 // To keep it from spamming the LRU list (by making a bunch of clients), 2578 // we will push down any other entries owned by the app. 2579 final int uid = app.info.uid; 2580 for (int i=N-2; i>mLruProcessActivityStart; i--) { 2581 ProcessRecord subProc = mLruProcesses.get(i); 2582 if (subProc.info.uid == uid) { 2583 // We want to push this one down the list. If the process after 2584 // it is for the same uid, however, don't do so, because we don't 2585 // want them internally to be re-ordered. 2586 if (mLruProcesses.get(i-1).info.uid != uid) { 2587 if (DEBUG_LRU) Slog.d(TAG, "Pushing uid " + uid + " swapping at " + i 2588 + ": " + mLruProcesses.get(i) + " : " + mLruProcesses.get(i-1)); 2589 ProcessRecord tmp = mLruProcesses.get(i); 2590 mLruProcesses.set(i, mLruProcesses.get(i-1)); 2591 mLruProcesses.set(i-1, tmp); 2592 i--; 2593 } 2594 } else { 2595 // A gap, we can stop here. 2596 break; 2597 } 2598 } 2599 } else { 2600 // Process has activities, put it at the very tipsy-top. 2601 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU activity list: " + app); 2602 mLruProcesses.add(app); 2603 } 2604 nextIndex = mLruProcessServiceStart; 2605 } else if (hasService) { 2606 // Process has services, put it at the top of the service list. 2607 if (DEBUG_LRU) Slog.d(TAG, "Adding to top of LRU service list: " + app); 2608 mLruProcesses.add(mLruProcessActivityStart, app); 2609 nextIndex = mLruProcessServiceStart; 2610 mLruProcessActivityStart++; 2611 } else { 2612 // Process not otherwise of interest, it goes to the top of the non-service area. 2613 int index = mLruProcessServiceStart; 2614 if (client != null) { 2615 // If there is a client, don't allow the process to be moved up higher 2616 // in the list than that client. 2617 int clientIndex = mLruProcesses.lastIndexOf(client); 2618 if (DEBUG_LRU && clientIndex < 0) Slog.d(TAG, "Unknown client " + client 2619 + " when updating " + app); 2620 if (clientIndex <= lrui) { 2621 // Don't allow the client index restriction to push it down farther in the 2622 // list than it already is. 2623 clientIndex = lrui; 2624 } 2625 if (clientIndex >= 0 && index > clientIndex) { 2626 index = clientIndex; 2627 } 2628 } 2629 if (DEBUG_LRU) Slog.d(TAG, "Adding at " + index + " of LRU list: " + app); 2630 mLruProcesses.add(index, app); 2631 nextIndex = index-1; 2632 mLruProcessActivityStart++; 2633 mLruProcessServiceStart++; 2634 } 2635 2636 // If the app is currently using a content provider or service, 2637 // bump those processes as well. 2638 for (int j=app.connections.size()-1; j>=0; j--) { 2639 ConnectionRecord cr = app.connections.valueAt(j); 2640 if (cr.binding != null && !cr.serviceDead && cr.binding.service != null 2641 && cr.binding.service.app != null 2642 && cr.binding.service.app.lruSeq != mLruSeq 2643 && !cr.binding.service.app.persistent) { 2644 nextIndex = updateLruProcessInternalLocked(cr.binding.service.app, now, nextIndex, 2645 "service connection", cr, app); 2646 } 2647 } 2648 for (int j=app.conProviders.size()-1; j>=0; j--) { 2649 ContentProviderRecord cpr = app.conProviders.get(j).provider; 2650 if (cpr.proc != null && cpr.proc.lruSeq != mLruSeq && !cpr.proc.persistent) { 2651 nextIndex = updateLruProcessInternalLocked(cpr.proc, now, nextIndex, 2652 "provider reference", cpr, app); 2653 } 2654 } 2655 } 2656 2657 final ProcessRecord getProcessRecordLocked(String processName, int uid, boolean keepIfLarge) { 2658 if (uid == Process.SYSTEM_UID) { 2659 // The system gets to run in any process. If there are multiple 2660 // processes with the same uid, just pick the first (this 2661 // should never happen). 2662 SparseArray<ProcessRecord> procs = mProcessNames.getMap().get(processName); 2663 if (procs == null) return null; 2664 final int N = procs.size(); 2665 for (int i = 0; i < N; i++) { 2666 if (UserHandle.isSameUser(procs.keyAt(i), uid)) return procs.valueAt(i); 2667 } 2668 } 2669 ProcessRecord proc = mProcessNames.get(processName, uid); 2670 if (false && proc != null && !keepIfLarge 2671 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY 2672 && proc.lastCachedPss >= 4000) { 2673 // Turn this condition on to cause killing to happen regularly, for testing. 2674 if (proc.baseProcessTracker != null) { 2675 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2676 } 2677 killUnneededProcessLocked(proc, Long.toString(proc.lastCachedPss) 2678 + "k from cached"); 2679 } else if (proc != null && !keepIfLarge 2680 && mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 2681 && proc.setProcState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 2682 if (DEBUG_PSS) Slog.d(TAG, "May not keep " + proc + ": pss=" + proc.lastCachedPss); 2683 if (proc.lastCachedPss >= mProcessList.getCachedRestoreThresholdKb()) { 2684 if (proc.baseProcessTracker != null) { 2685 proc.baseProcessTracker.reportCachedKill(proc.pkgList, proc.lastCachedPss); 2686 } 2687 killUnneededProcessLocked(proc, Long.toString(proc.lastCachedPss) 2688 + "k from cached"); 2689 } 2690 } 2691 return proc; 2692 } 2693 2694 void ensurePackageDexOpt(String packageName) { 2695 IPackageManager pm = AppGlobals.getPackageManager(); 2696 try { 2697 if (pm.performDexOpt(packageName)) { 2698 mDidDexOpt = true; 2699 } 2700 } catch (RemoteException e) { 2701 } 2702 } 2703 2704 boolean isNextTransitionForward() { 2705 int transit = mWindowManager.getPendingAppTransition(); 2706 return transit == AppTransition.TRANSIT_ACTIVITY_OPEN 2707 || transit == AppTransition.TRANSIT_TASK_OPEN 2708 || transit == AppTransition.TRANSIT_TASK_TO_FRONT; 2709 } 2710 2711 final ProcessRecord startProcessLocked(String processName, 2712 ApplicationInfo info, boolean knownToBeDead, int intentFlags, 2713 String hostingType, ComponentName hostingName, boolean allowWhileBooting, 2714 boolean isolated, boolean keepIfLarge) { 2715 ProcessRecord app; 2716 if (!isolated) { 2717 app = getProcessRecordLocked(processName, info.uid, keepIfLarge); 2718 } else { 2719 // If this is an isolated process, it can't re-use an existing process. 2720 app = null; 2721 } 2722 // We don't have to do anything more if: 2723 // (1) There is an existing application record; and 2724 // (2) The caller doesn't think it is dead, OR there is no thread 2725 // object attached to it so we know it couldn't have crashed; and 2726 // (3) There is a pid assigned to it, so it is either starting or 2727 // already running. 2728 if (DEBUG_PROCESSES) Slog.v(TAG, "startProcess: name=" + processName 2729 + " app=" + app + " knownToBeDead=" + knownToBeDead 2730 + " thread=" + (app != null ? app.thread : null) 2731 + " pid=" + (app != null ? app.pid : -1)); 2732 if (app != null && app.pid > 0) { 2733 if (!knownToBeDead || app.thread == null) { 2734 // We already have the app running, or are waiting for it to 2735 // come up (we have a pid but not yet its thread), so keep it. 2736 if (DEBUG_PROCESSES) Slog.v(TAG, "App already running: " + app); 2737 // If this is a new package in the process, add the package to the list 2738 app.addPackage(info.packageName, mProcessStats); 2739 return app; 2740 } 2741 2742 // An application record is attached to a previous process, 2743 // clean it up now. 2744 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, "App died: " + app); 2745 handleAppDiedLocked(app, true, true); 2746 } 2747 2748 String hostingNameStr = hostingName != null 2749 ? hostingName.flattenToShortString() : null; 2750 2751 if (!isolated) { 2752 if ((intentFlags&Intent.FLAG_FROM_BACKGROUND) != 0) { 2753 // If we are in the background, then check to see if this process 2754 // is bad. If so, we will just silently fail. 2755 if (mBadProcesses.get(info.processName, info.uid) != null) { 2756 if (DEBUG_PROCESSES) Slog.v(TAG, "Bad process: " + info.uid 2757 + "/" + info.processName); 2758 return null; 2759 } 2760 } else { 2761 // When the user is explicitly starting a process, then clear its 2762 // crash count so that we won't make it bad until they see at 2763 // least one crash dialog again, and make the process good again 2764 // if it had been bad. 2765 if (DEBUG_PROCESSES) Slog.v(TAG, "Clearing bad process: " + info.uid 2766 + "/" + info.processName); 2767 mProcessCrashTimes.remove(info.processName, info.uid); 2768 if (mBadProcesses.get(info.processName, info.uid) != null) { 2769 EventLog.writeEvent(EventLogTags.AM_PROC_GOOD, 2770 UserHandle.getUserId(info.uid), info.uid, 2771 info.processName); 2772 mBadProcesses.remove(info.processName, info.uid); 2773 if (app != null) { 2774 app.bad = false; 2775 } 2776 } 2777 } 2778 } 2779 2780 if (app == null) { 2781 app = newProcessRecordLocked(info, processName, isolated); 2782 if (app == null) { 2783 Slog.w(TAG, "Failed making new process record for " 2784 + processName + "/" + info.uid + " isolated=" + isolated); 2785 return null; 2786 } 2787 mProcessNames.put(processName, app.uid, app); 2788 if (isolated) { 2789 mIsolatedProcesses.put(app.uid, app); 2790 } 2791 } else { 2792 // If this is a new package in the process, add the package to the list 2793 app.addPackage(info.packageName, mProcessStats); 2794 } 2795 2796 // If the system is not ready yet, then hold off on starting this 2797 // process until it is. 2798 if (!mProcessesReady 2799 && !isAllowedWhileBooting(info) 2800 && !allowWhileBooting) { 2801 if (!mProcessesOnHold.contains(app)) { 2802 mProcessesOnHold.add(app); 2803 } 2804 if (DEBUG_PROCESSES) Slog.v(TAG, "System not ready, putting on hold: " + app); 2805 return app; 2806 } 2807 2808 startProcessLocked(app, hostingType, hostingNameStr); 2809 return (app.pid != 0) ? app : null; 2810 } 2811 2812 boolean isAllowedWhileBooting(ApplicationInfo ai) { 2813 return (ai.flags&ApplicationInfo.FLAG_PERSISTENT) != 0; 2814 } 2815 2816 private final void startProcessLocked(ProcessRecord app, 2817 String hostingType, String hostingNameStr) { 2818 if (app.pid > 0 && app.pid != MY_PID) { 2819 synchronized (mPidsSelfLocked) { 2820 mPidsSelfLocked.remove(app.pid); 2821 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 2822 } 2823 app.setPid(0); 2824 } 2825 2826 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 2827 "startProcessLocked removing on hold: " + app); 2828 mProcessesOnHold.remove(app); 2829 2830 updateCpuStats(); 2831 2832 try { 2833 int uid = app.uid; 2834 2835 int[] gids = null; 2836 int mountExternal = Zygote.MOUNT_EXTERNAL_NONE; 2837 if (!app.isolated) { 2838 int[] permGids = null; 2839 try { 2840 final PackageManager pm = mContext.getPackageManager(); 2841 permGids = pm.getPackageGids(app.info.packageName); 2842 2843 if (Environment.isExternalStorageEmulated()) { 2844 if (pm.checkPermission( 2845 android.Manifest.permission.ACCESS_ALL_EXTERNAL_STORAGE, 2846 app.info.packageName) == PERMISSION_GRANTED) { 2847 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER_ALL; 2848 } else { 2849 mountExternal = Zygote.MOUNT_EXTERNAL_MULTIUSER; 2850 } 2851 } 2852 } catch (PackageManager.NameNotFoundException e) { 2853 Slog.w(TAG, "Unable to retrieve gids", e); 2854 } 2855 2856 /* 2857 * Add shared application GID so applications can share some 2858 * resources like shared libraries 2859 */ 2860 if (permGids == null) { 2861 gids = new int[1]; 2862 } else { 2863 gids = new int[permGids.length + 1]; 2864 System.arraycopy(permGids, 0, gids, 1, permGids.length); 2865 } 2866 gids[0] = UserHandle.getSharedAppGid(UserHandle.getAppId(uid)); 2867 } 2868 if (mFactoryTest != FactoryTest.FACTORY_TEST_OFF) { 2869 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 2870 && mTopComponent != null 2871 && app.processName.equals(mTopComponent.getPackageName())) { 2872 uid = 0; 2873 } 2874 if (mFactoryTest == FactoryTest.FACTORY_TEST_HIGH_LEVEL 2875 && (app.info.flags&ApplicationInfo.FLAG_FACTORY_TEST) != 0) { 2876 uid = 0; 2877 } 2878 } 2879 int debugFlags = 0; 2880 if ((app.info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0) { 2881 debugFlags |= Zygote.DEBUG_ENABLE_DEBUGGER; 2882 // Also turn on CheckJNI for debuggable apps. It's quite 2883 // awkward to turn on otherwise. 2884 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 2885 } 2886 // Run the app in safe mode if its manifest requests so or the 2887 // system is booted in safe mode. 2888 if ((app.info.flags & ApplicationInfo.FLAG_VM_SAFE_MODE) != 0 || 2889 mSafeMode == true) { 2890 debugFlags |= Zygote.DEBUG_ENABLE_SAFEMODE; 2891 } 2892 if ("1".equals(SystemProperties.get("debug.checkjni"))) { 2893 debugFlags |= Zygote.DEBUG_ENABLE_CHECKJNI; 2894 } 2895 if ("1".equals(SystemProperties.get("debug.jni.logging"))) { 2896 debugFlags |= Zygote.DEBUG_ENABLE_JNI_LOGGING; 2897 } 2898 if ("1".equals(SystemProperties.get("debug.assert"))) { 2899 debugFlags |= Zygote.DEBUG_ENABLE_ASSERT; 2900 } 2901 2902 String requiredAbi = app.info.requiredCpuAbi; 2903 if (requiredAbi == null) { 2904 requiredAbi = Build.SUPPORTED_ABIS[0]; 2905 } 2906 2907 // Start the process. It will either succeed and return a result containing 2908 // the PID of the new process, or else throw a RuntimeException. 2909 Process.ProcessStartResult startResult = Process.start("android.app.ActivityThread", 2910 app.processName, uid, uid, gids, debugFlags, mountExternal, 2911 app.info.targetSdkVersion, app.info.seinfo, requiredAbi, null); 2912 2913 BatteryStatsImpl bs = mBatteryStatsService.getActiveStatistics(); 2914 synchronized (bs) { 2915 if (bs.isOnBattery()) { 2916 bs.getProcessStatsLocked(app.uid, app.processName).incStartsLocked(); 2917 } 2918 } 2919 2920 EventLog.writeEvent(EventLogTags.AM_PROC_START, 2921 UserHandle.getUserId(uid), startResult.pid, uid, 2922 app.processName, hostingType, 2923 hostingNameStr != null ? hostingNameStr : ""); 2924 2925 if (app.persistent) { 2926 Watchdog.getInstance().processStarted(app.processName, startResult.pid); 2927 } 2928 2929 StringBuilder buf = mStringBuilder; 2930 buf.setLength(0); 2931 buf.append("Start proc "); 2932 buf.append(app.processName); 2933 buf.append(" for "); 2934 buf.append(hostingType); 2935 if (hostingNameStr != null) { 2936 buf.append(" "); 2937 buf.append(hostingNameStr); 2938 } 2939 buf.append(": pid="); 2940 buf.append(startResult.pid); 2941 buf.append(" uid="); 2942 buf.append(uid); 2943 buf.append(" gids={"); 2944 if (gids != null) { 2945 for (int gi=0; gi<gids.length; gi++) { 2946 if (gi != 0) buf.append(", "); 2947 buf.append(gids[gi]); 2948 2949 } 2950 } 2951 buf.append("}"); 2952 Slog.i(TAG, buf.toString()); 2953 app.setPid(startResult.pid); 2954 app.usingWrapper = startResult.usingWrapper; 2955 app.removed = false; 2956 synchronized (mPidsSelfLocked) { 2957 this.mPidsSelfLocked.put(startResult.pid, app); 2958 Message msg = mHandler.obtainMessage(PROC_START_TIMEOUT_MSG); 2959 msg.obj = app; 2960 mHandler.sendMessageDelayed(msg, startResult.usingWrapper 2961 ? PROC_START_TIMEOUT_WITH_WRAPPER : PROC_START_TIMEOUT); 2962 } 2963 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_PROC_START, 2964 app.processName, app.info.uid); 2965 if (app.isolated) { 2966 mBatteryStatsService.addIsolatedUid(app.uid, app.info.uid); 2967 } 2968 } catch (RuntimeException e) { 2969 // XXX do better error recovery. 2970 app.setPid(0); 2971 Slog.e(TAG, "Failure starting process " + app.processName, e); 2972 } 2973 } 2974 2975 void updateUsageStats(ActivityRecord component, boolean resumed) { 2976 if (DEBUG_SWITCH) Slog.d(TAG, "updateUsageStats: comp=" + component + "res=" + resumed); 2977 final BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 2978 if (resumed) { 2979 mUsageStatsService.noteResumeComponent(component.realActivity); 2980 synchronized (stats) { 2981 stats.noteActivityResumedLocked(component.app.uid); 2982 } 2983 } else { 2984 mUsageStatsService.notePauseComponent(component.realActivity); 2985 synchronized (stats) { 2986 stats.noteActivityPausedLocked(component.app.uid); 2987 } 2988 } 2989 } 2990 2991 Intent getHomeIntent() { 2992 Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null); 2993 intent.setComponent(mTopComponent); 2994 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 2995 intent.addCategory(Intent.CATEGORY_HOME); 2996 } 2997 return intent; 2998 } 2999 3000 boolean startHomeActivityLocked(int userId) { 3001 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL 3002 && mTopAction == null) { 3003 // We are running in factory test mode, but unable to find 3004 // the factory test app, so just sit around displaying the 3005 // error message and don't try to start anything. 3006 return false; 3007 } 3008 Intent intent = getHomeIntent(); 3009 ActivityInfo aInfo = 3010 resolveActivityInfo(intent, STOCK_PM_FLAGS, userId); 3011 if (aInfo != null) { 3012 intent.setComponent(new ComponentName( 3013 aInfo.applicationInfo.packageName, aInfo.name)); 3014 // Don't do this if the home app is currently being 3015 // instrumented. 3016 aInfo = new ActivityInfo(aInfo); 3017 aInfo.applicationInfo = getAppInfoForUser(aInfo.applicationInfo, userId); 3018 ProcessRecord app = getProcessRecordLocked(aInfo.processName, 3019 aInfo.applicationInfo.uid, true); 3020 if (app == null || app.instrumentationClass == null) { 3021 intent.setFlags(intent.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK); 3022 mStackSupervisor.startHomeActivity(intent, aInfo); 3023 } 3024 } 3025 3026 return true; 3027 } 3028 3029 private ActivityInfo resolveActivityInfo(Intent intent, int flags, int userId) { 3030 ActivityInfo ai = null; 3031 ComponentName comp = intent.getComponent(); 3032 try { 3033 if (comp != null) { 3034 ai = AppGlobals.getPackageManager().getActivityInfo(comp, flags, userId); 3035 } else { 3036 ResolveInfo info = AppGlobals.getPackageManager().resolveIntent( 3037 intent, 3038 intent.resolveTypeIfNeeded(mContext.getContentResolver()), 3039 flags, userId); 3040 3041 if (info != null) { 3042 ai = info.activityInfo; 3043 } 3044 } 3045 } catch (RemoteException e) { 3046 // ignore 3047 } 3048 3049 return ai; 3050 } 3051 3052 /** 3053 * Starts the "new version setup screen" if appropriate. 3054 */ 3055 void startSetupActivityLocked() { 3056 // Only do this once per boot. 3057 if (mCheckedForSetup) { 3058 return; 3059 } 3060 3061 // We will show this screen if the current one is a different 3062 // version than the last one shown, and we are not running in 3063 // low-level factory test mode. 3064 final ContentResolver resolver = mContext.getContentResolver(); 3065 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL && 3066 Settings.Global.getInt(resolver, 3067 Settings.Global.DEVICE_PROVISIONED, 0) != 0) { 3068 mCheckedForSetup = true; 3069 3070 // See if we should be showing the platform update setup UI. 3071 Intent intent = new Intent(Intent.ACTION_UPGRADE_SETUP); 3072 List<ResolveInfo> ris = mContext.getPackageManager() 3073 .queryIntentActivities(intent, PackageManager.GET_META_DATA); 3074 3075 // We don't allow third party apps to replace this. 3076 ResolveInfo ri = null; 3077 for (int i=0; ris != null && i<ris.size(); i++) { 3078 if ((ris.get(i).activityInfo.applicationInfo.flags 3079 & ApplicationInfo.FLAG_SYSTEM) != 0) { 3080 ri = ris.get(i); 3081 break; 3082 } 3083 } 3084 3085 if (ri != null) { 3086 String vers = ri.activityInfo.metaData != null 3087 ? ri.activityInfo.metaData.getString(Intent.METADATA_SETUP_VERSION) 3088 : null; 3089 if (vers == null && ri.activityInfo.applicationInfo.metaData != null) { 3090 vers = ri.activityInfo.applicationInfo.metaData.getString( 3091 Intent.METADATA_SETUP_VERSION); 3092 } 3093 String lastVers = Settings.Secure.getString( 3094 resolver, Settings.Secure.LAST_SETUP_SHOWN); 3095 if (vers != null && !vers.equals(lastVers)) { 3096 intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 3097 intent.setComponent(new ComponentName( 3098 ri.activityInfo.packageName, ri.activityInfo.name)); 3099 mStackSupervisor.startActivityLocked(null, intent, null, ri.activityInfo, 3100 null, null, null, null, 0, 0, 0, null, 0, null, false, null, null); 3101 } 3102 } 3103 } 3104 } 3105 3106 CompatibilityInfo compatibilityInfoForPackageLocked(ApplicationInfo ai) { 3107 return mCompatModePackages.compatibilityInfoForPackageLocked(ai); 3108 } 3109 3110 void enforceNotIsolatedCaller(String caller) { 3111 if (UserHandle.isIsolated(Binder.getCallingUid())) { 3112 throw new SecurityException("Isolated process not allowed to call " + caller); 3113 } 3114 } 3115 3116 @Override 3117 public int getFrontActivityScreenCompatMode() { 3118 enforceNotIsolatedCaller("getFrontActivityScreenCompatMode"); 3119 synchronized (this) { 3120 return mCompatModePackages.getFrontActivityScreenCompatModeLocked(); 3121 } 3122 } 3123 3124 @Override 3125 public void setFrontActivityScreenCompatMode(int mode) { 3126 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3127 "setFrontActivityScreenCompatMode"); 3128 synchronized (this) { 3129 mCompatModePackages.setFrontActivityScreenCompatModeLocked(mode); 3130 } 3131 } 3132 3133 @Override 3134 public int getPackageScreenCompatMode(String packageName) { 3135 enforceNotIsolatedCaller("getPackageScreenCompatMode"); 3136 synchronized (this) { 3137 return mCompatModePackages.getPackageScreenCompatModeLocked(packageName); 3138 } 3139 } 3140 3141 @Override 3142 public void setPackageScreenCompatMode(String packageName, int mode) { 3143 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3144 "setPackageScreenCompatMode"); 3145 synchronized (this) { 3146 mCompatModePackages.setPackageScreenCompatModeLocked(packageName, mode); 3147 } 3148 } 3149 3150 @Override 3151 public boolean getPackageAskScreenCompat(String packageName) { 3152 enforceNotIsolatedCaller("getPackageAskScreenCompat"); 3153 synchronized (this) { 3154 return mCompatModePackages.getPackageAskCompatModeLocked(packageName); 3155 } 3156 } 3157 3158 @Override 3159 public void setPackageAskScreenCompat(String packageName, boolean ask) { 3160 enforceCallingPermission(android.Manifest.permission.SET_SCREEN_COMPATIBILITY, 3161 "setPackageAskScreenCompat"); 3162 synchronized (this) { 3163 mCompatModePackages.setPackageAskCompatModeLocked(packageName, ask); 3164 } 3165 } 3166 3167 private void dispatchProcessesChanged() { 3168 int N; 3169 synchronized (this) { 3170 N = mPendingProcessChanges.size(); 3171 if (mActiveProcessChanges.length < N) { 3172 mActiveProcessChanges = new ProcessChangeItem[N]; 3173 } 3174 mPendingProcessChanges.toArray(mActiveProcessChanges); 3175 mAvailProcessChanges.addAll(mPendingProcessChanges); 3176 mPendingProcessChanges.clear(); 3177 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "*** Delivering " + N + " process changes"); 3178 } 3179 3180 int i = mProcessObservers.beginBroadcast(); 3181 while (i > 0) { 3182 i--; 3183 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3184 if (observer != null) { 3185 try { 3186 for (int j=0; j<N; j++) { 3187 ProcessChangeItem item = mActiveProcessChanges[j]; 3188 if ((item.changes&ProcessChangeItem.CHANGE_ACTIVITIES) != 0) { 3189 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "ACTIVITIES CHANGED pid=" 3190 + item.pid + " uid=" + item.uid + ": " 3191 + item.foregroundActivities); 3192 observer.onForegroundActivitiesChanged(item.pid, item.uid, 3193 item.foregroundActivities); 3194 } 3195 if ((item.changes&ProcessChangeItem.CHANGE_PROCESS_STATE) != 0) { 3196 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "PROCSTATE CHANGED pid=" 3197 + item.pid + " uid=" + item.uid + ": " + item.processState); 3198 observer.onProcessStateChanged(item.pid, item.uid, item.processState); 3199 } 3200 } 3201 } catch (RemoteException e) { 3202 } 3203 } 3204 } 3205 mProcessObservers.finishBroadcast(); 3206 } 3207 3208 private void dispatchProcessDied(int pid, int uid) { 3209 int i = mProcessObservers.beginBroadcast(); 3210 while (i > 0) { 3211 i--; 3212 final IProcessObserver observer = mProcessObservers.getBroadcastItem(i); 3213 if (observer != null) { 3214 try { 3215 observer.onProcessDied(pid, uid); 3216 } catch (RemoteException e) { 3217 } 3218 } 3219 } 3220 mProcessObservers.finishBroadcast(); 3221 } 3222 3223 final void doPendingActivityLaunchesLocked(boolean doResume) { 3224 final int N = mPendingActivityLaunches.size(); 3225 if (N <= 0) { 3226 return; 3227 } 3228 for (int i=0; i<N; i++) { 3229 PendingActivityLaunch pal = mPendingActivityLaunches.get(i); 3230 mStackSupervisor.startActivityUncheckedLocked(pal.r, pal.sourceRecord, null, null, pal.startFlags, 3231 doResume && i == (N-1), null); 3232 } 3233 mPendingActivityLaunches.clear(); 3234 } 3235 3236 @Override 3237 public final int startActivity(IApplicationThread caller, String callingPackage, 3238 Intent intent, String resolvedType, IBinder resultTo, 3239 String resultWho, int requestCode, int startFlags, 3240 String profileFile, ParcelFileDescriptor profileFd, Bundle options) { 3241 return startActivityAsUser(caller, callingPackage, intent, resolvedType, resultTo, 3242 resultWho, requestCode, 3243 startFlags, profileFile, profileFd, options, UserHandle.getCallingUserId()); 3244 } 3245 3246 @Override 3247 public final int startActivityAsUser(IApplicationThread caller, String callingPackage, 3248 Intent intent, String resolvedType, IBinder resultTo, 3249 String resultWho, int requestCode, int startFlags, 3250 String profileFile, ParcelFileDescriptor profileFd, Bundle options, int userId) { 3251 enforceNotIsolatedCaller("startActivity"); 3252 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3253 false, true, "startActivity", null); 3254 // TODO: Switch to user app stacks here. 3255 return mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 3256 null, null, resultTo, resultWho, requestCode, startFlags, profileFile, profileFd, 3257 null, null, options, userId, null); 3258 } 3259 3260 @Override 3261 public final WaitResult startActivityAndWait(IApplicationThread caller, String callingPackage, 3262 Intent intent, String resolvedType, IBinder resultTo, 3263 String resultWho, int requestCode, int startFlags, String profileFile, 3264 ParcelFileDescriptor profileFd, Bundle options, int userId) { 3265 enforceNotIsolatedCaller("startActivityAndWait"); 3266 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3267 false, true, "startActivityAndWait", null); 3268 WaitResult res = new WaitResult(); 3269 // TODO: Switch to user app stacks here. 3270 mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, resolvedType, 3271 null, null, resultTo, resultWho, requestCode, startFlags, profileFile, profileFd, 3272 res, null, options, UserHandle.getCallingUserId(), null); 3273 return res; 3274 } 3275 3276 @Override 3277 public final int startActivityWithConfig(IApplicationThread caller, String callingPackage, 3278 Intent intent, String resolvedType, IBinder resultTo, 3279 String resultWho, int requestCode, int startFlags, Configuration config, 3280 Bundle options, int userId) { 3281 enforceNotIsolatedCaller("startActivityWithConfig"); 3282 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3283 false, true, "startActivityWithConfig", null); 3284 // TODO: Switch to user app stacks here. 3285 int ret = mStackSupervisor.startActivityMayWait(caller, -1, callingPackage, intent, 3286 resolvedType, null, null, resultTo, resultWho, requestCode, startFlags, 3287 null, null, null, config, options, userId, null); 3288 return ret; 3289 } 3290 3291 @Override 3292 public int startActivityIntentSender(IApplicationThread caller, 3293 IntentSender intent, Intent fillInIntent, String resolvedType, 3294 IBinder resultTo, String resultWho, int requestCode, 3295 int flagsMask, int flagsValues, Bundle options) { 3296 enforceNotIsolatedCaller("startActivityIntentSender"); 3297 // Refuse possible leaked file descriptors 3298 if (fillInIntent != null && fillInIntent.hasFileDescriptors()) { 3299 throw new IllegalArgumentException("File descriptors passed in Intent"); 3300 } 3301 3302 IIntentSender sender = intent.getTarget(); 3303 if (!(sender instanceof PendingIntentRecord)) { 3304 throw new IllegalArgumentException("Bad PendingIntent object"); 3305 } 3306 3307 PendingIntentRecord pir = (PendingIntentRecord)sender; 3308 3309 synchronized (this) { 3310 // If this is coming from the currently resumed activity, it is 3311 // effectively saying that app switches are allowed at this point. 3312 final ActivityStack stack = getFocusedStack(); 3313 if (stack.mResumedActivity != null && 3314 stack.mResumedActivity.info.applicationInfo.uid == Binder.getCallingUid()) { 3315 mAppSwitchesAllowedTime = 0; 3316 } 3317 } 3318 int ret = pir.sendInner(0, fillInIntent, resolvedType, null, null, 3319 resultTo, resultWho, requestCode, flagsMask, flagsValues, options, null); 3320 return ret; 3321 } 3322 3323 @Override 3324 public int startVoiceActivity(String callingPackage, int callingPid, int callingUid, 3325 Intent intent, String resolvedType, IVoiceInteractionSession session, 3326 IVoiceInteractor interactor, int startFlags, String profileFile, 3327 ParcelFileDescriptor profileFd, Bundle options, int userId) { 3328 if (checkCallingPermission(Manifest.permission.BIND_VOICE_INTERACTION) 3329 != PackageManager.PERMISSION_GRANTED) { 3330 String msg = "Permission Denial: startVoiceActivity() from pid=" 3331 + Binder.getCallingPid() 3332 + ", uid=" + Binder.getCallingUid() 3333 + " requires " + android.Manifest.permission.BIND_VOICE_INTERACTION; 3334 Slog.w(TAG, msg); 3335 throw new SecurityException(msg); 3336 } 3337 if (session == null || interactor == null) { 3338 throw new NullPointerException("null session or interactor"); 3339 } 3340 userId = handleIncomingUser(callingPid, callingUid, userId, 3341 false, true, "startVoiceActivity", null); 3342 // TODO: Switch to user app stacks here. 3343 return mStackSupervisor.startActivityMayWait(null, callingUid, callingPackage, intent, 3344 resolvedType, session, interactor, null, null, 0, startFlags, 3345 profileFile, profileFd, null, null, options, userId, null); 3346 } 3347 3348 @Override 3349 public boolean startNextMatchingActivity(IBinder callingActivity, 3350 Intent intent, Bundle options) { 3351 // Refuse possible leaked file descriptors 3352 if (intent != null && intent.hasFileDescriptors() == true) { 3353 throw new IllegalArgumentException("File descriptors passed in Intent"); 3354 } 3355 3356 synchronized (this) { 3357 final ActivityRecord r = ActivityRecord.isInStackLocked(callingActivity); 3358 if (r == null) { 3359 ActivityOptions.abort(options); 3360 return false; 3361 } 3362 if (r.app == null || r.app.thread == null) { 3363 // The caller is not running... d'oh! 3364 ActivityOptions.abort(options); 3365 return false; 3366 } 3367 intent = new Intent(intent); 3368 // The caller is not allowed to change the data. 3369 intent.setDataAndType(r.intent.getData(), r.intent.getType()); 3370 // And we are resetting to find the next component... 3371 intent.setComponent(null); 3372 3373 final boolean debug = ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0); 3374 3375 ActivityInfo aInfo = null; 3376 try { 3377 List<ResolveInfo> resolves = 3378 AppGlobals.getPackageManager().queryIntentActivities( 3379 intent, r.resolvedType, 3380 PackageManager.MATCH_DEFAULT_ONLY | STOCK_PM_FLAGS, 3381 UserHandle.getCallingUserId()); 3382 3383 // Look for the original activity in the list... 3384 final int N = resolves != null ? resolves.size() : 0; 3385 for (int i=0; i<N; i++) { 3386 ResolveInfo rInfo = resolves.get(i); 3387 if (rInfo.activityInfo.packageName.equals(r.packageName) 3388 && rInfo.activityInfo.name.equals(r.info.name)) { 3389 // We found the current one... the next matching is 3390 // after it. 3391 i++; 3392 if (i<N) { 3393 aInfo = resolves.get(i).activityInfo; 3394 } 3395 if (debug) { 3396 Slog.v(TAG, "Next matching activity: found current " + r.packageName 3397 + "/" + r.info.name); 3398 Slog.v(TAG, "Next matching activity: next is " + aInfo.packageName 3399 + "/" + aInfo.name); 3400 } 3401 break; 3402 } 3403 } 3404 } catch (RemoteException e) { 3405 } 3406 3407 if (aInfo == null) { 3408 // Nobody who is next! 3409 ActivityOptions.abort(options); 3410 if (debug) Slog.d(TAG, "Next matching activity: nothing found"); 3411 return false; 3412 } 3413 3414 intent.setComponent(new ComponentName( 3415 aInfo.applicationInfo.packageName, aInfo.name)); 3416 intent.setFlags(intent.getFlags()&~( 3417 Intent.FLAG_ACTIVITY_FORWARD_RESULT| 3418 Intent.FLAG_ACTIVITY_CLEAR_TOP| 3419 Intent.FLAG_ACTIVITY_MULTIPLE_TASK| 3420 Intent.FLAG_ACTIVITY_NEW_TASK)); 3421 3422 // Okay now we need to start the new activity, replacing the 3423 // currently running activity. This is a little tricky because 3424 // we want to start the new one as if the current one is finished, 3425 // but not finish the current one first so that there is no flicker. 3426 // And thus... 3427 final boolean wasFinishing = r.finishing; 3428 r.finishing = true; 3429 3430 // Propagate reply information over to the new activity. 3431 final ActivityRecord resultTo = r.resultTo; 3432 final String resultWho = r.resultWho; 3433 final int requestCode = r.requestCode; 3434 r.resultTo = null; 3435 if (resultTo != null) { 3436 resultTo.removeResultsLocked(r, resultWho, requestCode); 3437 } 3438 3439 final long origId = Binder.clearCallingIdentity(); 3440 int res = mStackSupervisor.startActivityLocked(r.app.thread, intent, 3441 r.resolvedType, aInfo, null, null, resultTo != null ? resultTo.appToken : null, 3442 resultWho, requestCode, -1, r.launchedFromUid, r.launchedFromPackage, 0, 3443 options, false, null, null); 3444 Binder.restoreCallingIdentity(origId); 3445 3446 r.finishing = wasFinishing; 3447 if (res != ActivityManager.START_SUCCESS) { 3448 return false; 3449 } 3450 return true; 3451 } 3452 } 3453 3454 final int startActivityInPackage(int uid, String callingPackage, 3455 Intent intent, String resolvedType, IBinder resultTo, 3456 String resultWho, int requestCode, int startFlags, Bundle options, int userId, 3457 IActivityContainer container) { 3458 3459 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3460 false, true, "startActivityInPackage", null); 3461 3462 // TODO: Switch to user app stacks here. 3463 int ret = mStackSupervisor.startActivityMayWait(null, uid, callingPackage, intent, resolvedType, 3464 null, null, resultTo, resultWho, requestCode, startFlags, 3465 null, null, null, null, options, userId, container); 3466 return ret; 3467 } 3468 3469 @Override 3470 public final int startActivities(IApplicationThread caller, String callingPackage, 3471 Intent[] intents, String[] resolvedTypes, IBinder resultTo, Bundle options, 3472 int userId) { 3473 enforceNotIsolatedCaller("startActivities"); 3474 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3475 false, true, "startActivity", null); 3476 // TODO: Switch to user app stacks here. 3477 int ret = mStackSupervisor.startActivities(caller, -1, callingPackage, intents, 3478 resolvedTypes, resultTo, options, userId); 3479 return ret; 3480 } 3481 3482 final int startActivitiesInPackage(int uid, String callingPackage, 3483 Intent[] intents, String[] resolvedTypes, IBinder resultTo, 3484 Bundle options, int userId) { 3485 3486 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 3487 false, true, "startActivityInPackage", null); 3488 // TODO: Switch to user app stacks here. 3489 int ret = mStackSupervisor.startActivities(null, uid, callingPackage, intents, resolvedTypes, 3490 resultTo, options, userId); 3491 return ret; 3492 } 3493 3494 final void addRecentTaskLocked(TaskRecord task) { 3495 int N = mRecentTasks.size(); 3496 // Quick case: check if the top-most recent task is the same. 3497 if (N > 0 && mRecentTasks.get(0) == task) { 3498 return; 3499 } 3500 // Another quick case: never add voice sessions. 3501 if (task.voiceSession != null) { 3502 return; 3503 } 3504 // Remove any existing entries that are the same kind of task. 3505 final Intent intent = task.intent; 3506 final boolean document = intent != null && intent.isDocument(); 3507 for (int i=0; i<N; i++) { 3508 TaskRecord tr = mRecentTasks.get(i); 3509 if (task != tr) { 3510 if (task.userId != tr.userId) { 3511 continue; 3512 } 3513 final Intent trIntent = tr.intent; 3514 if ((task.affinity == null || !task.affinity.equals(tr.affinity)) && 3515 (intent == null || !intent.filterEquals(trIntent))) { 3516 continue; 3517 } 3518 if (document || trIntent != null && trIntent.isDocument()) { 3519 // Document tasks do not match other tasks. 3520 continue; 3521 } 3522 } 3523 3524 // Either task and tr are the same or, their affinities match or their intents match 3525 // and neither of them is a document. 3526 tr.disposeThumbnail(); 3527 mRecentTasks.remove(i); 3528 i--; 3529 N--; 3530 if (task.intent == null) { 3531 // If the new recent task we are adding is not fully 3532 // specified, then replace it with the existing recent task. 3533 task = tr; 3534 } 3535 } 3536 if (N >= MAX_RECENT_TASKS) { 3537 mRecentTasks.remove(N-1).disposeThumbnail(); 3538 } 3539 mRecentTasks.add(0, task); 3540 } 3541 3542 @Override 3543 public void reportActivityFullyDrawn(IBinder token) { 3544 synchronized (this) { 3545 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3546 if (r == null) { 3547 return; 3548 } 3549 r.reportFullyDrawnLocked(); 3550 } 3551 } 3552 3553 @Override 3554 public void setRequestedOrientation(IBinder token, int requestedOrientation) { 3555 synchronized (this) { 3556 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3557 if (r == null) { 3558 return; 3559 } 3560 final long origId = Binder.clearCallingIdentity(); 3561 mWindowManager.setAppOrientation(r.appToken, requestedOrientation); 3562 Configuration config = mWindowManager.updateOrientationFromAppTokens( 3563 mConfiguration, r.mayFreezeScreenLocked(r.app) ? r.appToken : null); 3564 if (config != null) { 3565 r.frozenBeforeDestroy = true; 3566 if (!updateConfigurationLocked(config, r, false, false)) { 3567 mStackSupervisor.resumeTopActivitiesLocked(); 3568 } 3569 } 3570 Binder.restoreCallingIdentity(origId); 3571 } 3572 } 3573 3574 @Override 3575 public int getRequestedOrientation(IBinder token) { 3576 synchronized (this) { 3577 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3578 if (r == null) { 3579 return ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED; 3580 } 3581 return mWindowManager.getAppOrientation(r.appToken); 3582 } 3583 } 3584 3585 /** 3586 * This is the internal entry point for handling Activity.finish(). 3587 * 3588 * @param token The Binder token referencing the Activity we want to finish. 3589 * @param resultCode Result code, if any, from this Activity. 3590 * @param resultData Result data (Intent), if any, from this Activity. 3591 * @param finishTask Whether to finish the task associated with this Activity. Only applies to 3592 * the root Activity in the task. 3593 * 3594 * @return Returns true if the activity successfully finished, or false if it is still running. 3595 */ 3596 @Override 3597 public final boolean finishActivity(IBinder token, int resultCode, Intent resultData, 3598 boolean finishTask) { 3599 // Refuse possible leaked file descriptors 3600 if (resultData != null && resultData.hasFileDescriptors() == true) { 3601 throw new IllegalArgumentException("File descriptors passed in Intent"); 3602 } 3603 3604 synchronized(this) { 3605 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3606 if (r == null) { 3607 return true; 3608 } 3609 // Keep track of the root activity of the task before we finish it 3610 TaskRecord tr = r.task; 3611 ActivityRecord rootR = tr.getRootActivity(); 3612 if (mController != null) { 3613 // Find the first activity that is not finishing. 3614 ActivityRecord next = r.task.stack.topRunningActivityLocked(token, 0); 3615 if (next != null) { 3616 // ask watcher if this is allowed 3617 boolean resumeOK = true; 3618 try { 3619 resumeOK = mController.activityResuming(next.packageName); 3620 } catch (RemoteException e) { 3621 mController = null; 3622 Watchdog.getInstance().setActivityController(null); 3623 } 3624 3625 if (!resumeOK) { 3626 return false; 3627 } 3628 } 3629 } 3630 final long origId = Binder.clearCallingIdentity(); 3631 try { 3632 boolean res; 3633 if (finishTask && r == rootR) { 3634 // If requested, remove the task that is associated to this activity only if it 3635 // was the root activity in the task. The result code and data is ignored because 3636 // we don't support returning them across task boundaries. 3637 res = removeTaskByIdLocked(tr.taskId, 0); 3638 } else { 3639 res = tr.stack.requestFinishActivityLocked(token, resultCode, 3640 resultData, "app-request", true); 3641 } 3642 return res; 3643 } finally { 3644 Binder.restoreCallingIdentity(origId); 3645 } 3646 } 3647 } 3648 3649 @Override 3650 public final void finishHeavyWeightApp() { 3651 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 3652 != PackageManager.PERMISSION_GRANTED) { 3653 String msg = "Permission Denial: finishHeavyWeightApp() from pid=" 3654 + Binder.getCallingPid() 3655 + ", uid=" + Binder.getCallingUid() 3656 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 3657 Slog.w(TAG, msg); 3658 throw new SecurityException(msg); 3659 } 3660 3661 synchronized(this) { 3662 if (mHeavyWeightProcess == null) { 3663 return; 3664 } 3665 3666 ArrayList<ActivityRecord> activities = new ArrayList<ActivityRecord>( 3667 mHeavyWeightProcess.activities); 3668 for (int i=0; i<activities.size(); i++) { 3669 ActivityRecord r = activities.get(i); 3670 if (!r.finishing) { 3671 r.task.stack.finishActivityLocked(r, Activity.RESULT_CANCELED, 3672 null, "finish-heavy", true); 3673 } 3674 } 3675 3676 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 3677 mHeavyWeightProcess.userId, 0)); 3678 mHeavyWeightProcess = null; 3679 } 3680 } 3681 3682 @Override 3683 public void crashApplication(int uid, int initialPid, String packageName, 3684 String message) { 3685 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 3686 != PackageManager.PERMISSION_GRANTED) { 3687 String msg = "Permission Denial: crashApplication() from pid=" 3688 + Binder.getCallingPid() 3689 + ", uid=" + Binder.getCallingUid() 3690 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 3691 Slog.w(TAG, msg); 3692 throw new SecurityException(msg); 3693 } 3694 3695 synchronized(this) { 3696 ProcessRecord proc = null; 3697 3698 // Figure out which process to kill. We don't trust that initialPid 3699 // still has any relation to current pids, so must scan through the 3700 // list. 3701 synchronized (mPidsSelfLocked) { 3702 for (int i=0; i<mPidsSelfLocked.size(); i++) { 3703 ProcessRecord p = mPidsSelfLocked.valueAt(i); 3704 if (p.uid != uid) { 3705 continue; 3706 } 3707 if (p.pid == initialPid) { 3708 proc = p; 3709 break; 3710 } 3711 if (p.pkgList.containsKey(packageName)) { 3712 proc = p; 3713 } 3714 } 3715 } 3716 3717 if (proc == null) { 3718 Slog.w(TAG, "crashApplication: nothing for uid=" + uid 3719 + " initialPid=" + initialPid 3720 + " packageName=" + packageName); 3721 return; 3722 } 3723 3724 if (proc.thread != null) { 3725 if (proc.pid == Process.myPid()) { 3726 Log.w(TAG, "crashApplication: trying to crash self!"); 3727 return; 3728 } 3729 long ident = Binder.clearCallingIdentity(); 3730 try { 3731 proc.thread.scheduleCrash(message); 3732 } catch (RemoteException e) { 3733 } 3734 Binder.restoreCallingIdentity(ident); 3735 } 3736 } 3737 } 3738 3739 @Override 3740 public final void finishSubActivity(IBinder token, String resultWho, 3741 int requestCode) { 3742 synchronized(this) { 3743 final long origId = Binder.clearCallingIdentity(); 3744 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3745 if (r != null) { 3746 r.task.stack.finishSubActivityLocked(r, resultWho, requestCode); 3747 } 3748 Binder.restoreCallingIdentity(origId); 3749 } 3750 } 3751 3752 @Override 3753 public boolean finishActivityAffinity(IBinder token) { 3754 synchronized(this) { 3755 final long origId = Binder.clearCallingIdentity(); 3756 ActivityRecord r = ActivityRecord.isInStackLocked(token); 3757 boolean res = false; 3758 if (r != null) { 3759 res = r.task.stack.finishActivityAffinityLocked(r); 3760 } 3761 Binder.restoreCallingIdentity(origId); 3762 return res; 3763 } 3764 } 3765 3766 @Override 3767 public boolean willActivityBeVisible(IBinder token) { 3768 synchronized(this) { 3769 ActivityStack stack = ActivityRecord.getStackLocked(token); 3770 if (stack != null) { 3771 return stack.willActivityBeVisibleLocked(token); 3772 } 3773 return false; 3774 } 3775 } 3776 3777 @Override 3778 public void overridePendingTransition(IBinder token, String packageName, 3779 int enterAnim, int exitAnim) { 3780 synchronized(this) { 3781 ActivityRecord self = ActivityRecord.isInStackLocked(token); 3782 if (self == null) { 3783 return; 3784 } 3785 3786 final long origId = Binder.clearCallingIdentity(); 3787 3788 if (self.state == ActivityState.RESUMED 3789 || self.state == ActivityState.PAUSING) { 3790 mWindowManager.overridePendingAppTransition(packageName, 3791 enterAnim, exitAnim, null); 3792 } 3793 3794 Binder.restoreCallingIdentity(origId); 3795 } 3796 } 3797 3798 /** 3799 * Main function for removing an existing process from the activity manager 3800 * as a result of that process going away. Clears out all connections 3801 * to the process. 3802 */ 3803 private final void handleAppDiedLocked(ProcessRecord app, 3804 boolean restarting, boolean allowRestart) { 3805 int pid = app.pid; 3806 cleanUpApplicationRecordLocked(app, restarting, allowRestart, -1); 3807 if (!restarting) { 3808 removeLruProcessLocked(app); 3809 if (pid > 0) { 3810 ProcessList.remove(pid); 3811 } 3812 } 3813 3814 if (mProfileProc == app) { 3815 clearProfilerLocked(); 3816 } 3817 3818 // Remove this application's activities from active lists. 3819 boolean hasVisibleActivities = mStackSupervisor.handleAppDiedLocked(app); 3820 3821 app.activities.clear(); 3822 3823 if (app.instrumentationClass != null) { 3824 Slog.w(TAG, "Crash of app " + app.processName 3825 + " running instrumentation " + app.instrumentationClass); 3826 Bundle info = new Bundle(); 3827 info.putString("shortMsg", "Process crashed."); 3828 finishInstrumentationLocked(app, Activity.RESULT_CANCELED, info); 3829 } 3830 3831 if (!restarting) { 3832 if (!mStackSupervisor.resumeTopActivitiesLocked()) { 3833 // If there was nothing to resume, and we are not already 3834 // restarting this process, but there is a visible activity that 3835 // is hosted by the process... then make sure all visible 3836 // activities are running, taking care of restarting this 3837 // process. 3838 if (hasVisibleActivities) { 3839 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 3840 } 3841 } 3842 } 3843 } 3844 3845 private final int getLRURecordIndexForAppLocked(IApplicationThread thread) { 3846 IBinder threadBinder = thread.asBinder(); 3847 // Find the application record. 3848 for (int i=mLruProcesses.size()-1; i>=0; i--) { 3849 ProcessRecord rec = mLruProcesses.get(i); 3850 if (rec.thread != null && rec.thread.asBinder() == threadBinder) { 3851 return i; 3852 } 3853 } 3854 return -1; 3855 } 3856 3857 final ProcessRecord getRecordForAppLocked( 3858 IApplicationThread thread) { 3859 if (thread == null) { 3860 return null; 3861 } 3862 3863 int appIndex = getLRURecordIndexForAppLocked(thread); 3864 return appIndex >= 0 ? mLruProcesses.get(appIndex) : null; 3865 } 3866 3867 final void doLowMemReportIfNeededLocked(ProcessRecord dyingProc) { 3868 // If there are no longer any background processes running, 3869 // and the app that died was not running instrumentation, 3870 // then tell everyone we are now low on memory. 3871 boolean haveBg = false; 3872 for (int i=mLruProcesses.size()-1; i>=0; i--) { 3873 ProcessRecord rec = mLruProcesses.get(i); 3874 if (rec.thread != null 3875 && rec.setProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 3876 haveBg = true; 3877 break; 3878 } 3879 } 3880 3881 if (!haveBg) { 3882 boolean doReport = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 3883 if (doReport) { 3884 long now = SystemClock.uptimeMillis(); 3885 if (now < (mLastMemUsageReportTime+5*60*1000)) { 3886 doReport = false; 3887 } else { 3888 mLastMemUsageReportTime = now; 3889 } 3890 } 3891 final ArrayList<ProcessMemInfo> memInfos 3892 = doReport ? new ArrayList<ProcessMemInfo>(mLruProcesses.size()) : null; 3893 EventLog.writeEvent(EventLogTags.AM_LOW_MEMORY, mLruProcesses.size()); 3894 long now = SystemClock.uptimeMillis(); 3895 for (int i=mLruProcesses.size()-1; i>=0; i--) { 3896 ProcessRecord rec = mLruProcesses.get(i); 3897 if (rec == dyingProc || rec.thread == null) { 3898 continue; 3899 } 3900 if (doReport) { 3901 memInfos.add(new ProcessMemInfo(rec.processName, rec.pid, rec.setAdj, 3902 rec.setProcState, rec.adjType, rec.makeAdjReason())); 3903 } 3904 if ((rec.lastLowMemory+GC_MIN_INTERVAL) <= now) { 3905 // The low memory report is overriding any current 3906 // state for a GC request. Make sure to do 3907 // heavy/important/visible/foreground processes first. 3908 if (rec.setAdj <= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 3909 rec.lastRequestedGc = 0; 3910 } else { 3911 rec.lastRequestedGc = rec.lastLowMemory; 3912 } 3913 rec.reportLowMemory = true; 3914 rec.lastLowMemory = now; 3915 mProcessesToGc.remove(rec); 3916 addProcessToGcListLocked(rec); 3917 } 3918 } 3919 if (doReport) { 3920 Message msg = mHandler.obtainMessage(REPORT_MEM_USAGE_MSG, memInfos); 3921 mHandler.sendMessage(msg); 3922 } 3923 scheduleAppGcsLocked(); 3924 } 3925 } 3926 3927 final void appDiedLocked(ProcessRecord app, int pid, 3928 IApplicationThread thread) { 3929 3930 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 3931 synchronized (stats) { 3932 stats.noteProcessDiedLocked(app.info.uid, pid); 3933 } 3934 3935 // Clean up already done if the process has been re-started. 3936 if (app.pid == pid && app.thread != null && 3937 app.thread.asBinder() == thread.asBinder()) { 3938 boolean doLowMem = app.instrumentationClass == null; 3939 boolean doOomAdj = doLowMem; 3940 if (!app.killedByAm) { 3941 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 3942 + ") has died."); 3943 mAllowLowerMemLevel = true; 3944 } else { 3945 // Note that we always want to do oom adj to update our state with the 3946 // new number of procs. 3947 mAllowLowerMemLevel = false; 3948 doLowMem = false; 3949 } 3950 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 3951 if (DEBUG_CLEANUP) Slog.v( 3952 TAG, "Dying app: " + app + ", pid: " + pid 3953 + ", thread: " + thread.asBinder()); 3954 handleAppDiedLocked(app, false, true); 3955 3956 if (doOomAdj) { 3957 updateOomAdjLocked(); 3958 } 3959 if (doLowMem) { 3960 doLowMemReportIfNeededLocked(app); 3961 } 3962 } else if (app.pid != pid) { 3963 // A new process has already been started. 3964 Slog.i(TAG, "Process " + app.processName + " (pid " + pid 3965 + ") has died and restarted (pid " + app.pid + ")."); 3966 EventLog.writeEvent(EventLogTags.AM_PROC_DIED, app.userId, app.pid, app.processName); 3967 } else if (DEBUG_PROCESSES) { 3968 Slog.d(TAG, "Received spurious death notification for thread " 3969 + thread.asBinder()); 3970 } 3971 } 3972 3973 /** 3974 * If a stack trace dump file is configured, dump process stack traces. 3975 * @param clearTraces causes the dump file to be erased prior to the new 3976 * traces being written, if true; when false, the new traces will be 3977 * appended to any existing file content. 3978 * @param firstPids of dalvik VM processes to dump stack traces for first 3979 * @param lastPids of dalvik VM processes to dump stack traces for last 3980 * @param nativeProcs optional list of native process names to dump stack crawls 3981 * @return file containing stack traces, or null if no dump file is configured 3982 */ 3983 public static File dumpStackTraces(boolean clearTraces, ArrayList<Integer> firstPids, 3984 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 3985 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 3986 if (tracesPath == null || tracesPath.length() == 0) { 3987 return null; 3988 } 3989 3990 File tracesFile = new File(tracesPath); 3991 try { 3992 File tracesDir = tracesFile.getParentFile(); 3993 if (!tracesDir.exists()) { 3994 tracesFile.mkdirs(); 3995 if (!SELinux.restorecon(tracesDir)) { 3996 return null; 3997 } 3998 } 3999 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4000 4001 if (clearTraces && tracesFile.exists()) tracesFile.delete(); 4002 tracesFile.createNewFile(); 4003 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4004 } catch (IOException e) { 4005 Slog.w(TAG, "Unable to prepare ANR traces file: " + tracesPath, e); 4006 return null; 4007 } 4008 4009 dumpStackTraces(tracesPath, firstPids, processCpuTracker, lastPids, nativeProcs); 4010 return tracesFile; 4011 } 4012 4013 private static void dumpStackTraces(String tracesPath, ArrayList<Integer> firstPids, 4014 ProcessCpuTracker processCpuTracker, SparseArray<Boolean> lastPids, String[] nativeProcs) { 4015 // Use a FileObserver to detect when traces finish writing. 4016 // The order of traces is considered important to maintain for legibility. 4017 FileObserver observer = new FileObserver(tracesPath, FileObserver.CLOSE_WRITE) { 4018 @Override 4019 public synchronized void onEvent(int event, String path) { notify(); } 4020 }; 4021 4022 try { 4023 observer.startWatching(); 4024 4025 // First collect all of the stacks of the most important pids. 4026 if (firstPids != null) { 4027 try { 4028 int num = firstPids.size(); 4029 for (int i = 0; i < num; i++) { 4030 synchronized (observer) { 4031 Process.sendSignal(firstPids.get(i), Process.SIGNAL_QUIT); 4032 observer.wait(200); // Wait for write-close, give up after 200msec 4033 } 4034 } 4035 } catch (InterruptedException e) { 4036 Log.wtf(TAG, e); 4037 } 4038 } 4039 4040 // Next collect the stacks of the native pids 4041 if (nativeProcs != null) { 4042 int[] pids = Process.getPidsForCommands(nativeProcs); 4043 if (pids != null) { 4044 for (int pid : pids) { 4045 Debug.dumpNativeBacktraceToFile(pid, tracesPath); 4046 } 4047 } 4048 } 4049 4050 // Lastly, measure CPU usage. 4051 if (processCpuTracker != null) { 4052 processCpuTracker.init(); 4053 System.gc(); 4054 processCpuTracker.update(); 4055 try { 4056 synchronized (processCpuTracker) { 4057 processCpuTracker.wait(500); // measure over 1/2 second. 4058 } 4059 } catch (InterruptedException e) { 4060 } 4061 processCpuTracker.update(); 4062 4063 // We'll take the stack crawls of just the top apps using CPU. 4064 final int N = processCpuTracker.countWorkingStats(); 4065 int numProcs = 0; 4066 for (int i=0; i<N && numProcs<5; i++) { 4067 ProcessCpuTracker.Stats stats = processCpuTracker.getWorkingStats(i); 4068 if (lastPids.indexOfKey(stats.pid) >= 0) { 4069 numProcs++; 4070 try { 4071 synchronized (observer) { 4072 Process.sendSignal(stats.pid, Process.SIGNAL_QUIT); 4073 observer.wait(200); // Wait for write-close, give up after 200msec 4074 } 4075 } catch (InterruptedException e) { 4076 Log.wtf(TAG, e); 4077 } 4078 4079 } 4080 } 4081 } 4082 } finally { 4083 observer.stopWatching(); 4084 } 4085 } 4086 4087 final void logAppTooSlow(ProcessRecord app, long startTime, String msg) { 4088 if (true || IS_USER_BUILD) { 4089 return; 4090 } 4091 String tracesPath = SystemProperties.get("dalvik.vm.stack-trace-file", null); 4092 if (tracesPath == null || tracesPath.length() == 0) { 4093 return; 4094 } 4095 4096 StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads(); 4097 StrictMode.allowThreadDiskWrites(); 4098 try { 4099 final File tracesFile = new File(tracesPath); 4100 final File tracesDir = tracesFile.getParentFile(); 4101 final File tracesTmp = new File(tracesDir, "__tmp__"); 4102 try { 4103 if (!tracesDir.exists()) { 4104 tracesFile.mkdirs(); 4105 if (!SELinux.restorecon(tracesDir.getPath())) { 4106 return; 4107 } 4108 } 4109 FileUtils.setPermissions(tracesDir.getPath(), 0775, -1, -1); // drwxrwxr-x 4110 4111 if (tracesFile.exists()) { 4112 tracesTmp.delete(); 4113 tracesFile.renameTo(tracesTmp); 4114 } 4115 StringBuilder sb = new StringBuilder(); 4116 Time tobj = new Time(); 4117 tobj.set(System.currentTimeMillis()); 4118 sb.append(tobj.format("%Y-%m-%d %H:%M:%S")); 4119 sb.append(": "); 4120 TimeUtils.formatDuration(SystemClock.uptimeMillis()-startTime, sb); 4121 sb.append(" since "); 4122 sb.append(msg); 4123 FileOutputStream fos = new FileOutputStream(tracesFile); 4124 fos.write(sb.toString().getBytes()); 4125 if (app == null) { 4126 fos.write("\n*** No application process!".getBytes()); 4127 } 4128 fos.close(); 4129 FileUtils.setPermissions(tracesFile.getPath(), 0666, -1, -1); // -rw-rw-rw- 4130 } catch (IOException e) { 4131 Slog.w(TAG, "Unable to prepare slow app traces file: " + tracesPath, e); 4132 return; 4133 } 4134 4135 if (app != null) { 4136 ArrayList<Integer> firstPids = new ArrayList<Integer>(); 4137 firstPids.add(app.pid); 4138 dumpStackTraces(tracesPath, firstPids, null, null, null); 4139 } 4140 4141 File lastTracesFile = null; 4142 File curTracesFile = null; 4143 for (int i=9; i>=0; i--) { 4144 String name = String.format(Locale.US, "slow%02d.txt", i); 4145 curTracesFile = new File(tracesDir, name); 4146 if (curTracesFile.exists()) { 4147 if (lastTracesFile != null) { 4148 curTracesFile.renameTo(lastTracesFile); 4149 } else { 4150 curTracesFile.delete(); 4151 } 4152 } 4153 lastTracesFile = curTracesFile; 4154 } 4155 tracesFile.renameTo(curTracesFile); 4156 if (tracesTmp.exists()) { 4157 tracesTmp.renameTo(tracesFile); 4158 } 4159 } finally { 4160 StrictMode.setThreadPolicy(oldPolicy); 4161 } 4162 } 4163 4164 final void appNotResponding(ProcessRecord app, ActivityRecord activity, 4165 ActivityRecord parent, boolean aboveSystem, final String annotation) { 4166 ArrayList<Integer> firstPids = new ArrayList<Integer>(5); 4167 SparseArray<Boolean> lastPids = new SparseArray<Boolean>(20); 4168 4169 if (mController != null) { 4170 try { 4171 // 0 == continue, -1 = kill process immediately 4172 int res = mController.appEarlyNotResponding(app.processName, app.pid, annotation); 4173 if (res < 0 && app.pid != MY_PID) Process.killProcess(app.pid); 4174 } catch (RemoteException e) { 4175 mController = null; 4176 Watchdog.getInstance().setActivityController(null); 4177 } 4178 } 4179 4180 long anrTime = SystemClock.uptimeMillis(); 4181 if (MONITOR_CPU_USAGE) { 4182 updateCpuStatsNow(); 4183 } 4184 4185 synchronized (this) { 4186 // PowerManager.reboot() can block for a long time, so ignore ANRs while shutting down. 4187 if (mShuttingDown) { 4188 Slog.i(TAG, "During shutdown skipping ANR: " + app + " " + annotation); 4189 return; 4190 } else if (app.notResponding) { 4191 Slog.i(TAG, "Skipping duplicate ANR: " + app + " " + annotation); 4192 return; 4193 } else if (app.crashing) { 4194 Slog.i(TAG, "Crashing app skipping ANR: " + app + " " + annotation); 4195 return; 4196 } 4197 4198 // In case we come through here for the same app before completing 4199 // this one, mark as anring now so we will bail out. 4200 app.notResponding = true; 4201 4202 // Log the ANR to the event log. 4203 EventLog.writeEvent(EventLogTags.AM_ANR, app.userId, app.pid, 4204 app.processName, app.info.flags, annotation); 4205 4206 // Dump thread traces as quickly as we can, starting with "interesting" processes. 4207 firstPids.add(app.pid); 4208 4209 int parentPid = app.pid; 4210 if (parent != null && parent.app != null && parent.app.pid > 0) parentPid = parent.app.pid; 4211 if (parentPid != app.pid) firstPids.add(parentPid); 4212 4213 if (MY_PID != app.pid && MY_PID != parentPid) firstPids.add(MY_PID); 4214 4215 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 4216 ProcessRecord r = mLruProcesses.get(i); 4217 if (r != null && r.thread != null) { 4218 int pid = r.pid; 4219 if (pid > 0 && pid != app.pid && pid != parentPid && pid != MY_PID) { 4220 if (r.persistent) { 4221 firstPids.add(pid); 4222 } else { 4223 lastPids.put(pid, Boolean.TRUE); 4224 } 4225 } 4226 } 4227 } 4228 } 4229 4230 // Log the ANR to the main log. 4231 StringBuilder info = new StringBuilder(); 4232 info.setLength(0); 4233 info.append("ANR in ").append(app.processName); 4234 if (activity != null && activity.shortComponentName != null) { 4235 info.append(" (").append(activity.shortComponentName).append(")"); 4236 } 4237 info.append("\n"); 4238 info.append("PID: ").append(app.pid).append("\n"); 4239 if (annotation != null) { 4240 info.append("Reason: ").append(annotation).append("\n"); 4241 } 4242 if (parent != null && parent != activity) { 4243 info.append("Parent: ").append(parent.shortComponentName).append("\n"); 4244 } 4245 4246 final ProcessCpuTracker processCpuTracker = new ProcessCpuTracker(true); 4247 4248 File tracesFile = dumpStackTraces(true, firstPids, processCpuTracker, lastPids, 4249 NATIVE_STACKS_OF_INTEREST); 4250 4251 String cpuInfo = null; 4252 if (MONITOR_CPU_USAGE) { 4253 updateCpuStatsNow(); 4254 synchronized (mProcessCpuThread) { 4255 cpuInfo = mProcessCpuTracker.printCurrentState(anrTime); 4256 } 4257 info.append(processCpuTracker.printCurrentLoad()); 4258 info.append(cpuInfo); 4259 } 4260 4261 info.append(processCpuTracker.printCurrentState(anrTime)); 4262 4263 Slog.e(TAG, info.toString()); 4264 if (tracesFile == null) { 4265 // There is no trace file, so dump (only) the alleged culprit's threads to the log 4266 Process.sendSignal(app.pid, Process.SIGNAL_QUIT); 4267 } 4268 4269 addErrorToDropBox("anr", app, app.processName, activity, parent, annotation, 4270 cpuInfo, tracesFile, null); 4271 4272 if (mController != null) { 4273 try { 4274 // 0 == show dialog, 1 = keep waiting, -1 = kill process immediately 4275 int res = mController.appNotResponding(app.processName, app.pid, info.toString()); 4276 if (res != 0) { 4277 if (res < 0 && app.pid != MY_PID) { 4278 Process.killProcess(app.pid); 4279 } else { 4280 synchronized (this) { 4281 mServices.scheduleServiceTimeoutLocked(app); 4282 } 4283 } 4284 return; 4285 } 4286 } catch (RemoteException e) { 4287 mController = null; 4288 Watchdog.getInstance().setActivityController(null); 4289 } 4290 } 4291 4292 // Unless configured otherwise, swallow ANRs in background processes & kill the process. 4293 boolean showBackground = Settings.Secure.getInt(mContext.getContentResolver(), 4294 Settings.Secure.ANR_SHOW_BACKGROUND, 0) != 0; 4295 4296 synchronized (this) { 4297 if (!showBackground && !app.isInterestingToUserLocked() && app.pid != MY_PID) { 4298 killUnneededProcessLocked(app, "background ANR"); 4299 return; 4300 } 4301 4302 // Set the app's notResponding state, and look up the errorReportReceiver 4303 makeAppNotRespondingLocked(app, 4304 activity != null ? activity.shortComponentName : null, 4305 annotation != null ? "ANR " + annotation : "ANR", 4306 info.toString()); 4307 4308 // Bring up the infamous App Not Responding dialog 4309 Message msg = Message.obtain(); 4310 HashMap<String, Object> map = new HashMap<String, Object>(); 4311 msg.what = SHOW_NOT_RESPONDING_MSG; 4312 msg.obj = map; 4313 msg.arg1 = aboveSystem ? 1 : 0; 4314 map.put("app", app); 4315 if (activity != null) { 4316 map.put("activity", activity); 4317 } 4318 4319 mHandler.sendMessage(msg); 4320 } 4321 } 4322 4323 final void showLaunchWarningLocked(final ActivityRecord cur, final ActivityRecord next) { 4324 if (!mLaunchWarningShown) { 4325 mLaunchWarningShown = true; 4326 mHandler.post(new Runnable() { 4327 @Override 4328 public void run() { 4329 synchronized (ActivityManagerService.this) { 4330 final Dialog d = new LaunchWarningWindow(mContext, cur, next); 4331 d.show(); 4332 mHandler.postDelayed(new Runnable() { 4333 @Override 4334 public void run() { 4335 synchronized (ActivityManagerService.this) { 4336 d.dismiss(); 4337 mLaunchWarningShown = false; 4338 } 4339 } 4340 }, 4000); 4341 } 4342 } 4343 }); 4344 } 4345 } 4346 4347 @Override 4348 public boolean clearApplicationUserData(final String packageName, 4349 final IPackageDataObserver observer, int userId) { 4350 enforceNotIsolatedCaller("clearApplicationUserData"); 4351 int uid = Binder.getCallingUid(); 4352 int pid = Binder.getCallingPid(); 4353 userId = handleIncomingUser(pid, uid, 4354 userId, false, true, "clearApplicationUserData", null); 4355 long callingId = Binder.clearCallingIdentity(); 4356 try { 4357 IPackageManager pm = AppGlobals.getPackageManager(); 4358 int pkgUid = -1; 4359 synchronized(this) { 4360 try { 4361 pkgUid = pm.getPackageUid(packageName, userId); 4362 } catch (RemoteException e) { 4363 } 4364 if (pkgUid == -1) { 4365 Slog.w(TAG, "Invalid packageName: " + packageName); 4366 if (observer != null) { 4367 try { 4368 observer.onRemoveCompleted(packageName, false); 4369 } catch (RemoteException e) { 4370 Slog.i(TAG, "Observer no longer exists."); 4371 } 4372 } 4373 return false; 4374 } 4375 if (uid == pkgUid || checkComponentPermission( 4376 android.Manifest.permission.CLEAR_APP_USER_DATA, 4377 pid, uid, -1, true) 4378 == PackageManager.PERMISSION_GRANTED) { 4379 forceStopPackageLocked(packageName, pkgUid, "clear data"); 4380 } else { 4381 throw new SecurityException("PID " + pid + " does not have permission " 4382 + android.Manifest.permission.CLEAR_APP_USER_DATA + " to clear data" 4383 + " of package " + packageName); 4384 } 4385 } 4386 4387 try { 4388 // Clear application user data 4389 pm.clearApplicationUserData(packageName, observer, userId); 4390 4391 // Remove all permissions granted from/to this package 4392 removeUriPermissionsForPackageLocked(packageName, userId, true); 4393 4394 Intent intent = new Intent(Intent.ACTION_PACKAGE_DATA_CLEARED, 4395 Uri.fromParts("package", packageName, null)); 4396 intent.putExtra(Intent.EXTRA_UID, pkgUid); 4397 broadcastIntentInPackage("android", Process.SYSTEM_UID, intent, 4398 null, null, 0, null, null, null, false, false, userId); 4399 } catch (RemoteException e) { 4400 } 4401 } finally { 4402 Binder.restoreCallingIdentity(callingId); 4403 } 4404 return true; 4405 } 4406 4407 @Override 4408 public void killBackgroundProcesses(final String packageName, int userId) { 4409 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 4410 != PackageManager.PERMISSION_GRANTED && 4411 checkCallingPermission(android.Manifest.permission.RESTART_PACKAGES) 4412 != PackageManager.PERMISSION_GRANTED) { 4413 String msg = "Permission Denial: killBackgroundProcesses() from pid=" 4414 + Binder.getCallingPid() 4415 + ", uid=" + Binder.getCallingUid() 4416 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 4417 Slog.w(TAG, msg); 4418 throw new SecurityException(msg); 4419 } 4420 4421 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 4422 userId, true, true, "killBackgroundProcesses", null); 4423 long callingId = Binder.clearCallingIdentity(); 4424 try { 4425 IPackageManager pm = AppGlobals.getPackageManager(); 4426 synchronized(this) { 4427 int appId = -1; 4428 try { 4429 appId = UserHandle.getAppId(pm.getPackageUid(packageName, 0)); 4430 } catch (RemoteException e) { 4431 } 4432 if (appId == -1) { 4433 Slog.w(TAG, "Invalid packageName: " + packageName); 4434 return; 4435 } 4436 killPackageProcessesLocked(packageName, appId, userId, 4437 ProcessList.SERVICE_ADJ, false, true, true, false, "kill background"); 4438 } 4439 } finally { 4440 Binder.restoreCallingIdentity(callingId); 4441 } 4442 } 4443 4444 @Override 4445 public void killAllBackgroundProcesses() { 4446 if (checkCallingPermission(android.Manifest.permission.KILL_BACKGROUND_PROCESSES) 4447 != PackageManager.PERMISSION_GRANTED) { 4448 String msg = "Permission Denial: killAllBackgroundProcesses() from pid=" 4449 + Binder.getCallingPid() 4450 + ", uid=" + Binder.getCallingUid() 4451 + " requires " + android.Manifest.permission.KILL_BACKGROUND_PROCESSES; 4452 Slog.w(TAG, msg); 4453 throw new SecurityException(msg); 4454 } 4455 4456 long callingId = Binder.clearCallingIdentity(); 4457 try { 4458 synchronized(this) { 4459 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 4460 final int NP = mProcessNames.getMap().size(); 4461 for (int ip=0; ip<NP; ip++) { 4462 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 4463 final int NA = apps.size(); 4464 for (int ia=0; ia<NA; ia++) { 4465 ProcessRecord app = apps.valueAt(ia); 4466 if (app.persistent) { 4467 // we don't kill persistent processes 4468 continue; 4469 } 4470 if (app.removed) { 4471 procs.add(app); 4472 } else if (app.setAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 4473 app.removed = true; 4474 procs.add(app); 4475 } 4476 } 4477 } 4478 4479 int N = procs.size(); 4480 for (int i=0; i<N; i++) { 4481 removeProcessLocked(procs.get(i), false, true, "kill all background"); 4482 } 4483 mAllowLowerMemLevel = true; 4484 updateOomAdjLocked(); 4485 doLowMemReportIfNeededLocked(null); 4486 } 4487 } finally { 4488 Binder.restoreCallingIdentity(callingId); 4489 } 4490 } 4491 4492 @Override 4493 public void forceStopPackage(final String packageName, int userId) { 4494 if (checkCallingPermission(android.Manifest.permission.FORCE_STOP_PACKAGES) 4495 != PackageManager.PERMISSION_GRANTED) { 4496 String msg = "Permission Denial: forceStopPackage() from pid=" 4497 + Binder.getCallingPid() 4498 + ", uid=" + Binder.getCallingUid() 4499 + " requires " + android.Manifest.permission.FORCE_STOP_PACKAGES; 4500 Slog.w(TAG, msg); 4501 throw new SecurityException(msg); 4502 } 4503 final int callingPid = Binder.getCallingPid(); 4504 userId = handleIncomingUser(callingPid, Binder.getCallingUid(), 4505 userId, true, true, "forceStopPackage", null); 4506 long callingId = Binder.clearCallingIdentity(); 4507 try { 4508 IPackageManager pm = AppGlobals.getPackageManager(); 4509 synchronized(this) { 4510 int[] users = userId == UserHandle.USER_ALL 4511 ? getUsersLocked() : new int[] { userId }; 4512 for (int user : users) { 4513 int pkgUid = -1; 4514 try { 4515 pkgUid = pm.getPackageUid(packageName, user); 4516 } catch (RemoteException e) { 4517 } 4518 if (pkgUid == -1) { 4519 Slog.w(TAG, "Invalid packageName: " + packageName); 4520 continue; 4521 } 4522 try { 4523 pm.setPackageStoppedState(packageName, true, user); 4524 } catch (RemoteException e) { 4525 } catch (IllegalArgumentException e) { 4526 Slog.w(TAG, "Failed trying to unstop package " 4527 + packageName + ": " + e); 4528 } 4529 if (isUserRunningLocked(user, false)) { 4530 forceStopPackageLocked(packageName, pkgUid, "from pid " + callingPid); 4531 } 4532 } 4533 } 4534 } finally { 4535 Binder.restoreCallingIdentity(callingId); 4536 } 4537 } 4538 4539 /* 4540 * The pkg name and app id have to be specified. 4541 */ 4542 @Override 4543 public void killApplicationWithAppId(String pkg, int appid, String reason) { 4544 if (pkg == null) { 4545 return; 4546 } 4547 // Make sure the uid is valid. 4548 if (appid < 0) { 4549 Slog.w(TAG, "Invalid appid specified for pkg : " + pkg); 4550 return; 4551 } 4552 int callerUid = Binder.getCallingUid(); 4553 // Only the system server can kill an application 4554 if (callerUid == Process.SYSTEM_UID) { 4555 // Post an aysnc message to kill the application 4556 Message msg = mHandler.obtainMessage(KILL_APPLICATION_MSG); 4557 msg.arg1 = appid; 4558 msg.arg2 = 0; 4559 Bundle bundle = new Bundle(); 4560 bundle.putString("pkg", pkg); 4561 bundle.putString("reason", reason); 4562 msg.obj = bundle; 4563 mHandler.sendMessage(msg); 4564 } else { 4565 throw new SecurityException(callerUid + " cannot kill pkg: " + 4566 pkg); 4567 } 4568 } 4569 4570 @Override 4571 public void closeSystemDialogs(String reason) { 4572 enforceNotIsolatedCaller("closeSystemDialogs"); 4573 4574 final int pid = Binder.getCallingPid(); 4575 final int uid = Binder.getCallingUid(); 4576 final long origId = Binder.clearCallingIdentity(); 4577 try { 4578 synchronized (this) { 4579 // Only allow this from foreground processes, so that background 4580 // applications can't abuse it to prevent system UI from being shown. 4581 if (uid >= Process.FIRST_APPLICATION_UID) { 4582 ProcessRecord proc; 4583 synchronized (mPidsSelfLocked) { 4584 proc = mPidsSelfLocked.get(pid); 4585 } 4586 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 4587 Slog.w(TAG, "Ignoring closeSystemDialogs " + reason 4588 + " from background process " + proc); 4589 return; 4590 } 4591 } 4592 closeSystemDialogsLocked(reason); 4593 } 4594 } finally { 4595 Binder.restoreCallingIdentity(origId); 4596 } 4597 } 4598 4599 void closeSystemDialogsLocked(String reason) { 4600 Intent intent = new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS); 4601 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4602 | Intent.FLAG_RECEIVER_FOREGROUND); 4603 if (reason != null) { 4604 intent.putExtra("reason", reason); 4605 } 4606 mWindowManager.closeSystemDialogs(reason); 4607 4608 mStackSupervisor.closeSystemDialogsLocked(); 4609 4610 broadcastIntentLocked(null, null, intent, null, 4611 null, 0, null, null, null, AppOpsManager.OP_NONE, false, false, -1, 4612 Process.SYSTEM_UID, UserHandle.USER_ALL); 4613 } 4614 4615 @Override 4616 public Debug.MemoryInfo[] getProcessMemoryInfo(int[] pids) { 4617 enforceNotIsolatedCaller("getProcessMemoryInfo"); 4618 Debug.MemoryInfo[] infos = new Debug.MemoryInfo[pids.length]; 4619 for (int i=pids.length-1; i>=0; i--) { 4620 ProcessRecord proc; 4621 int oomAdj; 4622 synchronized (this) { 4623 synchronized (mPidsSelfLocked) { 4624 proc = mPidsSelfLocked.get(pids[i]); 4625 oomAdj = proc != null ? proc.setAdj : 0; 4626 } 4627 } 4628 infos[i] = new Debug.MemoryInfo(); 4629 Debug.getMemoryInfo(pids[i], infos[i]); 4630 if (proc != null) { 4631 synchronized (this) { 4632 if (proc.thread != null && proc.setAdj == oomAdj) { 4633 // Record this for posterity if the process has been stable. 4634 proc.baseProcessTracker.addPss(infos[i].getTotalPss(), 4635 infos[i].getTotalUss(), false, proc.pkgList); 4636 } 4637 } 4638 } 4639 } 4640 return infos; 4641 } 4642 4643 @Override 4644 public long[] getProcessPss(int[] pids) { 4645 enforceNotIsolatedCaller("getProcessPss"); 4646 long[] pss = new long[pids.length]; 4647 for (int i=pids.length-1; i>=0; i--) { 4648 ProcessRecord proc; 4649 int oomAdj; 4650 synchronized (this) { 4651 synchronized (mPidsSelfLocked) { 4652 proc = mPidsSelfLocked.get(pids[i]); 4653 oomAdj = proc != null ? proc.setAdj : 0; 4654 } 4655 } 4656 long[] tmpUss = new long[1]; 4657 pss[i] = Debug.getPss(pids[i], tmpUss); 4658 if (proc != null) { 4659 synchronized (this) { 4660 if (proc.thread != null && proc.setAdj == oomAdj) { 4661 // Record this for posterity if the process has been stable. 4662 proc.baseProcessTracker.addPss(pss[i], tmpUss[0], false, proc.pkgList); 4663 } 4664 } 4665 } 4666 } 4667 return pss; 4668 } 4669 4670 @Override 4671 public void killApplicationProcess(String processName, int uid) { 4672 if (processName == null) { 4673 return; 4674 } 4675 4676 int callerUid = Binder.getCallingUid(); 4677 // Only the system server can kill an application 4678 if (callerUid == Process.SYSTEM_UID) { 4679 synchronized (this) { 4680 ProcessRecord app = getProcessRecordLocked(processName, uid, true); 4681 if (app != null && app.thread != null) { 4682 try { 4683 app.thread.scheduleSuicide(); 4684 } catch (RemoteException e) { 4685 // If the other end already died, then our work here is done. 4686 } 4687 } else { 4688 Slog.w(TAG, "Process/uid not found attempting kill of " 4689 + processName + " / " + uid); 4690 } 4691 } 4692 } else { 4693 throw new SecurityException(callerUid + " cannot kill app process: " + 4694 processName); 4695 } 4696 } 4697 4698 private void forceStopPackageLocked(final String packageName, int uid, String reason) { 4699 forceStopPackageLocked(packageName, UserHandle.getAppId(uid), false, 4700 false, true, false, false, UserHandle.getUserId(uid), reason); 4701 Intent intent = new Intent(Intent.ACTION_PACKAGE_RESTARTED, 4702 Uri.fromParts("package", packageName, null)); 4703 if (!mProcessesReady) { 4704 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4705 | Intent.FLAG_RECEIVER_FOREGROUND); 4706 } 4707 intent.putExtra(Intent.EXTRA_UID, uid); 4708 intent.putExtra(Intent.EXTRA_USER_HANDLE, UserHandle.getUserId(uid)); 4709 broadcastIntentLocked(null, null, intent, 4710 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 4711 false, false, 4712 MY_PID, Process.SYSTEM_UID, UserHandle.getUserId(uid)); 4713 } 4714 4715 private void forceStopUserLocked(int userId, String reason) { 4716 forceStopPackageLocked(null, -1, false, false, true, false, false, userId, reason); 4717 Intent intent = new Intent(Intent.ACTION_USER_STOPPED); 4718 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 4719 | Intent.FLAG_RECEIVER_FOREGROUND); 4720 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 4721 broadcastIntentLocked(null, null, intent, 4722 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 4723 false, false, 4724 MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 4725 } 4726 4727 private final boolean killPackageProcessesLocked(String packageName, int appId, 4728 int userId, int minOomAdj, boolean callerWillRestart, boolean allowRestart, 4729 boolean doit, boolean evenPersistent, String reason) { 4730 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 4731 4732 // Remove all processes this package may have touched: all with the 4733 // same UID (except for the system or root user), and all whose name 4734 // matches the package name. 4735 final String procNamePrefix = packageName != null ? (packageName + ":") : null; 4736 final int NP = mProcessNames.getMap().size(); 4737 for (int ip=0; ip<NP; ip++) { 4738 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 4739 final int NA = apps.size(); 4740 for (int ia=0; ia<NA; ia++) { 4741 ProcessRecord app = apps.valueAt(ia); 4742 if (app.persistent && !evenPersistent) { 4743 // we don't kill persistent processes 4744 continue; 4745 } 4746 if (app.removed) { 4747 if (doit) { 4748 procs.add(app); 4749 } 4750 continue; 4751 } 4752 4753 // Skip process if it doesn't meet our oom adj requirement. 4754 if (app.setAdj < minOomAdj) { 4755 continue; 4756 } 4757 4758 // If no package is specified, we call all processes under the 4759 // give user id. 4760 if (packageName == null) { 4761 if (app.userId != userId) { 4762 continue; 4763 } 4764 if (appId >= 0 && UserHandle.getAppId(app.uid) != appId) { 4765 continue; 4766 } 4767 // Package has been specified, we want to hit all processes 4768 // that match it. We need to qualify this by the processes 4769 // that are running under the specified app and user ID. 4770 } else { 4771 if (UserHandle.getAppId(app.uid) != appId) { 4772 continue; 4773 } 4774 if (userId != UserHandle.USER_ALL && app.userId != userId) { 4775 continue; 4776 } 4777 if (!app.pkgList.containsKey(packageName)) { 4778 continue; 4779 } 4780 } 4781 4782 // Process has passed all conditions, kill it! 4783 if (!doit) { 4784 return true; 4785 } 4786 app.removed = true; 4787 procs.add(app); 4788 } 4789 } 4790 4791 int N = procs.size(); 4792 for (int i=0; i<N; i++) { 4793 removeProcessLocked(procs.get(i), callerWillRestart, allowRestart, reason); 4794 } 4795 updateOomAdjLocked(); 4796 return N > 0; 4797 } 4798 4799 private final boolean forceStopPackageLocked(String name, int appId, 4800 boolean callerWillRestart, boolean purgeCache, boolean doit, 4801 boolean evenPersistent, boolean uninstalling, int userId, String reason) { 4802 int i; 4803 int N; 4804 4805 if (userId == UserHandle.USER_ALL && name == null) { 4806 Slog.w(TAG, "Can't force stop all processes of all users, that is insane!"); 4807 } 4808 4809 if (appId < 0 && name != null) { 4810 try { 4811 appId = UserHandle.getAppId( 4812 AppGlobals.getPackageManager().getPackageUid(name, 0)); 4813 } catch (RemoteException e) { 4814 } 4815 } 4816 4817 if (doit) { 4818 if (name != null) { 4819 Slog.i(TAG, "Force stopping " + name + " appid=" + appId 4820 + " user=" + userId + ": " + reason); 4821 } else { 4822 Slog.i(TAG, "Force stopping u" + userId + ": " + reason); 4823 } 4824 4825 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 4826 for (int ip=pmap.size()-1; ip>=0; ip--) { 4827 SparseArray<Long> ba = pmap.valueAt(ip); 4828 for (i=ba.size()-1; i>=0; i--) { 4829 boolean remove = false; 4830 final int entUid = ba.keyAt(i); 4831 if (name != null) { 4832 if (userId == UserHandle.USER_ALL) { 4833 if (UserHandle.getAppId(entUid) == appId) { 4834 remove = true; 4835 } 4836 } else { 4837 if (entUid == UserHandle.getUid(userId, appId)) { 4838 remove = true; 4839 } 4840 } 4841 } else if (UserHandle.getUserId(entUid) == userId) { 4842 remove = true; 4843 } 4844 if (remove) { 4845 ba.removeAt(i); 4846 } 4847 } 4848 if (ba.size() == 0) { 4849 pmap.removeAt(ip); 4850 } 4851 } 4852 } 4853 4854 boolean didSomething = killPackageProcessesLocked(name, appId, userId, 4855 -100, callerWillRestart, true, doit, evenPersistent, 4856 name == null ? ("stop user " + userId) : ("stop " + name)); 4857 4858 if (mStackSupervisor.forceStopPackageLocked(name, doit, evenPersistent, userId)) { 4859 if (!doit) { 4860 return true; 4861 } 4862 didSomething = true; 4863 } 4864 4865 if (mServices.forceStopLocked(name, userId, evenPersistent, doit)) { 4866 if (!doit) { 4867 return true; 4868 } 4869 didSomething = true; 4870 } 4871 4872 if (name == null) { 4873 // Remove all sticky broadcasts from this user. 4874 mStickyBroadcasts.remove(userId); 4875 } 4876 4877 ArrayList<ContentProviderRecord> providers = new ArrayList<ContentProviderRecord>(); 4878 if (mProviderMap.collectForceStopProviders(name, appId, doit, evenPersistent, 4879 userId, providers)) { 4880 if (!doit) { 4881 return true; 4882 } 4883 didSomething = true; 4884 } 4885 N = providers.size(); 4886 for (i=0; i<N; i++) { 4887 removeDyingProviderLocked(null, providers.get(i), true); 4888 } 4889 4890 // Remove transient permissions granted from/to this package/user 4891 removeUriPermissionsForPackageLocked(name, userId, false); 4892 4893 if (name == null || uninstalling) { 4894 // Remove pending intents. For now we only do this when force 4895 // stopping users, because we have some problems when doing this 4896 // for packages -- app widgets are not currently cleaned up for 4897 // such packages, so they can be left with bad pending intents. 4898 if (mIntentSenderRecords.size() > 0) { 4899 Iterator<WeakReference<PendingIntentRecord>> it 4900 = mIntentSenderRecords.values().iterator(); 4901 while (it.hasNext()) { 4902 WeakReference<PendingIntentRecord> wpir = it.next(); 4903 if (wpir == null) { 4904 it.remove(); 4905 continue; 4906 } 4907 PendingIntentRecord pir = wpir.get(); 4908 if (pir == null) { 4909 it.remove(); 4910 continue; 4911 } 4912 if (name == null) { 4913 // Stopping user, remove all objects for the user. 4914 if (pir.key.userId != userId) { 4915 // Not the same user, skip it. 4916 continue; 4917 } 4918 } else { 4919 if (UserHandle.getAppId(pir.uid) != appId) { 4920 // Different app id, skip it. 4921 continue; 4922 } 4923 if (userId != UserHandle.USER_ALL && pir.key.userId != userId) { 4924 // Different user, skip it. 4925 continue; 4926 } 4927 if (!pir.key.packageName.equals(name)) { 4928 // Different package, skip it. 4929 continue; 4930 } 4931 } 4932 if (!doit) { 4933 return true; 4934 } 4935 didSomething = true; 4936 it.remove(); 4937 pir.canceled = true; 4938 if (pir.key.activity != null) { 4939 pir.key.activity.pendingResults.remove(pir.ref); 4940 } 4941 } 4942 } 4943 } 4944 4945 if (doit) { 4946 if (purgeCache && name != null) { 4947 AttributeCache ac = AttributeCache.instance(); 4948 if (ac != null) { 4949 ac.removePackage(name); 4950 } 4951 } 4952 if (mBooted) { 4953 mStackSupervisor.resumeTopActivitiesLocked(); 4954 mStackSupervisor.scheduleIdleLocked(); 4955 } 4956 } 4957 4958 return didSomething; 4959 } 4960 4961 private final boolean removeProcessLocked(ProcessRecord app, 4962 boolean callerWillRestart, boolean allowRestart, String reason) { 4963 final String name = app.processName; 4964 final int uid = app.uid; 4965 if (DEBUG_PROCESSES) Slog.d( 4966 TAG, "Force removing proc " + app.toShortString() + " (" + name 4967 + "/" + uid + ")"); 4968 4969 mProcessNames.remove(name, uid); 4970 mIsolatedProcesses.remove(app.uid); 4971 if (mHeavyWeightProcess == app) { 4972 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 4973 mHeavyWeightProcess.userId, 0)); 4974 mHeavyWeightProcess = null; 4975 } 4976 boolean needRestart = false; 4977 if (app.pid > 0 && app.pid != MY_PID) { 4978 int pid = app.pid; 4979 synchronized (mPidsSelfLocked) { 4980 mPidsSelfLocked.remove(pid); 4981 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 4982 } 4983 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_PROC_FINISH, 4984 app.processName, app.info.uid); 4985 if (app.isolated) { 4986 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 4987 } 4988 killUnneededProcessLocked(app, reason); 4989 handleAppDiedLocked(app, true, allowRestart); 4990 removeLruProcessLocked(app); 4991 4992 if (app.persistent && !app.isolated) { 4993 if (!callerWillRestart) { 4994 addAppLocked(app.info, false); 4995 } else { 4996 needRestart = true; 4997 } 4998 } 4999 } else { 5000 mRemovedProcesses.add(app); 5001 } 5002 5003 return needRestart; 5004 } 5005 5006 private final void processStartTimedOutLocked(ProcessRecord app) { 5007 final int pid = app.pid; 5008 boolean gone = false; 5009 synchronized (mPidsSelfLocked) { 5010 ProcessRecord knownApp = mPidsSelfLocked.get(pid); 5011 if (knownApp != null && knownApp.thread == null) { 5012 mPidsSelfLocked.remove(pid); 5013 gone = true; 5014 } 5015 } 5016 5017 if (gone) { 5018 Slog.w(TAG, "Process " + app + " failed to attach"); 5019 EventLog.writeEvent(EventLogTags.AM_PROCESS_START_TIMEOUT, app.userId, 5020 pid, app.uid, app.processName); 5021 mProcessNames.remove(app.processName, app.uid); 5022 mIsolatedProcesses.remove(app.uid); 5023 if (mHeavyWeightProcess == app) { 5024 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 5025 mHeavyWeightProcess.userId, 0)); 5026 mHeavyWeightProcess = null; 5027 } 5028 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_PROC_FINISH, 5029 app.processName, app.info.uid); 5030 if (app.isolated) { 5031 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 5032 } 5033 // Take care of any launching providers waiting for this process. 5034 checkAppInLaunchingProvidersLocked(app, true); 5035 // Take care of any services that are waiting for the process. 5036 mServices.processStartTimedOutLocked(app); 5037 killUnneededProcessLocked(app, "start timeout"); 5038 if (mBackupTarget != null && mBackupTarget.app.pid == pid) { 5039 Slog.w(TAG, "Unattached app died before backup, skipping"); 5040 try { 5041 IBackupManager bm = IBackupManager.Stub.asInterface( 5042 ServiceManager.getService(Context.BACKUP_SERVICE)); 5043 bm.agentDisconnected(app.info.packageName); 5044 } catch (RemoteException e) { 5045 // Can't happen; the backup manager is local 5046 } 5047 } 5048 if (isPendingBroadcastProcessLocked(pid)) { 5049 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 5050 skipPendingBroadcastLocked(pid); 5051 } 5052 } else { 5053 Slog.w(TAG, "Spurious process start timeout - pid not known for " + app); 5054 } 5055 } 5056 5057 private final boolean attachApplicationLocked(IApplicationThread thread, 5058 int pid) { 5059 5060 // Find the application record that is being attached... either via 5061 // the pid if we are running in multiple processes, or just pull the 5062 // next app record if we are emulating process with anonymous threads. 5063 ProcessRecord app; 5064 if (pid != MY_PID && pid >= 0) { 5065 synchronized (mPidsSelfLocked) { 5066 app = mPidsSelfLocked.get(pid); 5067 } 5068 } else { 5069 app = null; 5070 } 5071 5072 if (app == null) { 5073 Slog.w(TAG, "No pending application record for pid " + pid 5074 + " (IApplicationThread " + thread + "); dropping process"); 5075 EventLog.writeEvent(EventLogTags.AM_DROP_PROCESS, pid); 5076 if (pid > 0 && pid != MY_PID) { 5077 Process.killProcessQuiet(pid); 5078 } else { 5079 try { 5080 thread.scheduleExit(); 5081 } catch (Exception e) { 5082 // Ignore exceptions. 5083 } 5084 } 5085 return false; 5086 } 5087 5088 // If this application record is still attached to a previous 5089 // process, clean it up now. 5090 if (app.thread != null) { 5091 handleAppDiedLocked(app, true, true); 5092 } 5093 5094 // Tell the process all about itself. 5095 5096 if (localLOGV) Slog.v( 5097 TAG, "Binding process pid " + pid + " to record " + app); 5098 5099 final String processName = app.processName; 5100 try { 5101 AppDeathRecipient adr = new AppDeathRecipient( 5102 app, pid, thread); 5103 thread.asBinder().linkToDeath(adr, 0); 5104 app.deathRecipient = adr; 5105 } catch (RemoteException e) { 5106 app.resetPackageList(mProcessStats); 5107 startProcessLocked(app, "link fail", processName); 5108 return false; 5109 } 5110 5111 EventLog.writeEvent(EventLogTags.AM_PROC_BOUND, app.userId, app.pid, app.processName); 5112 5113 app.makeActive(thread, mProcessStats); 5114 app.curAdj = app.setAdj = -100; 5115 app.curSchedGroup = app.setSchedGroup = Process.THREAD_GROUP_DEFAULT; 5116 app.forcingToForeground = null; 5117 updateProcessForegroundLocked(app, false, false); 5118 app.hasShownUi = false; 5119 app.debugging = false; 5120 app.cached = false; 5121 5122 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 5123 5124 boolean normalMode = mProcessesReady || isAllowedWhileBooting(app.info); 5125 List<ProviderInfo> providers = normalMode ? generateApplicationProvidersLocked(app) : null; 5126 5127 if (!normalMode) { 5128 Slog.i(TAG, "Launching preboot mode app: " + app); 5129 } 5130 5131 if (localLOGV) Slog.v( 5132 TAG, "New app record " + app 5133 + " thread=" + thread.asBinder() + " pid=" + pid); 5134 try { 5135 int testMode = IApplicationThread.DEBUG_OFF; 5136 if (mDebugApp != null && mDebugApp.equals(processName)) { 5137 testMode = mWaitForDebugger 5138 ? IApplicationThread.DEBUG_WAIT 5139 : IApplicationThread.DEBUG_ON; 5140 app.debugging = true; 5141 if (mDebugTransient) { 5142 mDebugApp = mOrigDebugApp; 5143 mWaitForDebugger = mOrigWaitForDebugger; 5144 } 5145 } 5146 String profileFile = app.instrumentationProfileFile; 5147 ParcelFileDescriptor profileFd = null; 5148 boolean profileAutoStop = false; 5149 if (mProfileApp != null && mProfileApp.equals(processName)) { 5150 mProfileProc = app; 5151 profileFile = mProfileFile; 5152 profileFd = mProfileFd; 5153 profileAutoStop = mAutoStopProfiler; 5154 } 5155 boolean enableOpenGlTrace = false; 5156 if (mOpenGlTraceApp != null && mOpenGlTraceApp.equals(processName)) { 5157 enableOpenGlTrace = true; 5158 mOpenGlTraceApp = null; 5159 } 5160 5161 // If the app is being launched for restore or full backup, set it up specially 5162 boolean isRestrictedBackupMode = false; 5163 if (mBackupTarget != null && mBackupAppName.equals(processName)) { 5164 isRestrictedBackupMode = (mBackupTarget.backupMode == BackupRecord.RESTORE) 5165 || (mBackupTarget.backupMode == BackupRecord.RESTORE_FULL) 5166 || (mBackupTarget.backupMode == BackupRecord.BACKUP_FULL); 5167 } 5168 5169 ensurePackageDexOpt(app.instrumentationInfo != null 5170 ? app.instrumentationInfo.packageName 5171 : app.info.packageName); 5172 if (app.instrumentationClass != null) { 5173 ensurePackageDexOpt(app.instrumentationClass.getPackageName()); 5174 } 5175 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Binding proc " 5176 + processName + " with config " + mConfiguration); 5177 ApplicationInfo appInfo = app.instrumentationInfo != null 5178 ? app.instrumentationInfo : app.info; 5179 app.compat = compatibilityInfoForPackageLocked(appInfo); 5180 if (profileFd != null) { 5181 profileFd = profileFd.dup(); 5182 } 5183 thread.bindApplication(processName, appInfo, providers, 5184 app.instrumentationClass, profileFile, profileFd, profileAutoStop, 5185 app.instrumentationArguments, app.instrumentationWatcher, 5186 app.instrumentationUiAutomationConnection, testMode, enableOpenGlTrace, 5187 isRestrictedBackupMode || !normalMode, app.persistent, 5188 new Configuration(mConfiguration), app.compat, getCommonServicesLocked(), 5189 mCoreSettingsObserver.getCoreSettingsLocked()); 5190 updateLruProcessLocked(app, false, null); 5191 app.lastRequestedGc = app.lastLowMemory = SystemClock.uptimeMillis(); 5192 } catch (Exception e) { 5193 // todo: Yikes! What should we do? For now we will try to 5194 // start another process, but that could easily get us in 5195 // an infinite loop of restarting processes... 5196 Slog.w(TAG, "Exception thrown during bind!", e); 5197 5198 app.resetPackageList(mProcessStats); 5199 app.unlinkDeathRecipient(); 5200 startProcessLocked(app, "bind fail", processName); 5201 return false; 5202 } 5203 5204 // Remove this record from the list of starting applications. 5205 mPersistentStartingProcesses.remove(app); 5206 if (DEBUG_PROCESSES && mProcessesOnHold.contains(app)) Slog.v(TAG, 5207 "Attach application locked removing on hold: " + app); 5208 mProcessesOnHold.remove(app); 5209 5210 boolean badApp = false; 5211 boolean didSomething = false; 5212 5213 // See if the top visible activity is waiting to run in this process... 5214 if (normalMode) { 5215 try { 5216 if (mStackSupervisor.attachApplicationLocked(app)) { 5217 didSomething = true; 5218 } 5219 } catch (Exception e) { 5220 badApp = true; 5221 } 5222 } 5223 5224 // Find any services that should be running in this process... 5225 if (!badApp) { 5226 try { 5227 didSomething |= mServices.attachApplicationLocked(app, processName); 5228 } catch (Exception e) { 5229 badApp = true; 5230 } 5231 } 5232 5233 // Check if a next-broadcast receiver is in this process... 5234 if (!badApp && isPendingBroadcastProcessLocked(pid)) { 5235 try { 5236 didSomething |= sendPendingBroadcastsLocked(app); 5237 } catch (Exception e) { 5238 // If the app died trying to launch the receiver we declare it 'bad' 5239 badApp = true; 5240 } 5241 } 5242 5243 // Check whether the next backup agent is in this process... 5244 if (!badApp && mBackupTarget != null && mBackupTarget.appInfo.uid == app.uid) { 5245 if (DEBUG_BACKUP) Slog.v(TAG, "New app is backup target, launching agent for " + app); 5246 ensurePackageDexOpt(mBackupTarget.appInfo.packageName); 5247 try { 5248 thread.scheduleCreateBackupAgent(mBackupTarget.appInfo, 5249 compatibilityInfoForPackageLocked(mBackupTarget.appInfo), 5250 mBackupTarget.backupMode); 5251 } catch (Exception e) { 5252 Slog.w(TAG, "Exception scheduling backup agent creation: "); 5253 e.printStackTrace(); 5254 } 5255 } 5256 5257 if (badApp) { 5258 // todo: Also need to kill application to deal with all 5259 // kinds of exceptions. 5260 handleAppDiedLocked(app, false, true); 5261 return false; 5262 } 5263 5264 if (!didSomething) { 5265 updateOomAdjLocked(); 5266 } 5267 5268 return true; 5269 } 5270 5271 @Override 5272 public final void attachApplication(IApplicationThread thread) { 5273 synchronized (this) { 5274 int callingPid = Binder.getCallingPid(); 5275 final long origId = Binder.clearCallingIdentity(); 5276 attachApplicationLocked(thread, callingPid); 5277 Binder.restoreCallingIdentity(origId); 5278 } 5279 } 5280 5281 @Override 5282 public final void activityIdle(IBinder token, Configuration config, boolean stopProfiling) { 5283 final long origId = Binder.clearCallingIdentity(); 5284 synchronized (this) { 5285 ActivityStack stack = ActivityRecord.getStackLocked(token); 5286 if (stack != null) { 5287 ActivityRecord r = 5288 mStackSupervisor.activityIdleInternalLocked(token, false, config); 5289 if (stopProfiling) { 5290 if ((mProfileProc == r.app) && (mProfileFd != null)) { 5291 try { 5292 mProfileFd.close(); 5293 } catch (IOException e) { 5294 } 5295 clearProfilerLocked(); 5296 } 5297 } 5298 } 5299 } 5300 Binder.restoreCallingIdentity(origId); 5301 } 5302 5303 void enableScreenAfterBoot() { 5304 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_ENABLE_SCREEN, 5305 SystemClock.uptimeMillis()); 5306 mWindowManager.enableScreenAfterBoot(); 5307 5308 synchronized (this) { 5309 updateEventDispatchingLocked(); 5310 } 5311 } 5312 5313 @Override 5314 public void showBootMessage(final CharSequence msg, final boolean always) { 5315 enforceNotIsolatedCaller("showBootMessage"); 5316 mWindowManager.showBootMessage(msg, always); 5317 } 5318 5319 @Override 5320 public void dismissKeyguardOnNextActivity() { 5321 enforceNotIsolatedCaller("dismissKeyguardOnNextActivity"); 5322 final long token = Binder.clearCallingIdentity(); 5323 try { 5324 synchronized (this) { 5325 if (DEBUG_LOCKSCREEN) logLockScreen(""); 5326 if (mLockScreenShown) { 5327 mLockScreenShown = false; 5328 comeOutOfSleepIfNeededLocked(); 5329 } 5330 mStackSupervisor.setDismissKeyguard(true); 5331 } 5332 } finally { 5333 Binder.restoreCallingIdentity(token); 5334 } 5335 } 5336 5337 final void finishBooting() { 5338 // Register receivers to handle package update events 5339 mPackageMonitor.register(mContext, Looper.getMainLooper(), false); 5340 5341 synchronized (this) { 5342 // Ensure that any processes we had put on hold are now started 5343 // up. 5344 final int NP = mProcessesOnHold.size(); 5345 if (NP > 0) { 5346 ArrayList<ProcessRecord> procs = 5347 new ArrayList<ProcessRecord>(mProcessesOnHold); 5348 for (int ip=0; ip<NP; ip++) { 5349 if (DEBUG_PROCESSES) Slog.v(TAG, "Starting process on hold: " 5350 + procs.get(ip)); 5351 startProcessLocked(procs.get(ip), "on-hold", null); 5352 } 5353 } 5354 5355 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 5356 // Start looking for apps that are abusing wake locks. 5357 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 5358 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 5359 // Tell anyone interested that we are done booting! 5360 SystemProperties.set("sys.boot_completed", "1"); 5361 SystemProperties.set("dev.bootcomplete", "1"); 5362 for (int i=0; i<mStartedUsers.size(); i++) { 5363 UserStartedState uss = mStartedUsers.valueAt(i); 5364 if (uss.mState == UserStartedState.STATE_BOOTING) { 5365 uss.mState = UserStartedState.STATE_RUNNING; 5366 final int userId = mStartedUsers.keyAt(i); 5367 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 5368 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 5369 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 5370 broadcastIntentLocked(null, null, intent, null, 5371 new IIntentReceiver.Stub() { 5372 @Override 5373 public void performReceive(Intent intent, int resultCode, 5374 String data, Bundle extras, boolean ordered, 5375 boolean sticky, int sendingUser) { 5376 synchronized (ActivityManagerService.this) { 5377 requestPssAllProcsLocked(SystemClock.uptimeMillis(), 5378 true, false); 5379 } 5380 } 5381 }, 5382 0, null, null, 5383 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, 5384 AppOpsManager.OP_NONE, true, false, MY_PID, Process.SYSTEM_UID, 5385 userId); 5386 } 5387 } 5388 scheduleStartProfilesLocked(); 5389 } 5390 } 5391 } 5392 5393 final void ensureBootCompleted() { 5394 boolean booting; 5395 boolean enableScreen; 5396 synchronized (this) { 5397 booting = mBooting; 5398 mBooting = false; 5399 enableScreen = !mBooted; 5400 mBooted = true; 5401 } 5402 5403 if (booting) { 5404 finishBooting(); 5405 } 5406 5407 if (enableScreen) { 5408 enableScreenAfterBoot(); 5409 } 5410 } 5411 5412 @Override 5413 public final void activityResumed(IBinder token) { 5414 final long origId = Binder.clearCallingIdentity(); 5415 synchronized(this) { 5416 ActivityStack stack = ActivityRecord.getStackLocked(token); 5417 if (stack != null) { 5418 ActivityRecord.activityResumedLocked(token); 5419 } 5420 } 5421 Binder.restoreCallingIdentity(origId); 5422 } 5423 5424 @Override 5425 public final void activityPaused(IBinder token) { 5426 final long origId = Binder.clearCallingIdentity(); 5427 synchronized(this) { 5428 ActivityStack stack = ActivityRecord.getStackLocked(token); 5429 if (stack != null) { 5430 stack.activityPausedLocked(token, false); 5431 } 5432 } 5433 Binder.restoreCallingIdentity(origId); 5434 } 5435 5436 @Override 5437 public final void activityStopped(IBinder token, Bundle icicle, Bitmap thumbnail, 5438 CharSequence description) { 5439 if (localLOGV) Slog.v( 5440 TAG, "Activity stopped: token=" + token); 5441 5442 // Refuse possible leaked file descriptors 5443 if (icicle != null && icicle.hasFileDescriptors()) { 5444 throw new IllegalArgumentException("File descriptors passed in Bundle"); 5445 } 5446 5447 final long origId = Binder.clearCallingIdentity(); 5448 5449 synchronized (this) { 5450 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5451 if (r != null) { 5452 r.task.stack.activityStoppedLocked(r, icicle, thumbnail, description); 5453 } 5454 } 5455 5456 trimApplications(); 5457 5458 Binder.restoreCallingIdentity(origId); 5459 } 5460 5461 @Override 5462 public final void activityDestroyed(IBinder token) { 5463 if (DEBUG_SWITCH) Slog.v(TAG, "ACTIVITY DESTROYED: " + token); 5464 synchronized (this) { 5465 ActivityStack stack = ActivityRecord.getStackLocked(token); 5466 if (stack != null) { 5467 stack.activityDestroyedLocked(token); 5468 } 5469 } 5470 } 5471 5472 @Override 5473 public String getCallingPackage(IBinder token) { 5474 synchronized (this) { 5475 ActivityRecord r = getCallingRecordLocked(token); 5476 return r != null ? r.info.packageName : null; 5477 } 5478 } 5479 5480 @Override 5481 public ComponentName getCallingActivity(IBinder token) { 5482 synchronized (this) { 5483 ActivityRecord r = getCallingRecordLocked(token); 5484 return r != null ? r.intent.getComponent() : null; 5485 } 5486 } 5487 5488 private ActivityRecord getCallingRecordLocked(IBinder token) { 5489 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5490 if (r == null) { 5491 return null; 5492 } 5493 return r.resultTo; 5494 } 5495 5496 @Override 5497 public ComponentName getActivityClassForToken(IBinder token) { 5498 synchronized(this) { 5499 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5500 if (r == null) { 5501 return null; 5502 } 5503 return r.intent.getComponent(); 5504 } 5505 } 5506 5507 @Override 5508 public String getPackageForToken(IBinder token) { 5509 synchronized(this) { 5510 ActivityRecord r = ActivityRecord.isInStackLocked(token); 5511 if (r == null) { 5512 return null; 5513 } 5514 return r.packageName; 5515 } 5516 } 5517 5518 @Override 5519 public IIntentSender getIntentSender(int type, 5520 String packageName, IBinder token, String resultWho, 5521 int requestCode, Intent[] intents, String[] resolvedTypes, 5522 int flags, Bundle options, int userId) { 5523 enforceNotIsolatedCaller("getIntentSender"); 5524 // Refuse possible leaked file descriptors 5525 if (intents != null) { 5526 if (intents.length < 1) { 5527 throw new IllegalArgumentException("Intents array length must be >= 1"); 5528 } 5529 for (int i=0; i<intents.length; i++) { 5530 Intent intent = intents[i]; 5531 if (intent != null) { 5532 if (intent.hasFileDescriptors()) { 5533 throw new IllegalArgumentException("File descriptors passed in Intent"); 5534 } 5535 if (type == ActivityManager.INTENT_SENDER_BROADCAST && 5536 (intent.getFlags()&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 5537 throw new IllegalArgumentException( 5538 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 5539 } 5540 intents[i] = new Intent(intent); 5541 } 5542 } 5543 if (resolvedTypes != null && resolvedTypes.length != intents.length) { 5544 throw new IllegalArgumentException( 5545 "Intent array length does not match resolvedTypes length"); 5546 } 5547 } 5548 if (options != null) { 5549 if (options.hasFileDescriptors()) { 5550 throw new IllegalArgumentException("File descriptors passed in options"); 5551 } 5552 } 5553 5554 synchronized(this) { 5555 int callingUid = Binder.getCallingUid(); 5556 int origUserId = userId; 5557 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 5558 type == ActivityManager.INTENT_SENDER_BROADCAST, false, 5559 "getIntentSender", null); 5560 if (origUserId == UserHandle.USER_CURRENT) { 5561 // We don't want to evaluate this until the pending intent is 5562 // actually executed. However, we do want to always do the 5563 // security checking for it above. 5564 userId = UserHandle.USER_CURRENT; 5565 } 5566 try { 5567 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 5568 int uid = AppGlobals.getPackageManager() 5569 .getPackageUid(packageName, UserHandle.getUserId(callingUid)); 5570 if (!UserHandle.isSameApp(callingUid, uid)) { 5571 String msg = "Permission Denial: getIntentSender() from pid=" 5572 + Binder.getCallingPid() 5573 + ", uid=" + Binder.getCallingUid() 5574 + ", (need uid=" + uid + ")" 5575 + " is not allowed to send as package " + packageName; 5576 Slog.w(TAG, msg); 5577 throw new SecurityException(msg); 5578 } 5579 } 5580 5581 return getIntentSenderLocked(type, packageName, callingUid, userId, 5582 token, resultWho, requestCode, intents, resolvedTypes, flags, options); 5583 5584 } catch (RemoteException e) { 5585 throw new SecurityException(e); 5586 } 5587 } 5588 } 5589 5590 IIntentSender getIntentSenderLocked(int type, String packageName, 5591 int callingUid, int userId, IBinder token, String resultWho, 5592 int requestCode, Intent[] intents, String[] resolvedTypes, int flags, 5593 Bundle options) { 5594 if (DEBUG_MU) 5595 Slog.v(TAG_MU, "getIntentSenderLocked(): uid=" + callingUid); 5596 ActivityRecord activity = null; 5597 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 5598 activity = ActivityRecord.isInStackLocked(token); 5599 if (activity == null) { 5600 return null; 5601 } 5602 if (activity.finishing) { 5603 return null; 5604 } 5605 } 5606 5607 final boolean noCreate = (flags&PendingIntent.FLAG_NO_CREATE) != 0; 5608 final boolean cancelCurrent = (flags&PendingIntent.FLAG_CANCEL_CURRENT) != 0; 5609 final boolean updateCurrent = (flags&PendingIntent.FLAG_UPDATE_CURRENT) != 0; 5610 flags &= ~(PendingIntent.FLAG_NO_CREATE|PendingIntent.FLAG_CANCEL_CURRENT 5611 |PendingIntent.FLAG_UPDATE_CURRENT); 5612 5613 PendingIntentRecord.Key key = new PendingIntentRecord.Key( 5614 type, packageName, activity, resultWho, 5615 requestCode, intents, resolvedTypes, flags, options, userId); 5616 WeakReference<PendingIntentRecord> ref; 5617 ref = mIntentSenderRecords.get(key); 5618 PendingIntentRecord rec = ref != null ? ref.get() : null; 5619 if (rec != null) { 5620 if (!cancelCurrent) { 5621 if (updateCurrent) { 5622 if (rec.key.requestIntent != null) { 5623 rec.key.requestIntent.replaceExtras(intents != null ? 5624 intents[intents.length - 1] : null); 5625 } 5626 if (intents != null) { 5627 intents[intents.length-1] = rec.key.requestIntent; 5628 rec.key.allIntents = intents; 5629 rec.key.allResolvedTypes = resolvedTypes; 5630 } else { 5631 rec.key.allIntents = null; 5632 rec.key.allResolvedTypes = null; 5633 } 5634 } 5635 return rec; 5636 } 5637 rec.canceled = true; 5638 mIntentSenderRecords.remove(key); 5639 } 5640 if (noCreate) { 5641 return rec; 5642 } 5643 rec = new PendingIntentRecord(this, key, callingUid); 5644 mIntentSenderRecords.put(key, rec.ref); 5645 if (type == ActivityManager.INTENT_SENDER_ACTIVITY_RESULT) { 5646 if (activity.pendingResults == null) { 5647 activity.pendingResults 5648 = new HashSet<WeakReference<PendingIntentRecord>>(); 5649 } 5650 activity.pendingResults.add(rec.ref); 5651 } 5652 return rec; 5653 } 5654 5655 @Override 5656 public void cancelIntentSender(IIntentSender sender) { 5657 if (!(sender instanceof PendingIntentRecord)) { 5658 return; 5659 } 5660 synchronized(this) { 5661 PendingIntentRecord rec = (PendingIntentRecord)sender; 5662 try { 5663 int uid = AppGlobals.getPackageManager() 5664 .getPackageUid(rec.key.packageName, UserHandle.getCallingUserId()); 5665 if (!UserHandle.isSameApp(uid, Binder.getCallingUid())) { 5666 String msg = "Permission Denial: cancelIntentSender() from pid=" 5667 + Binder.getCallingPid() 5668 + ", uid=" + Binder.getCallingUid() 5669 + " is not allowed to cancel packges " 5670 + rec.key.packageName; 5671 Slog.w(TAG, msg); 5672 throw new SecurityException(msg); 5673 } 5674 } catch (RemoteException e) { 5675 throw new SecurityException(e); 5676 } 5677 cancelIntentSenderLocked(rec, true); 5678 } 5679 } 5680 5681 void cancelIntentSenderLocked(PendingIntentRecord rec, boolean cleanActivity) { 5682 rec.canceled = true; 5683 mIntentSenderRecords.remove(rec.key); 5684 if (cleanActivity && rec.key.activity != null) { 5685 rec.key.activity.pendingResults.remove(rec.ref); 5686 } 5687 } 5688 5689 @Override 5690 public String getPackageForIntentSender(IIntentSender pendingResult) { 5691 if (!(pendingResult instanceof PendingIntentRecord)) { 5692 return null; 5693 } 5694 try { 5695 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5696 return res.key.packageName; 5697 } catch (ClassCastException e) { 5698 } 5699 return null; 5700 } 5701 5702 @Override 5703 public int getUidForIntentSender(IIntentSender sender) { 5704 if (sender instanceof PendingIntentRecord) { 5705 try { 5706 PendingIntentRecord res = (PendingIntentRecord)sender; 5707 return res.uid; 5708 } catch (ClassCastException e) { 5709 } 5710 } 5711 return -1; 5712 } 5713 5714 @Override 5715 public boolean isIntentSenderTargetedToPackage(IIntentSender pendingResult) { 5716 if (!(pendingResult instanceof PendingIntentRecord)) { 5717 return false; 5718 } 5719 try { 5720 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5721 if (res.key.allIntents == null) { 5722 return false; 5723 } 5724 for (int i=0; i<res.key.allIntents.length; i++) { 5725 Intent intent = res.key.allIntents[i]; 5726 if (intent.getPackage() != null && intent.getComponent() != null) { 5727 return false; 5728 } 5729 } 5730 return true; 5731 } catch (ClassCastException e) { 5732 } 5733 return false; 5734 } 5735 5736 @Override 5737 public boolean isIntentSenderAnActivity(IIntentSender pendingResult) { 5738 if (!(pendingResult instanceof PendingIntentRecord)) { 5739 return false; 5740 } 5741 try { 5742 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5743 if (res.key.type == ActivityManager.INTENT_SENDER_ACTIVITY) { 5744 return true; 5745 } 5746 return false; 5747 } catch (ClassCastException e) { 5748 } 5749 return false; 5750 } 5751 5752 @Override 5753 public Intent getIntentForIntentSender(IIntentSender pendingResult) { 5754 if (!(pendingResult instanceof PendingIntentRecord)) { 5755 return null; 5756 } 5757 try { 5758 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5759 return res.key.requestIntent != null ? new Intent(res.key.requestIntent) : null; 5760 } catch (ClassCastException e) { 5761 } 5762 return null; 5763 } 5764 5765 @Override 5766 public String getTagForIntentSender(IIntentSender pendingResult, String prefix) { 5767 if (!(pendingResult instanceof PendingIntentRecord)) { 5768 return null; 5769 } 5770 try { 5771 PendingIntentRecord res = (PendingIntentRecord)pendingResult; 5772 Intent intent = res.key.requestIntent; 5773 if (intent != null) { 5774 if (res.lastTag != null && res.lastTagPrefix == prefix && (res.lastTagPrefix == null 5775 || res.lastTagPrefix.equals(prefix))) { 5776 return res.lastTag; 5777 } 5778 res.lastTagPrefix = prefix; 5779 StringBuilder sb = new StringBuilder(128); 5780 if (prefix != null) { 5781 sb.append(prefix); 5782 } 5783 if (intent.getAction() != null) { 5784 sb.append(intent.getAction()); 5785 } else if (intent.getComponent() != null) { 5786 intent.getComponent().appendShortString(sb); 5787 } else { 5788 sb.append("?"); 5789 } 5790 return res.lastTag = sb.toString(); 5791 } 5792 } catch (ClassCastException e) { 5793 } 5794 return null; 5795 } 5796 5797 @Override 5798 public void setProcessLimit(int max) { 5799 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 5800 "setProcessLimit()"); 5801 synchronized (this) { 5802 mProcessLimit = max < 0 ? ProcessList.MAX_CACHED_APPS : max; 5803 mProcessLimitOverride = max; 5804 } 5805 trimApplications(); 5806 } 5807 5808 @Override 5809 public int getProcessLimit() { 5810 synchronized (this) { 5811 return mProcessLimitOverride; 5812 } 5813 } 5814 5815 void foregroundTokenDied(ForegroundToken token) { 5816 synchronized (ActivityManagerService.this) { 5817 synchronized (mPidsSelfLocked) { 5818 ForegroundToken cur 5819 = mForegroundProcesses.get(token.pid); 5820 if (cur != token) { 5821 return; 5822 } 5823 mForegroundProcesses.remove(token.pid); 5824 ProcessRecord pr = mPidsSelfLocked.get(token.pid); 5825 if (pr == null) { 5826 return; 5827 } 5828 pr.forcingToForeground = null; 5829 updateProcessForegroundLocked(pr, false, false); 5830 } 5831 updateOomAdjLocked(); 5832 } 5833 } 5834 5835 @Override 5836 public void setProcessForeground(IBinder token, int pid, boolean isForeground) { 5837 enforceCallingPermission(android.Manifest.permission.SET_PROCESS_LIMIT, 5838 "setProcessForeground()"); 5839 synchronized(this) { 5840 boolean changed = false; 5841 5842 synchronized (mPidsSelfLocked) { 5843 ProcessRecord pr = mPidsSelfLocked.get(pid); 5844 if (pr == null && isForeground) { 5845 Slog.w(TAG, "setProcessForeground called on unknown pid: " + pid); 5846 return; 5847 } 5848 ForegroundToken oldToken = mForegroundProcesses.get(pid); 5849 if (oldToken != null) { 5850 oldToken.token.unlinkToDeath(oldToken, 0); 5851 mForegroundProcesses.remove(pid); 5852 if (pr != null) { 5853 pr.forcingToForeground = null; 5854 } 5855 changed = true; 5856 } 5857 if (isForeground && token != null) { 5858 ForegroundToken newToken = new ForegroundToken() { 5859 @Override 5860 public void binderDied() { 5861 foregroundTokenDied(this); 5862 } 5863 }; 5864 newToken.pid = pid; 5865 newToken.token = token; 5866 try { 5867 token.linkToDeath(newToken, 0); 5868 mForegroundProcesses.put(pid, newToken); 5869 pr.forcingToForeground = token; 5870 changed = true; 5871 } catch (RemoteException e) { 5872 // If the process died while doing this, we will later 5873 // do the cleanup with the process death link. 5874 } 5875 } 5876 } 5877 5878 if (changed) { 5879 updateOomAdjLocked(); 5880 } 5881 } 5882 } 5883 5884 // ========================================================= 5885 // PERMISSIONS 5886 // ========================================================= 5887 5888 static class PermissionController extends IPermissionController.Stub { 5889 ActivityManagerService mActivityManagerService; 5890 PermissionController(ActivityManagerService activityManagerService) { 5891 mActivityManagerService = activityManagerService; 5892 } 5893 5894 @Override 5895 public boolean checkPermission(String permission, int pid, int uid) { 5896 return mActivityManagerService.checkPermission(permission, pid, 5897 uid) == PackageManager.PERMISSION_GRANTED; 5898 } 5899 } 5900 5901 class IntentFirewallInterface implements IntentFirewall.AMSInterface { 5902 @Override 5903 public int checkComponentPermission(String permission, int pid, int uid, 5904 int owningUid, boolean exported) { 5905 return ActivityManagerService.this.checkComponentPermission(permission, pid, uid, 5906 owningUid, exported); 5907 } 5908 5909 @Override 5910 public Object getAMSLock() { 5911 return ActivityManagerService.this; 5912 } 5913 } 5914 5915 /** 5916 * This can be called with or without the global lock held. 5917 */ 5918 int checkComponentPermission(String permission, int pid, int uid, 5919 int owningUid, boolean exported) { 5920 // We might be performing an operation on behalf of an indirect binder 5921 // invocation, e.g. via {@link #openContentUri}. Check and adjust the 5922 // client identity accordingly before proceeding. 5923 Identity tlsIdentity = sCallerIdentity.get(); 5924 if (tlsIdentity != null) { 5925 Slog.d(TAG, "checkComponentPermission() adjusting {pid,uid} to {" 5926 + tlsIdentity.pid + "," + tlsIdentity.uid + "}"); 5927 uid = tlsIdentity.uid; 5928 pid = tlsIdentity.pid; 5929 } 5930 5931 if (pid == MY_PID) { 5932 return PackageManager.PERMISSION_GRANTED; 5933 } 5934 5935 return ActivityManager.checkComponentPermission(permission, uid, 5936 owningUid, exported); 5937 } 5938 5939 /** 5940 * As the only public entry point for permissions checking, this method 5941 * can enforce the semantic that requesting a check on a null global 5942 * permission is automatically denied. (Internally a null permission 5943 * string is used when calling {@link #checkComponentPermission} in cases 5944 * when only uid-based security is needed.) 5945 * 5946 * This can be called with or without the global lock held. 5947 */ 5948 @Override 5949 public int checkPermission(String permission, int pid, int uid) { 5950 if (permission == null) { 5951 return PackageManager.PERMISSION_DENIED; 5952 } 5953 return checkComponentPermission(permission, pid, UserHandle.getAppId(uid), -1, true); 5954 } 5955 5956 /** 5957 * Binder IPC calls go through the public entry point. 5958 * This can be called with or without the global lock held. 5959 */ 5960 int checkCallingPermission(String permission) { 5961 return checkPermission(permission, 5962 Binder.getCallingPid(), 5963 UserHandle.getAppId(Binder.getCallingUid())); 5964 } 5965 5966 /** 5967 * This can be called with or without the global lock held. 5968 */ 5969 void enforceCallingPermission(String permission, String func) { 5970 if (checkCallingPermission(permission) 5971 == PackageManager.PERMISSION_GRANTED) { 5972 return; 5973 } 5974 5975 String msg = "Permission Denial: " + func + " from pid=" 5976 + Binder.getCallingPid() 5977 + ", uid=" + Binder.getCallingUid() 5978 + " requires " + permission; 5979 Slog.w(TAG, msg); 5980 throw new SecurityException(msg); 5981 } 5982 5983 /** 5984 * Determine if UID is holding permissions required to access {@link Uri} in 5985 * the given {@link ProviderInfo}. Final permission checking is always done 5986 * in {@link ContentProvider}. 5987 */ 5988 private final boolean checkHoldingPermissionsLocked( 5989 IPackageManager pm, ProviderInfo pi, Uri uri, int uid, final int modeFlags) { 5990 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 5991 "checkHoldingPermissionsLocked: uri=" + uri + " uid=" + uid); 5992 5993 if (pi.applicationInfo.uid == uid) { 5994 return true; 5995 } else if (!pi.exported) { 5996 return false; 5997 } 5998 5999 boolean readMet = (modeFlags & Intent.FLAG_GRANT_READ_URI_PERMISSION) == 0; 6000 boolean writeMet = (modeFlags & Intent.FLAG_GRANT_WRITE_URI_PERMISSION) == 0; 6001 try { 6002 // check if target holds top-level <provider> permissions 6003 if (!readMet && pi.readPermission != null 6004 && (pm.checkUidPermission(pi.readPermission, uid) == PERMISSION_GRANTED)) { 6005 readMet = true; 6006 } 6007 if (!writeMet && pi.writePermission != null 6008 && (pm.checkUidPermission(pi.writePermission, uid) == PERMISSION_GRANTED)) { 6009 writeMet = true; 6010 } 6011 6012 // track if unprotected read/write is allowed; any denied 6013 // <path-permission> below removes this ability 6014 boolean allowDefaultRead = pi.readPermission == null; 6015 boolean allowDefaultWrite = pi.writePermission == null; 6016 6017 // check if target holds any <path-permission> that match uri 6018 final PathPermission[] pps = pi.pathPermissions; 6019 if (pps != null) { 6020 final String path = uri.getPath(); 6021 int i = pps.length; 6022 while (i > 0 && (!readMet || !writeMet)) { 6023 i--; 6024 PathPermission pp = pps[i]; 6025 if (pp.match(path)) { 6026 if (!readMet) { 6027 final String pprperm = pp.getReadPermission(); 6028 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking read perm for " 6029 + pprperm + " for " + pp.getPath() 6030 + ": match=" + pp.match(path) 6031 + " check=" + pm.checkUidPermission(pprperm, uid)); 6032 if (pprperm != null) { 6033 if (pm.checkUidPermission(pprperm, uid) == PERMISSION_GRANTED) { 6034 readMet = true; 6035 } else { 6036 allowDefaultRead = false; 6037 } 6038 } 6039 } 6040 if (!writeMet) { 6041 final String ppwperm = pp.getWritePermission(); 6042 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Checking write perm " 6043 + ppwperm + " for " + pp.getPath() 6044 + ": match=" + pp.match(path) 6045 + " check=" + pm.checkUidPermission(ppwperm, uid)); 6046 if (ppwperm != null) { 6047 if (pm.checkUidPermission(ppwperm, uid) == PERMISSION_GRANTED) { 6048 writeMet = true; 6049 } else { 6050 allowDefaultWrite = false; 6051 } 6052 } 6053 } 6054 } 6055 } 6056 } 6057 6058 // grant unprotected <provider> read/write, if not blocked by 6059 // <path-permission> above 6060 if (allowDefaultRead) readMet = true; 6061 if (allowDefaultWrite) writeMet = true; 6062 6063 } catch (RemoteException e) { 6064 return false; 6065 } 6066 6067 return readMet && writeMet; 6068 } 6069 6070 private ProviderInfo getProviderInfoLocked(String authority, int userHandle) { 6071 ProviderInfo pi = null; 6072 ContentProviderRecord cpr = mProviderMap.getProviderByName(authority, userHandle); 6073 if (cpr != null) { 6074 pi = cpr.info; 6075 } else { 6076 try { 6077 pi = AppGlobals.getPackageManager().resolveContentProvider( 6078 authority, PackageManager.GET_URI_PERMISSION_PATTERNS, userHandle); 6079 } catch (RemoteException ex) { 6080 } 6081 } 6082 return pi; 6083 } 6084 6085 private UriPermission findUriPermissionLocked(int targetUid, GrantUri uri) { 6086 final ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6087 if (targetUris != null) { 6088 return targetUris.get(uri); 6089 } 6090 return null; 6091 } 6092 6093 private UriPermission findOrCreateUriPermissionLocked(String sourcePkg, 6094 String targetPkg, int targetUid, GrantUri uri) { 6095 ArrayMap<GrantUri, UriPermission> targetUris = mGrantedUriPermissions.get(targetUid); 6096 if (targetUris == null) { 6097 targetUris = Maps.newArrayMap(); 6098 mGrantedUriPermissions.put(targetUid, targetUris); 6099 } 6100 6101 UriPermission perm = targetUris.get(uri); 6102 if (perm == null) { 6103 perm = new UriPermission(sourcePkg, targetPkg, targetUid, uri); 6104 targetUris.put(uri, perm); 6105 } 6106 6107 return perm; 6108 } 6109 6110 private final boolean checkUriPermissionLocked(Uri uri, int uid, final int modeFlags) { 6111 final boolean persistable = (modeFlags & Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION) != 0; 6112 final int minStrength = persistable ? UriPermission.STRENGTH_PERSISTABLE 6113 : UriPermission.STRENGTH_OWNED; 6114 6115 // Root gets to do everything. 6116 if (uid == 0) { 6117 return true; 6118 } 6119 6120 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 6121 if (perms == null) return false; 6122 6123 // First look for exact match 6124 final UriPermission exactPerm = perms.get(new GrantUri(uri, false)); 6125 if (exactPerm != null && exactPerm.getStrength(modeFlags) >= minStrength) { 6126 return true; 6127 } 6128 6129 // No exact match, look for prefixes 6130 final int N = perms.size(); 6131 for (int i = 0; i < N; i++) { 6132 final UriPermission perm = perms.valueAt(i); 6133 if (perm.uri.prefix && uri.isPathPrefixMatch(perm.uri.uri) 6134 && perm.getStrength(modeFlags) >= minStrength) { 6135 return true; 6136 } 6137 } 6138 6139 return false; 6140 } 6141 6142 @Override 6143 public int checkUriPermission(Uri uri, int pid, int uid, final int modeFlags) { 6144 enforceNotIsolatedCaller("checkUriPermission"); 6145 6146 // Another redirected-binder-call permissions check as in 6147 // {@link checkComponentPermission}. 6148 Identity tlsIdentity = sCallerIdentity.get(); 6149 if (tlsIdentity != null) { 6150 uid = tlsIdentity.uid; 6151 pid = tlsIdentity.pid; 6152 } 6153 6154 // Our own process gets to do everything. 6155 if (pid == MY_PID) { 6156 return PackageManager.PERMISSION_GRANTED; 6157 } 6158 synchronized (this) { 6159 return checkUriPermissionLocked(uri, uid, modeFlags) 6160 ? PackageManager.PERMISSION_GRANTED 6161 : PackageManager.PERMISSION_DENIED; 6162 } 6163 } 6164 6165 /** 6166 * Check if the targetPkg can be granted permission to access uri by 6167 * the callingUid using the given modeFlags. Throws a security exception 6168 * if callingUid is not allowed to do this. Returns the uid of the target 6169 * if the URI permission grant should be performed; returns -1 if it is not 6170 * needed (for example targetPkg already has permission to access the URI). 6171 * If you already know the uid of the target, you can supply it in 6172 * lastTargetUid else set that to -1. 6173 */ 6174 int checkGrantUriPermissionLocked(int callingUid, String targetPkg, 6175 Uri uri, final int modeFlags, int lastTargetUid) { 6176 if (!Intent.isAccessUriMode(modeFlags)) { 6177 return -1; 6178 } 6179 6180 if (targetPkg != null) { 6181 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6182 "Checking grant " + targetPkg + " permission to " + uri); 6183 } 6184 6185 final IPackageManager pm = AppGlobals.getPackageManager(); 6186 6187 // If this is not a content: uri, we can't do anything with it. 6188 if (!ContentResolver.SCHEME_CONTENT.equals(uri.getScheme())) { 6189 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6190 "Can't grant URI permission for non-content URI: " + uri); 6191 return -1; 6192 } 6193 6194 final String authority = uri.getAuthority(); 6195 final ProviderInfo pi = getProviderInfoLocked(authority, UserHandle.getUserId(callingUid)); 6196 if (pi == null) { 6197 Slog.w(TAG, "No content provider found for permission check: " + uri.toSafeString()); 6198 return -1; 6199 } 6200 6201 int targetUid = lastTargetUid; 6202 if (targetUid < 0 && targetPkg != null) { 6203 try { 6204 targetUid = pm.getPackageUid(targetPkg, UserHandle.getUserId(callingUid)); 6205 if (targetUid < 0) { 6206 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6207 "Can't grant URI permission no uid for: " + targetPkg); 6208 return -1; 6209 } 6210 } catch (RemoteException ex) { 6211 return -1; 6212 } 6213 } 6214 6215 if (targetUid >= 0) { 6216 // First... does the target actually need this permission? 6217 if (checkHoldingPermissionsLocked(pm, pi, uri, targetUid, modeFlags)) { 6218 // No need to grant the target this permission. 6219 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6220 "Target " + targetPkg + " already has full permission to " + uri); 6221 return -1; 6222 } 6223 } else { 6224 // First... there is no target package, so can anyone access it? 6225 boolean allowed = pi.exported; 6226 if ((modeFlags&Intent.FLAG_GRANT_READ_URI_PERMISSION) != 0) { 6227 if (pi.readPermission != null) { 6228 allowed = false; 6229 } 6230 } 6231 if ((modeFlags&Intent.FLAG_GRANT_WRITE_URI_PERMISSION) != 0) { 6232 if (pi.writePermission != null) { 6233 allowed = false; 6234 } 6235 } 6236 if (allowed) { 6237 return -1; 6238 } 6239 } 6240 6241 // Second... is the provider allowing granting of URI permissions? 6242 if (!pi.grantUriPermissions) { 6243 throw new SecurityException("Provider " + pi.packageName 6244 + "/" + pi.name 6245 + " does not allow granting of Uri permissions (uri " 6246 + uri + ")"); 6247 } 6248 if (pi.uriPermissionPatterns != null) { 6249 final int N = pi.uriPermissionPatterns.length; 6250 boolean allowed = false; 6251 for (int i=0; i<N; i++) { 6252 if (pi.uriPermissionPatterns[i] != null 6253 && pi.uriPermissionPatterns[i].match(uri.getPath())) { 6254 allowed = true; 6255 break; 6256 } 6257 } 6258 if (!allowed) { 6259 throw new SecurityException("Provider " + pi.packageName 6260 + "/" + pi.name 6261 + " does not allow granting of permission to path of Uri " 6262 + uri); 6263 } 6264 } 6265 6266 // Third... does the caller itself have permission to access 6267 // this uri? 6268 if (callingUid != Process.myUid()) { 6269 if (!checkHoldingPermissionsLocked(pm, pi, uri, callingUid, modeFlags)) { 6270 // Require they hold a strong enough Uri permission 6271 if (!checkUriPermissionLocked(uri, callingUid, modeFlags)) { 6272 throw new SecurityException("Uid " + callingUid 6273 + " does not have permission to uri " + uri); 6274 } 6275 } 6276 } 6277 6278 return targetUid; 6279 } 6280 6281 @Override 6282 public int checkGrantUriPermission(int callingUid, String targetPkg, 6283 Uri uri, final int modeFlags) { 6284 enforceNotIsolatedCaller("checkGrantUriPermission"); 6285 synchronized(this) { 6286 return checkGrantUriPermissionLocked(callingUid, targetPkg, uri, modeFlags, -1); 6287 } 6288 } 6289 6290 void grantUriPermissionUncheckedLocked(int targetUid, String targetPkg, Uri uri, 6291 final int modeFlags, UriPermissionOwner owner) { 6292 if (!Intent.isAccessUriMode(modeFlags)) { 6293 return; 6294 } 6295 6296 // So here we are: the caller has the assumed permission 6297 // to the uri, and the target doesn't. Let's now give this to 6298 // the target. 6299 6300 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6301 "Granting " + targetPkg + "/" + targetUid + " permission to " + uri); 6302 6303 final String authority = uri.getAuthority(); 6304 final ProviderInfo pi = getProviderInfoLocked(authority, UserHandle.getUserId(targetUid)); 6305 if (pi == null) { 6306 Slog.w(TAG, "No content provider found for grant: " + uri.toSafeString()); 6307 return; 6308 } 6309 6310 final boolean prefix = (modeFlags & Intent.FLAG_GRANT_PREFIX_URI_PERMISSION) != 0; 6311 final UriPermission perm = findOrCreateUriPermissionLocked( 6312 pi.packageName, targetPkg, targetUid, new GrantUri(uri, prefix)); 6313 perm.grantModes(modeFlags, owner); 6314 } 6315 6316 void grantUriPermissionLocked(int callingUid, String targetPkg, Uri uri, 6317 final int modeFlags, UriPermissionOwner owner) { 6318 if (targetPkg == null) { 6319 throw new NullPointerException("targetPkg"); 6320 } 6321 6322 int targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, uri, modeFlags, -1); 6323 if (targetUid < 0) { 6324 return; 6325 } 6326 6327 grantUriPermissionUncheckedLocked(targetUid, targetPkg, uri, modeFlags, owner); 6328 } 6329 6330 static class NeededUriGrants extends ArrayList<Uri> { 6331 final String targetPkg; 6332 final int targetUid; 6333 final int flags; 6334 6335 NeededUriGrants(String targetPkg, int targetUid, int flags) { 6336 this.targetPkg = targetPkg; 6337 this.targetUid = targetUid; 6338 this.flags = flags; 6339 } 6340 } 6341 6342 /** 6343 * Like checkGrantUriPermissionLocked, but takes an Intent. 6344 */ 6345 NeededUriGrants checkGrantUriPermissionFromIntentLocked(int callingUid, 6346 String targetPkg, Intent intent, int mode, NeededUriGrants needed) { 6347 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6348 "Checking URI perm to data=" + (intent != null ? intent.getData() : null) 6349 + " clip=" + (intent != null ? intent.getClipData() : null) 6350 + " from " + intent + "; flags=0x" 6351 + Integer.toHexString(intent != null ? intent.getFlags() : 0)); 6352 6353 if (targetPkg == null) { 6354 throw new NullPointerException("targetPkg"); 6355 } 6356 6357 if (intent == null) { 6358 return null; 6359 } 6360 Uri data = intent.getData(); 6361 ClipData clip = intent.getClipData(); 6362 if (data == null && clip == null) { 6363 return null; 6364 } 6365 6366 if (data != null) { 6367 int targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, data, 6368 mode, needed != null ? needed.targetUid : -1); 6369 if (targetUid > 0) { 6370 if (needed == null) { 6371 needed = new NeededUriGrants(targetPkg, targetUid, mode); 6372 } 6373 needed.add(data); 6374 } 6375 } 6376 if (clip != null) { 6377 for (int i=0; i<clip.getItemCount(); i++) { 6378 Uri uri = clip.getItemAt(i).getUri(); 6379 if (uri != null) { 6380 int targetUid = -1; 6381 targetUid = checkGrantUriPermissionLocked(callingUid, targetPkg, uri, 6382 mode, needed != null ? needed.targetUid : -1); 6383 if (targetUid > 0) { 6384 if (needed == null) { 6385 needed = new NeededUriGrants(targetPkg, targetUid, mode); 6386 } 6387 needed.add(uri); 6388 } 6389 } else { 6390 Intent clipIntent = clip.getItemAt(i).getIntent(); 6391 if (clipIntent != null) { 6392 NeededUriGrants newNeeded = checkGrantUriPermissionFromIntentLocked( 6393 callingUid, targetPkg, clipIntent, mode, needed); 6394 if (newNeeded != null) { 6395 needed = newNeeded; 6396 } 6397 } 6398 } 6399 } 6400 } 6401 6402 return needed; 6403 } 6404 6405 /** 6406 * Like grantUriPermissionUncheckedLocked, but takes an Intent. 6407 */ 6408 void grantUriPermissionUncheckedFromIntentLocked(NeededUriGrants needed, 6409 UriPermissionOwner owner) { 6410 if (needed != null) { 6411 for (int i=0; i<needed.size(); i++) { 6412 grantUriPermissionUncheckedLocked(needed.targetUid, needed.targetPkg, 6413 needed.get(i), needed.flags, owner); 6414 } 6415 } 6416 } 6417 6418 void grantUriPermissionFromIntentLocked(int callingUid, 6419 String targetPkg, Intent intent, UriPermissionOwner owner) { 6420 NeededUriGrants needed = checkGrantUriPermissionFromIntentLocked(callingUid, targetPkg, 6421 intent, intent != null ? intent.getFlags() : 0, null); 6422 if (needed == null) { 6423 return; 6424 } 6425 6426 grantUriPermissionUncheckedFromIntentLocked(needed, owner); 6427 } 6428 6429 @Override 6430 public void grantUriPermission(IApplicationThread caller, String targetPkg, 6431 Uri uri, final int modeFlags) { 6432 enforceNotIsolatedCaller("grantUriPermission"); 6433 synchronized(this) { 6434 final ProcessRecord r = getRecordForAppLocked(caller); 6435 if (r == null) { 6436 throw new SecurityException("Unable to find app for caller " 6437 + caller 6438 + " when granting permission to uri " + uri); 6439 } 6440 if (targetPkg == null) { 6441 throw new IllegalArgumentException("null target"); 6442 } 6443 if (uri == null) { 6444 throw new IllegalArgumentException("null uri"); 6445 } 6446 6447 Preconditions.checkFlagsArgument(modeFlags, Intent.FLAG_GRANT_READ_URI_PERMISSION 6448 | Intent.FLAG_GRANT_WRITE_URI_PERMISSION 6449 | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION 6450 | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION); 6451 6452 grantUriPermissionLocked(r.uid, targetPkg, uri, modeFlags, null); 6453 } 6454 } 6455 6456 void removeUriPermissionIfNeededLocked(UriPermission perm) { 6457 if (perm.modeFlags == 0) { 6458 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 6459 perm.targetUid); 6460 if (perms != null) { 6461 if (DEBUG_URI_PERMISSION) Slog.v(TAG, 6462 "Removing " + perm.targetUid + " permission to " + perm.uri); 6463 6464 perms.remove(perm.uri); 6465 if (perms.isEmpty()) { 6466 mGrantedUriPermissions.remove(perm.targetUid); 6467 } 6468 } 6469 } 6470 } 6471 6472 private void revokeUriPermissionLocked(int callingUid, Uri uri, final int modeFlags) { 6473 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "Revoking all granted permissions to " + uri); 6474 6475 final IPackageManager pm = AppGlobals.getPackageManager(); 6476 final String authority = uri.getAuthority(); 6477 final ProviderInfo pi = getProviderInfoLocked(authority, UserHandle.getUserId(callingUid)); 6478 if (pi == null) { 6479 Slog.w(TAG, "No content provider found for permission revoke: " + uri.toSafeString()); 6480 return; 6481 } 6482 6483 // Does the caller have this permission on the URI? 6484 if (!checkHoldingPermissionsLocked(pm, pi, uri, callingUid, modeFlags)) { 6485 // Right now, if you are not the original owner of the permission, 6486 // you are not allowed to revoke it. 6487 //if (!checkUriPermissionLocked(uri, callingUid, modeFlags)) { 6488 throw new SecurityException("Uid " + callingUid 6489 + " does not have permission to uri " + uri); 6490 //} 6491 } 6492 6493 boolean persistChanged = false; 6494 6495 // Go through all of the permissions and remove any that match. 6496 int N = mGrantedUriPermissions.size(); 6497 for (int i = 0; i < N; i++) { 6498 final int targetUid = mGrantedUriPermissions.keyAt(i); 6499 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6500 6501 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 6502 final UriPermission perm = it.next(); 6503 if (perm.uri.uri.isPathPrefixMatch(uri)) { 6504 if (DEBUG_URI_PERMISSION) 6505 Slog.v(TAG, 6506 "Revoking " + perm.targetUid + " permission to " + perm.uri); 6507 persistChanged |= perm.revokeModes( 6508 modeFlags | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 6509 if (perm.modeFlags == 0) { 6510 it.remove(); 6511 } 6512 } 6513 } 6514 6515 if (perms.isEmpty()) { 6516 mGrantedUriPermissions.remove(targetUid); 6517 N--; 6518 i--; 6519 } 6520 } 6521 6522 if (persistChanged) { 6523 schedulePersistUriGrants(); 6524 } 6525 } 6526 6527 @Override 6528 public void revokeUriPermission(IApplicationThread caller, Uri uri, 6529 final int modeFlags) { 6530 enforceNotIsolatedCaller("revokeUriPermission"); 6531 synchronized(this) { 6532 final ProcessRecord r = getRecordForAppLocked(caller); 6533 if (r == null) { 6534 throw new SecurityException("Unable to find app for caller " 6535 + caller 6536 + " when revoking permission to uri " + uri); 6537 } 6538 if (uri == null) { 6539 Slog.w(TAG, "revokeUriPermission: null uri"); 6540 return; 6541 } 6542 6543 if (!Intent.isAccessUriMode(modeFlags)) { 6544 return; 6545 } 6546 6547 final IPackageManager pm = AppGlobals.getPackageManager(); 6548 final String authority = uri.getAuthority(); 6549 final ProviderInfo pi = getProviderInfoLocked(authority, r.userId); 6550 if (pi == null) { 6551 Slog.w(TAG, "No content provider found for permission revoke: " 6552 + uri.toSafeString()); 6553 return; 6554 } 6555 6556 revokeUriPermissionLocked(r.uid, uri, modeFlags); 6557 } 6558 } 6559 6560 /** 6561 * Remove any {@link UriPermission} granted <em>from</em> or <em>to</em> the 6562 * given package. 6563 * 6564 * @param packageName Package name to match, or {@code null} to apply to all 6565 * packages. 6566 * @param userHandle User to match, or {@link UserHandle#USER_ALL} to apply 6567 * to all users. 6568 * @param persistable If persistable grants should be removed. 6569 */ 6570 private void removeUriPermissionsForPackageLocked( 6571 String packageName, int userHandle, boolean persistable) { 6572 if (userHandle == UserHandle.USER_ALL && packageName == null) { 6573 throw new IllegalArgumentException("Must narrow by either package or user"); 6574 } 6575 6576 boolean persistChanged = false; 6577 6578 int N = mGrantedUriPermissions.size(); 6579 for (int i = 0; i < N; i++) { 6580 final int targetUid = mGrantedUriPermissions.keyAt(i); 6581 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6582 6583 // Only inspect grants matching user 6584 if (userHandle == UserHandle.USER_ALL 6585 || userHandle == UserHandle.getUserId(targetUid)) { 6586 for (Iterator<UriPermission> it = perms.values().iterator(); it.hasNext();) { 6587 final UriPermission perm = it.next(); 6588 6589 // Only inspect grants matching package 6590 if (packageName == null || perm.sourcePkg.equals(packageName) 6591 || perm.targetPkg.equals(packageName)) { 6592 persistChanged |= perm.revokeModes( 6593 persistable ? ~0 : ~Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); 6594 6595 // Only remove when no modes remain; any persisted grants 6596 // will keep this alive. 6597 if (perm.modeFlags == 0) { 6598 it.remove(); 6599 } 6600 } 6601 } 6602 6603 if (perms.isEmpty()) { 6604 mGrantedUriPermissions.remove(targetUid); 6605 N--; 6606 i--; 6607 } 6608 } 6609 } 6610 6611 if (persistChanged) { 6612 schedulePersistUriGrants(); 6613 } 6614 } 6615 6616 @Override 6617 public IBinder newUriPermissionOwner(String name) { 6618 enforceNotIsolatedCaller("newUriPermissionOwner"); 6619 synchronized(this) { 6620 UriPermissionOwner owner = new UriPermissionOwner(this, name); 6621 return owner.getExternalTokenLocked(); 6622 } 6623 } 6624 6625 @Override 6626 public void grantUriPermissionFromOwner(IBinder token, int fromUid, String targetPkg, 6627 Uri uri, final int modeFlags) { 6628 synchronized(this) { 6629 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 6630 if (owner == null) { 6631 throw new IllegalArgumentException("Unknown owner: " + token); 6632 } 6633 if (fromUid != Binder.getCallingUid()) { 6634 if (Binder.getCallingUid() != Process.myUid()) { 6635 // Only system code can grant URI permissions on behalf 6636 // of other users. 6637 throw new SecurityException("nice try"); 6638 } 6639 } 6640 if (targetPkg == null) { 6641 throw new IllegalArgumentException("null target"); 6642 } 6643 if (uri == null) { 6644 throw new IllegalArgumentException("null uri"); 6645 } 6646 6647 grantUriPermissionLocked(fromUid, targetPkg, uri, modeFlags, owner); 6648 } 6649 } 6650 6651 @Override 6652 public void revokeUriPermissionFromOwner(IBinder token, Uri uri, int mode) { 6653 synchronized(this) { 6654 UriPermissionOwner owner = UriPermissionOwner.fromExternalToken(token); 6655 if (owner == null) { 6656 throw new IllegalArgumentException("Unknown owner: " + token); 6657 } 6658 6659 if (uri == null) { 6660 owner.removeUriPermissionsLocked(mode); 6661 } else { 6662 owner.removeUriPermissionLocked(uri, mode); 6663 } 6664 } 6665 } 6666 6667 private void schedulePersistUriGrants() { 6668 if (!mHandler.hasMessages(PERSIST_URI_GRANTS_MSG)) { 6669 mHandler.sendMessageDelayed(mHandler.obtainMessage(PERSIST_URI_GRANTS_MSG), 6670 10 * DateUtils.SECOND_IN_MILLIS); 6671 } 6672 } 6673 6674 private void writeGrantedUriPermissions() { 6675 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "writeGrantedUriPermissions()"); 6676 6677 // Snapshot permissions so we can persist without lock 6678 ArrayList<UriPermission.Snapshot> persist = Lists.newArrayList(); 6679 synchronized (this) { 6680 final int size = mGrantedUriPermissions.size(); 6681 for (int i = 0; i < size; i++) { 6682 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 6683 for (UriPermission perm : perms.values()) { 6684 if (perm.persistedModeFlags != 0) { 6685 persist.add(perm.snapshot()); 6686 } 6687 } 6688 } 6689 } 6690 6691 FileOutputStream fos = null; 6692 try { 6693 fos = mGrantFile.startWrite(); 6694 6695 XmlSerializer out = new FastXmlSerializer(); 6696 out.setOutput(fos, "utf-8"); 6697 out.startDocument(null, true); 6698 out.startTag(null, TAG_URI_GRANTS); 6699 for (UriPermission.Snapshot perm : persist) { 6700 out.startTag(null, TAG_URI_GRANT); 6701 writeIntAttribute(out, ATTR_USER_HANDLE, perm.userHandle); 6702 out.attribute(null, ATTR_SOURCE_PKG, perm.sourcePkg); 6703 out.attribute(null, ATTR_TARGET_PKG, perm.targetPkg); 6704 out.attribute(null, ATTR_URI, String.valueOf(perm.uri.uri)); 6705 writeBooleanAttribute(out, ATTR_PREFIX, perm.uri.prefix); 6706 writeIntAttribute(out, ATTR_MODE_FLAGS, perm.persistedModeFlags); 6707 writeLongAttribute(out, ATTR_CREATED_TIME, perm.persistedCreateTime); 6708 out.endTag(null, TAG_URI_GRANT); 6709 } 6710 out.endTag(null, TAG_URI_GRANTS); 6711 out.endDocument(); 6712 6713 mGrantFile.finishWrite(fos); 6714 } catch (IOException e) { 6715 if (fos != null) { 6716 mGrantFile.failWrite(fos); 6717 } 6718 } 6719 } 6720 6721 private void readGrantedUriPermissionsLocked() { 6722 if (DEBUG_URI_PERMISSION) Slog.v(TAG, "readGrantedUriPermissions()"); 6723 6724 final long now = System.currentTimeMillis(); 6725 6726 FileInputStream fis = null; 6727 try { 6728 fis = mGrantFile.openRead(); 6729 final XmlPullParser in = Xml.newPullParser(); 6730 in.setInput(fis, null); 6731 6732 int type; 6733 while ((type = in.next()) != END_DOCUMENT) { 6734 final String tag = in.getName(); 6735 if (type == START_TAG) { 6736 if (TAG_URI_GRANT.equals(tag)) { 6737 final int userHandle = readIntAttribute(in, ATTR_USER_HANDLE); 6738 final String sourcePkg = in.getAttributeValue(null, ATTR_SOURCE_PKG); 6739 final String targetPkg = in.getAttributeValue(null, ATTR_TARGET_PKG); 6740 final Uri uri = Uri.parse(in.getAttributeValue(null, ATTR_URI)); 6741 final boolean prefix = readBooleanAttribute(in, ATTR_PREFIX); 6742 final int modeFlags = readIntAttribute(in, ATTR_MODE_FLAGS); 6743 final long createdTime = readLongAttribute(in, ATTR_CREATED_TIME, now); 6744 6745 // Sanity check that provider still belongs to source package 6746 final ProviderInfo pi = getProviderInfoLocked( 6747 uri.getAuthority(), userHandle); 6748 if (pi != null && sourcePkg.equals(pi.packageName)) { 6749 int targetUid = -1; 6750 try { 6751 targetUid = AppGlobals.getPackageManager() 6752 .getPackageUid(targetPkg, userHandle); 6753 } catch (RemoteException e) { 6754 } 6755 if (targetUid != -1) { 6756 final UriPermission perm = findOrCreateUriPermissionLocked( 6757 sourcePkg, targetPkg, targetUid, new GrantUri(uri, prefix)); 6758 perm.initPersistedModes(modeFlags, createdTime); 6759 } 6760 } else { 6761 Slog.w(TAG, "Persisted grant for " + uri + " had source " + sourcePkg 6762 + " but instead found " + pi); 6763 } 6764 } 6765 } 6766 } 6767 } catch (FileNotFoundException e) { 6768 // Missing grants is okay 6769 } catch (IOException e) { 6770 Log.wtf(TAG, "Failed reading Uri grants", e); 6771 } catch (XmlPullParserException e) { 6772 Log.wtf(TAG, "Failed reading Uri grants", e); 6773 } finally { 6774 IoUtils.closeQuietly(fis); 6775 } 6776 } 6777 6778 @Override 6779 public void takePersistableUriPermission(Uri uri, final int modeFlags) { 6780 enforceNotIsolatedCaller("takePersistableUriPermission"); 6781 6782 Preconditions.checkFlagsArgument(modeFlags, 6783 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 6784 6785 synchronized (this) { 6786 final int callingUid = Binder.getCallingUid(); 6787 boolean persistChanged = false; 6788 6789 UriPermission exactPerm = findUriPermissionLocked(callingUid, new GrantUri(uri, false)); 6790 UriPermission prefixPerm = findUriPermissionLocked(callingUid, new GrantUri(uri, true)); 6791 6792 final boolean exactValid = (exactPerm != null) 6793 && ((modeFlags & exactPerm.persistableModeFlags) == modeFlags); 6794 final boolean prefixValid = (prefixPerm != null) 6795 && ((modeFlags & prefixPerm.persistableModeFlags) == modeFlags); 6796 6797 if (!(exactValid || prefixValid)) { 6798 throw new SecurityException("No persistable permission grants found for UID " 6799 + callingUid + " and Uri " + uri.toSafeString()); 6800 } 6801 6802 if (exactValid) { 6803 persistChanged |= exactPerm.takePersistableModes(modeFlags); 6804 } 6805 if (prefixValid) { 6806 persistChanged |= prefixPerm.takePersistableModes(modeFlags); 6807 } 6808 6809 persistChanged |= maybePrunePersistedUriGrantsLocked(callingUid); 6810 6811 if (persistChanged) { 6812 schedulePersistUriGrants(); 6813 } 6814 } 6815 } 6816 6817 @Override 6818 public void releasePersistableUriPermission(Uri uri, final int modeFlags) { 6819 enforceNotIsolatedCaller("releasePersistableUriPermission"); 6820 6821 Preconditions.checkFlagsArgument(modeFlags, 6822 Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION); 6823 6824 synchronized (this) { 6825 final int callingUid = Binder.getCallingUid(); 6826 boolean persistChanged = false; 6827 6828 UriPermission exactPerm = findUriPermissionLocked(callingUid, new GrantUri(uri, false)); 6829 UriPermission prefixPerm = findUriPermissionLocked(callingUid, new GrantUri(uri, true)); 6830 if (exactPerm == null && prefixPerm == null) { 6831 throw new SecurityException("No permission grants found for UID " + callingUid 6832 + " and Uri " + uri.toSafeString()); 6833 } 6834 6835 if (exactPerm != null) { 6836 persistChanged |= exactPerm.releasePersistableModes(modeFlags); 6837 removeUriPermissionIfNeededLocked(exactPerm); 6838 } 6839 if (prefixPerm != null) { 6840 persistChanged |= prefixPerm.releasePersistableModes(modeFlags); 6841 removeUriPermissionIfNeededLocked(prefixPerm); 6842 } 6843 6844 if (persistChanged) { 6845 schedulePersistUriGrants(); 6846 } 6847 } 6848 } 6849 6850 /** 6851 * Prune any older {@link UriPermission} for the given UID until outstanding 6852 * persisted grants are below {@link #MAX_PERSISTED_URI_GRANTS}. 6853 * 6854 * @return if any mutations occured that require persisting. 6855 */ 6856 private boolean maybePrunePersistedUriGrantsLocked(int uid) { 6857 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(uid); 6858 if (perms == null) return false; 6859 if (perms.size() < MAX_PERSISTED_URI_GRANTS) return false; 6860 6861 final ArrayList<UriPermission> persisted = Lists.newArrayList(); 6862 for (UriPermission perm : perms.values()) { 6863 if (perm.persistedModeFlags != 0) { 6864 persisted.add(perm); 6865 } 6866 } 6867 6868 final int trimCount = persisted.size() - MAX_PERSISTED_URI_GRANTS; 6869 if (trimCount <= 0) return false; 6870 6871 Collections.sort(persisted, new UriPermission.PersistedTimeComparator()); 6872 for (int i = 0; i < trimCount; i++) { 6873 final UriPermission perm = persisted.get(i); 6874 6875 if (DEBUG_URI_PERMISSION) { 6876 Slog.v(TAG, "Trimming grant created at " + perm.persistedCreateTime); 6877 } 6878 6879 perm.releasePersistableModes(~0); 6880 removeUriPermissionIfNeededLocked(perm); 6881 } 6882 6883 return true; 6884 } 6885 6886 @Override 6887 public ParceledListSlice<android.content.UriPermission> getPersistedUriPermissions( 6888 String packageName, boolean incoming) { 6889 enforceNotIsolatedCaller("getPersistedUriPermissions"); 6890 Preconditions.checkNotNull(packageName, "packageName"); 6891 6892 final int callingUid = Binder.getCallingUid(); 6893 final IPackageManager pm = AppGlobals.getPackageManager(); 6894 try { 6895 final int packageUid = pm.getPackageUid(packageName, UserHandle.getUserId(callingUid)); 6896 if (packageUid != callingUid) { 6897 throw new SecurityException( 6898 "Package " + packageName + " does not belong to calling UID " + callingUid); 6899 } 6900 } catch (RemoteException e) { 6901 throw new SecurityException("Failed to verify package name ownership"); 6902 } 6903 6904 final ArrayList<android.content.UriPermission> result = Lists.newArrayList(); 6905 synchronized (this) { 6906 if (incoming) { 6907 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get( 6908 callingUid); 6909 if (perms == null) { 6910 Slog.w(TAG, "No permission grants found for " + packageName); 6911 } else { 6912 for (UriPermission perm : perms.values()) { 6913 if (packageName.equals(perm.targetPkg) && perm.persistedModeFlags != 0) { 6914 result.add(perm.buildPersistedPublicApiObject()); 6915 } 6916 } 6917 } 6918 } else { 6919 final int size = mGrantedUriPermissions.size(); 6920 for (int i = 0; i < size; i++) { 6921 final ArrayMap<GrantUri, UriPermission> perms = 6922 mGrantedUriPermissions.valueAt(i); 6923 for (UriPermission perm : perms.values()) { 6924 if (packageName.equals(perm.sourcePkg) && perm.persistedModeFlags != 0) { 6925 result.add(perm.buildPersistedPublicApiObject()); 6926 } 6927 } 6928 } 6929 } 6930 } 6931 return new ParceledListSlice<android.content.UriPermission>(result); 6932 } 6933 6934 @Override 6935 public void showWaitingForDebugger(IApplicationThread who, boolean waiting) { 6936 synchronized (this) { 6937 ProcessRecord app = 6938 who != null ? getRecordForAppLocked(who) : null; 6939 if (app == null) return; 6940 6941 Message msg = Message.obtain(); 6942 msg.what = WAIT_FOR_DEBUGGER_MSG; 6943 msg.obj = app; 6944 msg.arg1 = waiting ? 1 : 0; 6945 mHandler.sendMessage(msg); 6946 } 6947 } 6948 6949 @Override 6950 public void getMemoryInfo(ActivityManager.MemoryInfo outInfo) { 6951 final long homeAppMem = mProcessList.getMemLevel(ProcessList.HOME_APP_ADJ); 6952 final long cachedAppMem = mProcessList.getMemLevel(ProcessList.CACHED_APP_MIN_ADJ); 6953 outInfo.availMem = Process.getFreeMemory(); 6954 outInfo.totalMem = Process.getTotalMemory(); 6955 outInfo.threshold = homeAppMem; 6956 outInfo.lowMemory = outInfo.availMem < (homeAppMem + ((cachedAppMem-homeAppMem)/2)); 6957 outInfo.hiddenAppThreshold = cachedAppMem; 6958 outInfo.secondaryServerThreshold = mProcessList.getMemLevel( 6959 ProcessList.SERVICE_ADJ); 6960 outInfo.visibleAppThreshold = mProcessList.getMemLevel( 6961 ProcessList.VISIBLE_APP_ADJ); 6962 outInfo.foregroundAppThreshold = mProcessList.getMemLevel( 6963 ProcessList.FOREGROUND_APP_ADJ); 6964 } 6965 6966 // ========================================================= 6967 // TASK MANAGEMENT 6968 // ========================================================= 6969 6970 @Override 6971 public List<RunningTaskInfo> getTasks(int maxNum, int flags) { 6972 final int callingUid = Binder.getCallingUid(); 6973 ArrayList<RunningTaskInfo> list = new ArrayList<RunningTaskInfo>(); 6974 6975 synchronized(this) { 6976 if (localLOGV) Slog.v( 6977 TAG, "getTasks: max=" + maxNum + ", flags=" + flags); 6978 6979 final boolean allowed = checkCallingPermission( 6980 android.Manifest.permission.GET_TASKS) 6981 == PackageManager.PERMISSION_GRANTED; 6982 if (!allowed) { 6983 Slog.w(TAG, "getTasks: caller " + callingUid 6984 + " does not hold GET_TASKS; limiting output"); 6985 } 6986 6987 // TODO: Improve with MRU list from all ActivityStacks. 6988 mStackSupervisor.getTasksLocked(maxNum, list, callingUid, allowed); 6989 } 6990 6991 return list; 6992 } 6993 6994 TaskRecord getMostRecentTask() { 6995 return mRecentTasks.get(0); 6996 } 6997 6998 @Override 6999 public List<ActivityManager.RecentTaskInfo> getRecentTasks(int maxNum, 7000 int flags, int userId) { 7001 final int callingUid = Binder.getCallingUid(); 7002 userId = handleIncomingUser(Binder.getCallingPid(), callingUid, userId, 7003 false, true, "getRecentTasks", null); 7004 7005 synchronized (this) { 7006 final boolean allowed = checkCallingPermission( 7007 android.Manifest.permission.GET_TASKS) 7008 == PackageManager.PERMISSION_GRANTED; 7009 if (!allowed) { 7010 Slog.w(TAG, "getRecentTasks: caller " + callingUid 7011 + " does not hold GET_TASKS; limiting output"); 7012 } 7013 final boolean detailed = checkCallingPermission( 7014 android.Manifest.permission.GET_DETAILED_TASKS) 7015 == PackageManager.PERMISSION_GRANTED; 7016 7017 IPackageManager pm = AppGlobals.getPackageManager(); 7018 7019 final int N = mRecentTasks.size(); 7020 ArrayList<ActivityManager.RecentTaskInfo> res 7021 = new ArrayList<ActivityManager.RecentTaskInfo>( 7022 maxNum < N ? maxNum : N); 7023 7024 final Set<Integer> includedUsers; 7025 if ((flags & ActivityManager.RECENT_INCLUDE_PROFILES) != 0) { 7026 includedUsers = getProfileIdsLocked(userId); 7027 } else { 7028 includedUsers = new HashSet<Integer>(); 7029 } 7030 includedUsers.add(Integer.valueOf(userId)); 7031 for (int i=0; i<N && maxNum > 0; i++) { 7032 TaskRecord tr = mRecentTasks.get(i); 7033 // Only add calling user or related users recent tasks 7034 if (!includedUsers.contains(Integer.valueOf(tr.userId))) continue; 7035 7036 // Return the entry if desired by the caller. We always return 7037 // the first entry, because callers always expect this to be the 7038 // foreground app. We may filter others if the caller has 7039 // not supplied RECENT_WITH_EXCLUDED and there is some reason 7040 // we should exclude the entry. 7041 7042 if (i == 0 7043 || ((flags&ActivityManager.RECENT_WITH_EXCLUDED) != 0) 7044 || (tr.intent == null) 7045 || ((tr.intent.getFlags() 7046 &Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS) == 0)) { 7047 if (!allowed) { 7048 // If the caller doesn't have the GET_TASKS permission, then only 7049 // allow them to see a small subset of tasks -- their own and home. 7050 if (!tr.isHomeTask() && tr.creatorUid != callingUid) { 7051 continue; 7052 } 7053 } 7054 ActivityManager.RecentTaskInfo rti 7055 = new ActivityManager.RecentTaskInfo(); 7056 rti.id = tr.numActivities > 0 ? tr.taskId : -1; 7057 rti.persistentId = tr.taskId; 7058 rti.baseIntent = new Intent( 7059 tr.intent != null ? tr.intent : tr.affinityIntent); 7060 if (!detailed) { 7061 rti.baseIntent.replaceExtras((Bundle)null); 7062 } 7063 rti.origActivity = tr.origActivity; 7064 rti.description = tr.lastDescription; 7065 rti.stackId = tr.stack.mStackId; 7066 rti.userId = tr.userId; 7067 7068 // Traverse upwards looking for any break between main task activities and 7069 // utility activities. 7070 final ArrayList<ActivityRecord> activities = tr.mActivities; 7071 int activityNdx; 7072 final int numActivities = activities.size(); 7073 for (activityNdx = Math.min(numActivities, 1); activityNdx < numActivities; 7074 ++activityNdx) { 7075 final ActivityRecord r = activities.get(activityNdx); 7076 if (r.intent != null && 7077 (r.intent.getFlags() & Intent.FLAG_ACTIVITY_CLEAR_WHEN_TASK_RESET) 7078 != 0) { 7079 break; 7080 } 7081 } 7082 // Traverse downwards starting below break looking for set label and icon. 7083 for (--activityNdx; activityNdx >= 0; --activityNdx) { 7084 final ActivityRecord r = activities.get(activityNdx); 7085 if (r.activityLabel != null || r.activityIcon != null) { 7086 rti.activityLabel = r.activityLabel; 7087 rti.activityIcon = r.activityIcon; 7088 break; 7089 } 7090 } 7091 7092 if ((flags&ActivityManager.RECENT_IGNORE_UNAVAILABLE) != 0) { 7093 // Check whether this activity is currently available. 7094 try { 7095 if (rti.origActivity != null) { 7096 if (pm.getActivityInfo(rti.origActivity, 0, userId) 7097 == null) { 7098 continue; 7099 } 7100 } else if (rti.baseIntent != null) { 7101 if (pm.queryIntentActivities(rti.baseIntent, 7102 null, 0, userId) == null) { 7103 continue; 7104 } 7105 } 7106 } catch (RemoteException e) { 7107 // Will never happen. 7108 } 7109 } 7110 7111 res.add(rti); 7112 maxNum--; 7113 } 7114 } 7115 return res; 7116 } 7117 } 7118 7119 private TaskRecord recentTaskForIdLocked(int id) { 7120 final int N = mRecentTasks.size(); 7121 for (int i=0; i<N; i++) { 7122 TaskRecord tr = mRecentTasks.get(i); 7123 if (tr.taskId == id) { 7124 return tr; 7125 } 7126 } 7127 return null; 7128 } 7129 7130 @Override 7131 public ActivityManager.TaskThumbnails getTaskThumbnails(int id) { 7132 synchronized (this) { 7133 enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER, 7134 "getTaskThumbnails()"); 7135 TaskRecord tr = recentTaskForIdLocked(id); 7136 if (tr != null) { 7137 return tr.getTaskThumbnailsLocked(); 7138 } 7139 } 7140 return null; 7141 } 7142 7143 @Override 7144 public Bitmap getTaskTopThumbnail(int id) { 7145 synchronized (this) { 7146 enforceCallingPermission(android.Manifest.permission.READ_FRAME_BUFFER, 7147 "getTaskTopThumbnail()"); 7148 TaskRecord tr = recentTaskForIdLocked(id); 7149 if (tr != null) { 7150 return tr.getTaskTopThumbnailLocked(); 7151 } 7152 } 7153 return null; 7154 } 7155 7156 @Override 7157 public void setActivityLabelAndIcon(IBinder token, CharSequence activityLabel, 7158 Bitmap activityIcon) { 7159 synchronized (this) { 7160 ActivityRecord r = ActivityRecord.isInStackLocked(token); 7161 if (r != null) { 7162 r.activityLabel = activityLabel.toString(); 7163 r.activityIcon = activityIcon; 7164 } 7165 } 7166 } 7167 7168 @Override 7169 public boolean removeSubTask(int taskId, int subTaskIndex) { 7170 synchronized (this) { 7171 enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, 7172 "removeSubTask()"); 7173 long ident = Binder.clearCallingIdentity(); 7174 try { 7175 TaskRecord tr = recentTaskForIdLocked(taskId); 7176 if (tr != null) { 7177 return tr.removeTaskActivitiesLocked(subTaskIndex, true) != null; 7178 } 7179 return false; 7180 } finally { 7181 Binder.restoreCallingIdentity(ident); 7182 } 7183 } 7184 } 7185 7186 private void killUnneededProcessLocked(ProcessRecord pr, String reason) { 7187 if (!pr.killedByAm) { 7188 Slog.i(TAG, "Killing " + pr.toShortString() + " (adj " + pr.setAdj + "): " + reason); 7189 EventLog.writeEvent(EventLogTags.AM_KILL, pr.userId, pr.pid, 7190 pr.processName, pr.setAdj, reason); 7191 pr.killedByAm = true; 7192 Process.killProcessQuiet(pr.pid); 7193 } 7194 } 7195 7196 private void cleanUpRemovedTaskLocked(TaskRecord tr, int flags) { 7197 tr.disposeThumbnail(); 7198 mRecentTasks.remove(tr); 7199 final boolean killProcesses = (flags&ActivityManager.REMOVE_TASK_KILL_PROCESS) != 0; 7200 Intent baseIntent = new Intent( 7201 tr.intent != null ? tr.intent : tr.affinityIntent); 7202 ComponentName component = baseIntent.getComponent(); 7203 if (component == null) { 7204 Slog.w(TAG, "Now component for base intent of task: " + tr); 7205 return; 7206 } 7207 7208 // Find any running services associated with this app. 7209 mServices.cleanUpRemovedTaskLocked(tr, component, baseIntent); 7210 7211 if (killProcesses) { 7212 // Find any running processes associated with this app. 7213 final String pkg = component.getPackageName(); 7214 ArrayList<ProcessRecord> procs = new ArrayList<ProcessRecord>(); 7215 ArrayMap<String, SparseArray<ProcessRecord>> pmap = mProcessNames.getMap(); 7216 for (int i=0; i<pmap.size(); i++) { 7217 SparseArray<ProcessRecord> uids = pmap.valueAt(i); 7218 for (int j=0; j<uids.size(); j++) { 7219 ProcessRecord proc = uids.valueAt(j); 7220 if (proc.userId != tr.userId) { 7221 continue; 7222 } 7223 if (!proc.pkgList.containsKey(pkg)) { 7224 continue; 7225 } 7226 procs.add(proc); 7227 } 7228 } 7229 7230 // Kill the running processes. 7231 for (int i=0; i<procs.size(); i++) { 7232 ProcessRecord pr = procs.get(i); 7233 if (pr == mHomeProcess) { 7234 // Don't kill the home process along with tasks from the same package. 7235 continue; 7236 } 7237 if (pr.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 7238 killUnneededProcessLocked(pr, "remove task"); 7239 } else { 7240 pr.waitingToKill = "remove task"; 7241 } 7242 } 7243 } 7244 } 7245 7246 /** 7247 * Removes the task with the specified task id. 7248 * 7249 * @param taskId Identifier of the task to be removed. 7250 * @param flags Additional operational flags. May be 0 or 7251 * {@link ActivityManager#REMOVE_TASK_KILL_PROCESS}. 7252 * @return Returns true if the given task was found and removed. 7253 */ 7254 private boolean removeTaskByIdLocked(int taskId, int flags) { 7255 TaskRecord tr = recentTaskForIdLocked(taskId); 7256 if (tr != null) { 7257 tr.removeTaskActivitiesLocked(-1, false); 7258 cleanUpRemovedTaskLocked(tr, flags); 7259 return true; 7260 } 7261 return false; 7262 } 7263 7264 @Override 7265 public boolean removeTask(int taskId, int flags) { 7266 synchronized (this) { 7267 enforceCallingPermission(android.Manifest.permission.REMOVE_TASKS, 7268 "removeTask()"); 7269 long ident = Binder.clearCallingIdentity(); 7270 try { 7271 return removeTaskByIdLocked(taskId, flags); 7272 } finally { 7273 Binder.restoreCallingIdentity(ident); 7274 } 7275 } 7276 } 7277 7278 /** 7279 * TODO: Add mController hook 7280 */ 7281 @Override 7282 public void moveTaskToFront(int taskId, int flags, Bundle options) { 7283 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7284 "moveTaskToFront()"); 7285 7286 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToFront: moving taskId=" + taskId); 7287 synchronized(this) { 7288 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7289 Binder.getCallingUid(), "Task to front")) { 7290 ActivityOptions.abort(options); 7291 return; 7292 } 7293 final long origId = Binder.clearCallingIdentity(); 7294 try { 7295 final TaskRecord task = mStackSupervisor.anyTaskForIdLocked(taskId); 7296 if (task == null) { 7297 return; 7298 } 7299 if (mStackSupervisor.isLockTaskModeViolation(task)) { 7300 Slog.e(TAG, "moveTaskToFront: Attempt to violate Lock Task Mode"); 7301 return; 7302 } 7303 mStackSupervisor.findTaskToMoveToFrontLocked(task, flags, options); 7304 } finally { 7305 Binder.restoreCallingIdentity(origId); 7306 } 7307 ActivityOptions.abort(options); 7308 } 7309 } 7310 7311 @Override 7312 public void moveTaskToBack(int taskId) { 7313 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7314 "moveTaskToBack()"); 7315 7316 synchronized(this) { 7317 TaskRecord tr = recentTaskForIdLocked(taskId); 7318 if (tr != null) { 7319 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToBack: moving task=" + tr); 7320 ActivityStack stack = tr.stack; 7321 if (stack.mResumedActivity != null && stack.mResumedActivity.task == tr) { 7322 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7323 Binder.getCallingUid(), "Task to back")) { 7324 return; 7325 } 7326 } 7327 final long origId = Binder.clearCallingIdentity(); 7328 try { 7329 stack.moveTaskToBackLocked(taskId, null); 7330 } finally { 7331 Binder.restoreCallingIdentity(origId); 7332 } 7333 } 7334 } 7335 } 7336 7337 /** 7338 * Moves an activity, and all of the other activities within the same task, to the bottom 7339 * of the history stack. The activity's order within the task is unchanged. 7340 * 7341 * @param token A reference to the activity we wish to move 7342 * @param nonRoot If false then this only works if the activity is the root 7343 * of a task; if true it will work for any activity in a task. 7344 * @return Returns true if the move completed, false if not. 7345 */ 7346 @Override 7347 public boolean moveActivityTaskToBack(IBinder token, boolean nonRoot) { 7348 enforceNotIsolatedCaller("moveActivityTaskToBack"); 7349 synchronized(this) { 7350 final long origId = Binder.clearCallingIdentity(); 7351 int taskId = ActivityRecord.getTaskForActivityLocked(token, !nonRoot); 7352 if (taskId >= 0) { 7353 return ActivityRecord.getStackLocked(token).moveTaskToBackLocked(taskId, null); 7354 } 7355 Binder.restoreCallingIdentity(origId); 7356 } 7357 return false; 7358 } 7359 7360 @Override 7361 public void moveTaskBackwards(int task) { 7362 enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7363 "moveTaskBackwards()"); 7364 7365 synchronized(this) { 7366 if (!checkAppSwitchAllowedLocked(Binder.getCallingPid(), 7367 Binder.getCallingUid(), "Task backwards")) { 7368 return; 7369 } 7370 final long origId = Binder.clearCallingIdentity(); 7371 moveTaskBackwardsLocked(task); 7372 Binder.restoreCallingIdentity(origId); 7373 } 7374 } 7375 7376 private final void moveTaskBackwardsLocked(int task) { 7377 Slog.e(TAG, "moveTaskBackwards not yet implemented!"); 7378 } 7379 7380 @Override 7381 public IBinder getHomeActivityToken() throws RemoteException { 7382 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7383 "getHomeActivityToken()"); 7384 synchronized (this) { 7385 return mStackSupervisor.getHomeActivityToken(); 7386 } 7387 } 7388 7389 @Override 7390 public IActivityContainer createActivityContainer(IBinder parentActivityToken, 7391 IActivityContainerCallback callback) throws RemoteException { 7392 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7393 "createActivityContainer()"); 7394 synchronized (this) { 7395 if (parentActivityToken == null) { 7396 throw new IllegalArgumentException("parent token must not be null"); 7397 } 7398 ActivityRecord r = ActivityRecord.forToken(parentActivityToken); 7399 if (r == null) { 7400 return null; 7401 } 7402 if (callback == null) { 7403 throw new IllegalArgumentException("callback must not be null"); 7404 } 7405 return mStackSupervisor.createActivityContainer(r, callback); 7406 } 7407 } 7408 7409 @Override 7410 public void deleteActivityContainer(IActivityContainer container) throws RemoteException { 7411 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7412 "deleteActivityContainer()"); 7413 synchronized (this) { 7414 mStackSupervisor.deleteActivityContainer(container); 7415 } 7416 } 7417 7418 @Override 7419 public IActivityContainer getEnclosingActivityContainer(IBinder activityToken) 7420 throws RemoteException { 7421 synchronized (this) { 7422 ActivityStack stack = ActivityRecord.getStackLocked(activityToken); 7423 if (stack != null) { 7424 return stack.mActivityContainer; 7425 } 7426 return null; 7427 } 7428 } 7429 7430 @Override 7431 public void moveTaskToStack(int taskId, int stackId, boolean toTop) { 7432 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7433 "moveTaskToStack()"); 7434 if (stackId == HOME_STACK_ID) { 7435 Slog.e(TAG, "moveTaskToStack: Attempt to move task " + taskId + " to home stack", 7436 new RuntimeException("here").fillInStackTrace()); 7437 } 7438 synchronized (this) { 7439 long ident = Binder.clearCallingIdentity(); 7440 try { 7441 if (DEBUG_STACK) Slog.d(TAG, "moveTaskToStack: moving task=" + taskId + " to stackId=" 7442 + stackId + " toTop=" + toTop); 7443 mStackSupervisor.moveTaskToStack(taskId, stackId, toTop); 7444 } finally { 7445 Binder.restoreCallingIdentity(ident); 7446 } 7447 } 7448 } 7449 7450 @Override 7451 public void resizeStack(int stackBoxId, Rect bounds) { 7452 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7453 "resizeStackBox()"); 7454 long ident = Binder.clearCallingIdentity(); 7455 try { 7456 mWindowManager.resizeStack(stackBoxId, bounds); 7457 } finally { 7458 Binder.restoreCallingIdentity(ident); 7459 } 7460 } 7461 7462 @Override 7463 public List<StackInfo> getAllStackInfos() { 7464 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7465 "getAllStackInfos()"); 7466 long ident = Binder.clearCallingIdentity(); 7467 try { 7468 synchronized (this) { 7469 return mStackSupervisor.getAllStackInfosLocked(); 7470 } 7471 } finally { 7472 Binder.restoreCallingIdentity(ident); 7473 } 7474 } 7475 7476 @Override 7477 public StackInfo getStackInfo(int stackId) { 7478 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7479 "getStackInfo()"); 7480 long ident = Binder.clearCallingIdentity(); 7481 try { 7482 synchronized (this) { 7483 return mStackSupervisor.getStackInfoLocked(stackId); 7484 } 7485 } finally { 7486 Binder.restoreCallingIdentity(ident); 7487 } 7488 } 7489 7490 @Override 7491 public boolean isInHomeStack(int taskId) { 7492 enforceCallingPermission(android.Manifest.permission.MANAGE_ACTIVITY_STACKS, 7493 "getStackInfo()"); 7494 long ident = Binder.clearCallingIdentity(); 7495 try { 7496 synchronized (this) { 7497 TaskRecord tr = recentTaskForIdLocked(taskId); 7498 if (tr != null) { 7499 return tr.stack.isHomeStack(); 7500 } 7501 } 7502 } finally { 7503 Binder.restoreCallingIdentity(ident); 7504 } 7505 return false; 7506 } 7507 7508 @Override 7509 public int getTaskForActivity(IBinder token, boolean onlyRoot) { 7510 synchronized(this) { 7511 return ActivityRecord.getTaskForActivityLocked(token, onlyRoot); 7512 } 7513 } 7514 7515 private boolean isLockTaskAuthorized(ComponentName name) { 7516// enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7517// "startLockTaskMode()"); 7518// DevicePolicyManager dpm = (DevicePolicyManager) 7519// mContext.getSystemService(Context.DEVICE_POLICY_SERVICE); 7520// return dpm != null && dpm.isLockTaskPermitted(name); 7521 return true; 7522 } 7523 7524 private void startLockTaskMode(TaskRecord task) { 7525 if (!isLockTaskAuthorized(task.intent.getComponent())) { 7526 return; 7527 } 7528 long ident = Binder.clearCallingIdentity(); 7529 try { 7530 synchronized (this) { 7531 // Since we lost lock on task, make sure it is still there. 7532 task = mStackSupervisor.anyTaskForIdLocked(task.taskId); 7533 if (task != null) { 7534 mStackSupervisor.setLockTaskModeLocked(task); 7535 } 7536 } 7537 } finally { 7538 Binder.restoreCallingIdentity(ident); 7539 } 7540 } 7541 7542 @Override 7543 public void startLockTaskMode(int taskId) { 7544 long ident = Binder.clearCallingIdentity(); 7545 try { 7546 final TaskRecord task; 7547 synchronized (this) { 7548 task = mStackSupervisor.anyTaskForIdLocked(taskId); 7549 } 7550 if (task != null) { 7551 startLockTaskMode(task); 7552 } 7553 } finally { 7554 Binder.restoreCallingIdentity(ident); 7555 } 7556 } 7557 7558 @Override 7559 public void startLockTaskMode(IBinder token) { 7560 long ident = Binder.clearCallingIdentity(); 7561 try { 7562 final TaskRecord task; 7563 synchronized (this) { 7564 final ActivityRecord r = ActivityRecord.forToken(token); 7565 if (r == null) { 7566 return; 7567 } 7568 task = r.task; 7569 } 7570 if (task != null) { 7571 startLockTaskMode(task); 7572 } 7573 } finally { 7574 Binder.restoreCallingIdentity(ident); 7575 } 7576 } 7577 7578 @Override 7579 public void stopLockTaskMode() { 7580// enforceCallingPermission(android.Manifest.permission.REORDER_TASKS, 7581// "stopLockTaskMode()"); 7582 synchronized (this) { 7583 mStackSupervisor.setLockTaskModeLocked(null); 7584 } 7585 } 7586 7587 @Override 7588 public boolean isInLockTaskMode() { 7589 synchronized (this) { 7590 return mStackSupervisor.isInLockTaskMode(); 7591 } 7592 } 7593 7594 // ========================================================= 7595 // CONTENT PROVIDERS 7596 // ========================================================= 7597 7598 private final List<ProviderInfo> generateApplicationProvidersLocked(ProcessRecord app) { 7599 List<ProviderInfo> providers = null; 7600 try { 7601 providers = AppGlobals.getPackageManager(). 7602 queryContentProviders(app.processName, app.uid, 7603 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS); 7604 } catch (RemoteException ex) { 7605 } 7606 if (DEBUG_MU) 7607 Slog.v(TAG_MU, "generateApplicationProvidersLocked, app.info.uid = " + app.uid); 7608 int userId = app.userId; 7609 if (providers != null) { 7610 int N = providers.size(); 7611 app.pubProviders.ensureCapacity(N + app.pubProviders.size()); 7612 for (int i=0; i<N; i++) { 7613 ProviderInfo cpi = 7614 (ProviderInfo)providers.get(i); 7615 boolean singleton = isSingleton(cpi.processName, cpi.applicationInfo, 7616 cpi.name, cpi.flags); 7617 if (singleton && UserHandle.getUserId(app.uid) != 0) { 7618 // This is a singleton provider, but a user besides the 7619 // default user is asking to initialize a process it runs 7620 // in... well, no, it doesn't actually run in this process, 7621 // it runs in the process of the default user. Get rid of it. 7622 providers.remove(i); 7623 N--; 7624 i--; 7625 continue; 7626 } 7627 7628 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 7629 ContentProviderRecord cpr = mProviderMap.getProviderByClass(comp, userId); 7630 if (cpr == null) { 7631 cpr = new ContentProviderRecord(this, cpi, app.info, comp, singleton); 7632 mProviderMap.putProviderByClass(comp, cpr); 7633 } 7634 if (DEBUG_MU) 7635 Slog.v(TAG_MU, "generateApplicationProvidersLocked, cpi.uid = " + cpr.uid); 7636 app.pubProviders.put(cpi.name, cpr); 7637 if (!cpi.multiprocess || !"android".equals(cpi.packageName)) { 7638 // Don't add this if it is a platform component that is marked 7639 // to run in multiple processes, because this is actually 7640 // part of the framework so doesn't make sense to track as a 7641 // separate apk in the process. 7642 app.addPackage(cpi.applicationInfo.packageName, mProcessStats); 7643 } 7644 ensurePackageDexOpt(cpi.applicationInfo.packageName); 7645 } 7646 } 7647 return providers; 7648 } 7649 7650 /** 7651 * Check if {@link ProcessRecord} has a possible chance at accessing the 7652 * given {@link ProviderInfo}. Final permission checking is always done 7653 * in {@link ContentProvider}. 7654 */ 7655 private final String checkContentProviderPermissionLocked( 7656 ProviderInfo cpi, ProcessRecord r) { 7657 final int callingPid = (r != null) ? r.pid : Binder.getCallingPid(); 7658 final int callingUid = (r != null) ? r.uid : Binder.getCallingUid(); 7659 if (checkComponentPermission(cpi.readPermission, callingPid, callingUid, 7660 cpi.applicationInfo.uid, cpi.exported) 7661 == PackageManager.PERMISSION_GRANTED) { 7662 return null; 7663 } 7664 if (checkComponentPermission(cpi.writePermission, callingPid, callingUid, 7665 cpi.applicationInfo.uid, cpi.exported) 7666 == PackageManager.PERMISSION_GRANTED) { 7667 return null; 7668 } 7669 7670 PathPermission[] pps = cpi.pathPermissions; 7671 if (pps != null) { 7672 int i = pps.length; 7673 while (i > 0) { 7674 i--; 7675 PathPermission pp = pps[i]; 7676 if (checkComponentPermission(pp.getReadPermission(), callingPid, callingUid, 7677 cpi.applicationInfo.uid, cpi.exported) 7678 == PackageManager.PERMISSION_GRANTED) { 7679 return null; 7680 } 7681 if (checkComponentPermission(pp.getWritePermission(), callingPid, callingUid, 7682 cpi.applicationInfo.uid, cpi.exported) 7683 == PackageManager.PERMISSION_GRANTED) { 7684 return null; 7685 } 7686 } 7687 } 7688 7689 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.get(callingUid); 7690 if (perms != null) { 7691 for (GrantUri uri : perms.keySet()) { 7692 if (uri.uri.getAuthority().equals(cpi.authority)) { 7693 return null; 7694 } 7695 } 7696 } 7697 7698 String msg; 7699 if (!cpi.exported) { 7700 msg = "Permission Denial: opening provider " + cpi.name 7701 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 7702 + ", uid=" + callingUid + ") that is not exported from uid " 7703 + cpi.applicationInfo.uid; 7704 } else { 7705 msg = "Permission Denial: opening provider " + cpi.name 7706 + " from " + (r != null ? r : "(null)") + " (pid=" + callingPid 7707 + ", uid=" + callingUid + ") requires " 7708 + cpi.readPermission + " or " + cpi.writePermission; 7709 } 7710 Slog.w(TAG, msg); 7711 return msg; 7712 } 7713 7714 ContentProviderConnection incProviderCountLocked(ProcessRecord r, 7715 final ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 7716 if (r != null) { 7717 for (int i=0; i<r.conProviders.size(); i++) { 7718 ContentProviderConnection conn = r.conProviders.get(i); 7719 if (conn.provider == cpr) { 7720 if (DEBUG_PROVIDER) Slog.v(TAG, 7721 "Adding provider requested by " 7722 + r.processName + " from process " 7723 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 7724 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 7725 if (stable) { 7726 conn.stableCount++; 7727 conn.numStableIncs++; 7728 } else { 7729 conn.unstableCount++; 7730 conn.numUnstableIncs++; 7731 } 7732 return conn; 7733 } 7734 } 7735 ContentProviderConnection conn = new ContentProviderConnection(cpr, r); 7736 if (stable) { 7737 conn.stableCount = 1; 7738 conn.numStableIncs = 1; 7739 } else { 7740 conn.unstableCount = 1; 7741 conn.numUnstableIncs = 1; 7742 } 7743 cpr.connections.add(conn); 7744 r.conProviders.add(conn); 7745 return conn; 7746 } 7747 cpr.addExternalProcessHandleLocked(externalProcessToken); 7748 return null; 7749 } 7750 7751 boolean decProviderCountLocked(ContentProviderConnection conn, 7752 ContentProviderRecord cpr, IBinder externalProcessToken, boolean stable) { 7753 if (conn != null) { 7754 cpr = conn.provider; 7755 if (DEBUG_PROVIDER) Slog.v(TAG, 7756 "Removing provider requested by " 7757 + conn.client.processName + " from process " 7758 + cpr.info.processName + ": " + cpr.name.flattenToShortString() 7759 + " scnt=" + conn.stableCount + " uscnt=" + conn.unstableCount); 7760 if (stable) { 7761 conn.stableCount--; 7762 } else { 7763 conn.unstableCount--; 7764 } 7765 if (conn.stableCount == 0 && conn.unstableCount == 0) { 7766 cpr.connections.remove(conn); 7767 conn.client.conProviders.remove(conn); 7768 return true; 7769 } 7770 return false; 7771 } 7772 cpr.removeExternalProcessHandleLocked(externalProcessToken); 7773 return false; 7774 } 7775 7776 private final ContentProviderHolder getContentProviderImpl(IApplicationThread caller, 7777 String name, IBinder token, boolean stable, int userId) { 7778 ContentProviderRecord cpr; 7779 ContentProviderConnection conn = null; 7780 ProviderInfo cpi = null; 7781 7782 synchronized(this) { 7783 ProcessRecord r = null; 7784 if (caller != null) { 7785 r = getRecordForAppLocked(caller); 7786 if (r == null) { 7787 throw new SecurityException( 7788 "Unable to find app for caller " + caller 7789 + " (pid=" + Binder.getCallingPid() 7790 + ") when getting content provider " + name); 7791 } 7792 } 7793 7794 // First check if this content provider has been published... 7795 cpr = mProviderMap.getProviderByName(name, userId); 7796 boolean providerRunning = cpr != null; 7797 if (providerRunning) { 7798 cpi = cpr.info; 7799 String msg; 7800 if ((msg=checkContentProviderPermissionLocked(cpi, r)) != null) { 7801 throw new SecurityException(msg); 7802 } 7803 7804 if (r != null && cpr.canRunHere(r)) { 7805 // This provider has been published or is in the process 7806 // of being published... but it is also allowed to run 7807 // in the caller's process, so don't make a connection 7808 // and just let the caller instantiate its own instance. 7809 ContentProviderHolder holder = cpr.newHolder(null); 7810 // don't give caller the provider object, it needs 7811 // to make its own. 7812 holder.provider = null; 7813 return holder; 7814 } 7815 7816 final long origId = Binder.clearCallingIdentity(); 7817 7818 // In this case the provider instance already exists, so we can 7819 // return it right away. 7820 conn = incProviderCountLocked(r, cpr, token, stable); 7821 if (conn != null && (conn.stableCount+conn.unstableCount) == 1) { 7822 if (cpr.proc != null && r.setAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 7823 // If this is a perceptible app accessing the provider, 7824 // make sure to count it as being accessed and thus 7825 // back up on the LRU list. This is good because 7826 // content providers are often expensive to start. 7827 updateLruProcessLocked(cpr.proc, false, null); 7828 } 7829 } 7830 7831 if (cpr.proc != null) { 7832 if (false) { 7833 if (cpr.name.flattenToShortString().equals( 7834 "com.android.providers.calendar/.CalendarProvider2")) { 7835 Slog.v(TAG, "****************** KILLING " 7836 + cpr.name.flattenToShortString()); 7837 Process.killProcess(cpr.proc.pid); 7838 } 7839 } 7840 boolean success = updateOomAdjLocked(cpr.proc); 7841 if (DEBUG_PROVIDER) Slog.i(TAG, "Adjust success: " + success); 7842 // NOTE: there is still a race here where a signal could be 7843 // pending on the process even though we managed to update its 7844 // adj level. Not sure what to do about this, but at least 7845 // the race is now smaller. 7846 if (!success) { 7847 // Uh oh... it looks like the provider's process 7848 // has been killed on us. We need to wait for a new 7849 // process to be started, and make sure its death 7850 // doesn't kill our process. 7851 Slog.i(TAG, 7852 "Existing provider " + cpr.name.flattenToShortString() 7853 + " is crashing; detaching " + r); 7854 boolean lastRef = decProviderCountLocked(conn, cpr, token, stable); 7855 appDiedLocked(cpr.proc, cpr.proc.pid, cpr.proc.thread); 7856 if (!lastRef) { 7857 // This wasn't the last ref our process had on 7858 // the provider... we have now been killed, bail. 7859 return null; 7860 } 7861 providerRunning = false; 7862 conn = null; 7863 } 7864 } 7865 7866 Binder.restoreCallingIdentity(origId); 7867 } 7868 7869 boolean singleton; 7870 if (!providerRunning) { 7871 try { 7872 cpi = AppGlobals.getPackageManager(). 7873 resolveContentProvider(name, 7874 STOCK_PM_FLAGS | PackageManager.GET_URI_PERMISSION_PATTERNS, userId); 7875 } catch (RemoteException ex) { 7876 } 7877 if (cpi == null) { 7878 return null; 7879 } 7880 singleton = isSingleton(cpi.processName, cpi.applicationInfo, 7881 cpi.name, cpi.flags); 7882 if (singleton) { 7883 userId = 0; 7884 } 7885 cpi.applicationInfo = getAppInfoForUser(cpi.applicationInfo, userId); 7886 7887 String msg; 7888 if ((msg=checkContentProviderPermissionLocked(cpi, r)) != null) { 7889 throw new SecurityException(msg); 7890 } 7891 7892 if (!mProcessesReady && !mDidUpdate && !mWaitingUpdate 7893 && !cpi.processName.equals("system")) { 7894 // If this content provider does not run in the system 7895 // process, and the system is not yet ready to run other 7896 // processes, then fail fast instead of hanging. 7897 throw new IllegalArgumentException( 7898 "Attempt to launch content provider before system ready"); 7899 } 7900 7901 // Make sure that the user who owns this provider is started. If not, 7902 // we don't want to allow it to run. 7903 if (mStartedUsers.get(userId) == null) { 7904 Slog.w(TAG, "Unable to launch app " 7905 + cpi.applicationInfo.packageName + "/" 7906 + cpi.applicationInfo.uid + " for provider " 7907 + name + ": user " + userId + " is stopped"); 7908 return null; 7909 } 7910 7911 ComponentName comp = new ComponentName(cpi.packageName, cpi.name); 7912 cpr = mProviderMap.getProviderByClass(comp, userId); 7913 final boolean firstClass = cpr == null; 7914 if (firstClass) { 7915 try { 7916 ApplicationInfo ai = 7917 AppGlobals.getPackageManager(). 7918 getApplicationInfo( 7919 cpi.applicationInfo.packageName, 7920 STOCK_PM_FLAGS, userId); 7921 if (ai == null) { 7922 Slog.w(TAG, "No package info for content provider " 7923 + cpi.name); 7924 return null; 7925 } 7926 ai = getAppInfoForUser(ai, userId); 7927 cpr = new ContentProviderRecord(this, cpi, ai, comp, singleton); 7928 } catch (RemoteException ex) { 7929 // pm is in same process, this will never happen. 7930 } 7931 } 7932 7933 if (r != null && cpr.canRunHere(r)) { 7934 // If this is a multiprocess provider, then just return its 7935 // info and allow the caller to instantiate it. Only do 7936 // this if the provider is the same user as the caller's 7937 // process, or can run as root (so can be in any process). 7938 return cpr.newHolder(null); 7939 } 7940 7941 if (DEBUG_PROVIDER) { 7942 RuntimeException e = new RuntimeException("here"); 7943 Slog.w(TAG, "LAUNCHING REMOTE PROVIDER (myuid " + (r != null ? r.uid : null) 7944 + " pruid " + cpr.appInfo.uid + "): " + cpr.info.name, e); 7945 } 7946 7947 // This is single process, and our app is now connecting to it. 7948 // See if we are already in the process of launching this 7949 // provider. 7950 final int N = mLaunchingProviders.size(); 7951 int i; 7952 for (i=0; i<N; i++) { 7953 if (mLaunchingProviders.get(i) == cpr) { 7954 break; 7955 } 7956 } 7957 7958 // If the provider is not already being launched, then get it 7959 // started. 7960 if (i >= N) { 7961 final long origId = Binder.clearCallingIdentity(); 7962 7963 try { 7964 // Content provider is now in use, its package can't be stopped. 7965 try { 7966 AppGlobals.getPackageManager().setPackageStoppedState( 7967 cpr.appInfo.packageName, false, userId); 7968 } catch (RemoteException e) { 7969 } catch (IllegalArgumentException e) { 7970 Slog.w(TAG, "Failed trying to unstop package " 7971 + cpr.appInfo.packageName + ": " + e); 7972 } 7973 7974 // Use existing process if already started 7975 ProcessRecord proc = getProcessRecordLocked( 7976 cpi.processName, cpr.appInfo.uid, false); 7977 if (proc != null && proc.thread != null) { 7978 if (DEBUG_PROVIDER) { 7979 Slog.d(TAG, "Installing in existing process " + proc); 7980 } 7981 proc.pubProviders.put(cpi.name, cpr); 7982 try { 7983 proc.thread.scheduleInstallProvider(cpi); 7984 } catch (RemoteException e) { 7985 } 7986 } else { 7987 proc = startProcessLocked(cpi.processName, 7988 cpr.appInfo, false, 0, "content provider", 7989 new ComponentName(cpi.applicationInfo.packageName, 7990 cpi.name), false, false, false); 7991 if (proc == null) { 7992 Slog.w(TAG, "Unable to launch app " 7993 + cpi.applicationInfo.packageName + "/" 7994 + cpi.applicationInfo.uid + " for provider " 7995 + name + ": process is bad"); 7996 return null; 7997 } 7998 } 7999 cpr.launchingApp = proc; 8000 mLaunchingProviders.add(cpr); 8001 } finally { 8002 Binder.restoreCallingIdentity(origId); 8003 } 8004 } 8005 8006 // Make sure the provider is published (the same provider class 8007 // may be published under multiple names). 8008 if (firstClass) { 8009 mProviderMap.putProviderByClass(comp, cpr); 8010 } 8011 8012 mProviderMap.putProviderByName(name, cpr); 8013 conn = incProviderCountLocked(r, cpr, token, stable); 8014 if (conn != null) { 8015 conn.waiting = true; 8016 } 8017 } 8018 } 8019 8020 // Wait for the provider to be published... 8021 synchronized (cpr) { 8022 while (cpr.provider == null) { 8023 if (cpr.launchingApp == null) { 8024 Slog.w(TAG, "Unable to launch app " 8025 + cpi.applicationInfo.packageName + "/" 8026 + cpi.applicationInfo.uid + " for provider " 8027 + name + ": launching app became null"); 8028 EventLog.writeEvent(EventLogTags.AM_PROVIDER_LOST_PROCESS, 8029 UserHandle.getUserId(cpi.applicationInfo.uid), 8030 cpi.applicationInfo.packageName, 8031 cpi.applicationInfo.uid, name); 8032 return null; 8033 } 8034 try { 8035 if (DEBUG_MU) { 8036 Slog.v(TAG_MU, "Waiting to start provider " + cpr + " launchingApp=" 8037 + cpr.launchingApp); 8038 } 8039 if (conn != null) { 8040 conn.waiting = true; 8041 } 8042 cpr.wait(); 8043 } catch (InterruptedException ex) { 8044 } finally { 8045 if (conn != null) { 8046 conn.waiting = false; 8047 } 8048 } 8049 } 8050 } 8051 return cpr != null ? cpr.newHolder(conn) : null; 8052 } 8053 8054 public final ContentProviderHolder getContentProvider( 8055 IApplicationThread caller, String name, int userId, boolean stable) { 8056 enforceNotIsolatedCaller("getContentProvider"); 8057 if (caller == null) { 8058 String msg = "null IApplicationThread when getting content provider " 8059 + name; 8060 Slog.w(TAG, msg); 8061 throw new SecurityException(msg); 8062 } 8063 8064 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 8065 false, true, "getContentProvider", null); 8066 return getContentProviderImpl(caller, name, null, stable, userId); 8067 } 8068 8069 public ContentProviderHolder getContentProviderExternal( 8070 String name, int userId, IBinder token) { 8071 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 8072 "Do not have permission in call getContentProviderExternal()"); 8073 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), userId, 8074 false, true, "getContentProvider", null); 8075 return getContentProviderExternalUnchecked(name, token, userId); 8076 } 8077 8078 private ContentProviderHolder getContentProviderExternalUnchecked(String name, 8079 IBinder token, int userId) { 8080 return getContentProviderImpl(null, name, token, true, userId); 8081 } 8082 8083 /** 8084 * Drop a content provider from a ProcessRecord's bookkeeping 8085 */ 8086 public void removeContentProvider(IBinder connection, boolean stable) { 8087 enforceNotIsolatedCaller("removeContentProvider"); 8088 long ident = Binder.clearCallingIdentity(); 8089 try { 8090 synchronized (this) { 8091 ContentProviderConnection conn; 8092 try { 8093 conn = (ContentProviderConnection)connection; 8094 } catch (ClassCastException e) { 8095 String msg ="removeContentProvider: " + connection 8096 + " not a ContentProviderConnection"; 8097 Slog.w(TAG, msg); 8098 throw new IllegalArgumentException(msg); 8099 } 8100 if (conn == null) { 8101 throw new NullPointerException("connection is null"); 8102 } 8103 if (decProviderCountLocked(conn, null, null, stable)) { 8104 updateOomAdjLocked(); 8105 } 8106 } 8107 } finally { 8108 Binder.restoreCallingIdentity(ident); 8109 } 8110 } 8111 8112 public void removeContentProviderExternal(String name, IBinder token) { 8113 enforceCallingPermission(android.Manifest.permission.ACCESS_CONTENT_PROVIDERS_EXTERNALLY, 8114 "Do not have permission in call removeContentProviderExternal()"); 8115 removeContentProviderExternalUnchecked(name, token, UserHandle.getCallingUserId()); 8116 } 8117 8118 private void removeContentProviderExternalUnchecked(String name, IBinder token, int userId) { 8119 synchronized (this) { 8120 ContentProviderRecord cpr = mProviderMap.getProviderByName(name, userId); 8121 if(cpr == null) { 8122 //remove from mProvidersByClass 8123 if(localLOGV) Slog.v(TAG, name+" content provider not found in providers list"); 8124 return; 8125 } 8126 8127 //update content provider record entry info 8128 ComponentName comp = new ComponentName(cpr.info.packageName, cpr.info.name); 8129 ContentProviderRecord localCpr = mProviderMap.getProviderByClass(comp, userId); 8130 if (localCpr.hasExternalProcessHandles()) { 8131 if (localCpr.removeExternalProcessHandleLocked(token)) { 8132 updateOomAdjLocked(); 8133 } else { 8134 Slog.e(TAG, "Attmpt to remove content provider " + localCpr 8135 + " with no external reference for token: " 8136 + token + "."); 8137 } 8138 } else { 8139 Slog.e(TAG, "Attmpt to remove content provider: " + localCpr 8140 + " with no external references."); 8141 } 8142 } 8143 } 8144 8145 public final void publishContentProviders(IApplicationThread caller, 8146 List<ContentProviderHolder> providers) { 8147 if (providers == null) { 8148 return; 8149 } 8150 8151 enforceNotIsolatedCaller("publishContentProviders"); 8152 synchronized (this) { 8153 final ProcessRecord r = getRecordForAppLocked(caller); 8154 if (DEBUG_MU) 8155 Slog.v(TAG_MU, "ProcessRecord uid = " + r.uid); 8156 if (r == null) { 8157 throw new SecurityException( 8158 "Unable to find app for caller " + caller 8159 + " (pid=" + Binder.getCallingPid() 8160 + ") when publishing content providers"); 8161 } 8162 8163 final long origId = Binder.clearCallingIdentity(); 8164 8165 final int N = providers.size(); 8166 for (int i=0; i<N; i++) { 8167 ContentProviderHolder src = providers.get(i); 8168 if (src == null || src.info == null || src.provider == null) { 8169 continue; 8170 } 8171 ContentProviderRecord dst = r.pubProviders.get(src.info.name); 8172 if (DEBUG_MU) 8173 Slog.v(TAG_MU, "ContentProviderRecord uid = " + dst.uid); 8174 if (dst != null) { 8175 ComponentName comp = new ComponentName(dst.info.packageName, dst.info.name); 8176 mProviderMap.putProviderByClass(comp, dst); 8177 String names[] = dst.info.authority.split(";"); 8178 for (int j = 0; j < names.length; j++) { 8179 mProviderMap.putProviderByName(names[j], dst); 8180 } 8181 8182 int NL = mLaunchingProviders.size(); 8183 int j; 8184 for (j=0; j<NL; j++) { 8185 if (mLaunchingProviders.get(j) == dst) { 8186 mLaunchingProviders.remove(j); 8187 j--; 8188 NL--; 8189 } 8190 } 8191 synchronized (dst) { 8192 dst.provider = src.provider; 8193 dst.proc = r; 8194 dst.notifyAll(); 8195 } 8196 updateOomAdjLocked(r); 8197 } 8198 } 8199 8200 Binder.restoreCallingIdentity(origId); 8201 } 8202 } 8203 8204 public boolean refContentProvider(IBinder connection, int stable, int unstable) { 8205 ContentProviderConnection conn; 8206 try { 8207 conn = (ContentProviderConnection)connection; 8208 } catch (ClassCastException e) { 8209 String msg ="refContentProvider: " + connection 8210 + " not a ContentProviderConnection"; 8211 Slog.w(TAG, msg); 8212 throw new IllegalArgumentException(msg); 8213 } 8214 if (conn == null) { 8215 throw new NullPointerException("connection is null"); 8216 } 8217 8218 synchronized (this) { 8219 if (stable > 0) { 8220 conn.numStableIncs += stable; 8221 } 8222 stable = conn.stableCount + stable; 8223 if (stable < 0) { 8224 throw new IllegalStateException("stableCount < 0: " + stable); 8225 } 8226 8227 if (unstable > 0) { 8228 conn.numUnstableIncs += unstable; 8229 } 8230 unstable = conn.unstableCount + unstable; 8231 if (unstable < 0) { 8232 throw new IllegalStateException("unstableCount < 0: " + unstable); 8233 } 8234 8235 if ((stable+unstable) <= 0) { 8236 throw new IllegalStateException("ref counts can't go to zero here: stable=" 8237 + stable + " unstable=" + unstable); 8238 } 8239 conn.stableCount = stable; 8240 conn.unstableCount = unstable; 8241 return !conn.dead; 8242 } 8243 } 8244 8245 public void unstableProviderDied(IBinder connection) { 8246 ContentProviderConnection conn; 8247 try { 8248 conn = (ContentProviderConnection)connection; 8249 } catch (ClassCastException e) { 8250 String msg ="refContentProvider: " + connection 8251 + " not a ContentProviderConnection"; 8252 Slog.w(TAG, msg); 8253 throw new IllegalArgumentException(msg); 8254 } 8255 if (conn == null) { 8256 throw new NullPointerException("connection is null"); 8257 } 8258 8259 // Safely retrieve the content provider associated with the connection. 8260 IContentProvider provider; 8261 synchronized (this) { 8262 provider = conn.provider.provider; 8263 } 8264 8265 if (provider == null) { 8266 // Um, yeah, we're way ahead of you. 8267 return; 8268 } 8269 8270 // Make sure the caller is being honest with us. 8271 if (provider.asBinder().pingBinder()) { 8272 // Er, no, still looks good to us. 8273 synchronized (this) { 8274 Slog.w(TAG, "unstableProviderDied: caller " + Binder.getCallingUid() 8275 + " says " + conn + " died, but we don't agree"); 8276 return; 8277 } 8278 } 8279 8280 // Well look at that! It's dead! 8281 synchronized (this) { 8282 if (conn.provider.provider != provider) { 8283 // But something changed... good enough. 8284 return; 8285 } 8286 8287 ProcessRecord proc = conn.provider.proc; 8288 if (proc == null || proc.thread == null) { 8289 // Seems like the process is already cleaned up. 8290 return; 8291 } 8292 8293 // As far as we're concerned, this is just like receiving a 8294 // death notification... just a bit prematurely. 8295 Slog.i(TAG, "Process " + proc.processName + " (pid " + proc.pid 8296 + ") early provider death"); 8297 final long ident = Binder.clearCallingIdentity(); 8298 try { 8299 appDiedLocked(proc, proc.pid, proc.thread); 8300 } finally { 8301 Binder.restoreCallingIdentity(ident); 8302 } 8303 } 8304 } 8305 8306 @Override 8307 public void appNotRespondingViaProvider(IBinder connection) { 8308 enforceCallingPermission( 8309 android.Manifest.permission.REMOVE_TASKS, "appNotRespondingViaProvider()"); 8310 8311 final ContentProviderConnection conn = (ContentProviderConnection) connection; 8312 if (conn == null) { 8313 Slog.w(TAG, "ContentProviderConnection is null"); 8314 return; 8315 } 8316 8317 final ProcessRecord host = conn.provider.proc; 8318 if (host == null) { 8319 Slog.w(TAG, "Failed to find hosting ProcessRecord"); 8320 return; 8321 } 8322 8323 final long token = Binder.clearCallingIdentity(); 8324 try { 8325 appNotResponding(host, null, null, false, "ContentProvider not responding"); 8326 } finally { 8327 Binder.restoreCallingIdentity(token); 8328 } 8329 } 8330 8331 public final void installSystemProviders() { 8332 List<ProviderInfo> providers; 8333 synchronized (this) { 8334 ProcessRecord app = mProcessNames.get("system", Process.SYSTEM_UID); 8335 providers = generateApplicationProvidersLocked(app); 8336 if (providers != null) { 8337 for (int i=providers.size()-1; i>=0; i--) { 8338 ProviderInfo pi = (ProviderInfo)providers.get(i); 8339 if ((pi.applicationInfo.flags&ApplicationInfo.FLAG_SYSTEM) == 0) { 8340 Slog.w(TAG, "Not installing system proc provider " + pi.name 8341 + ": not system .apk"); 8342 providers.remove(i); 8343 } 8344 } 8345 } 8346 } 8347 if (providers != null) { 8348 mSystemThread.installSystemProviders(providers); 8349 } 8350 8351 mCoreSettingsObserver = new CoreSettingsObserver(this); 8352 8353 mUsageStatsService.monitorPackages(); 8354 } 8355 8356 /** 8357 * Allows app to retrieve the MIME type of a URI without having permission 8358 * to access its content provider. 8359 * 8360 * CTS tests for this functionality can be run with "runtest cts-appsecurity". 8361 * 8362 * Test cases are at cts/tests/appsecurity-tests/test-apps/UsePermissionDiffCert/ 8363 * src/com/android/cts/usespermissiondiffcertapp/AccessPermissionWithDiffSigTest.java 8364 */ 8365 public String getProviderMimeType(Uri uri, int userId) { 8366 enforceNotIsolatedCaller("getProviderMimeType"); 8367 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 8368 userId, false, true, "getProviderMimeType", null); 8369 final String name = uri.getAuthority(); 8370 final long ident = Binder.clearCallingIdentity(); 8371 ContentProviderHolder holder = null; 8372 8373 try { 8374 holder = getContentProviderExternalUnchecked(name, null, userId); 8375 if (holder != null) { 8376 return holder.provider.getType(uri); 8377 } 8378 } catch (RemoteException e) { 8379 Log.w(TAG, "Content provider dead retrieving " + uri, e); 8380 return null; 8381 } finally { 8382 if (holder != null) { 8383 removeContentProviderExternalUnchecked(name, null, userId); 8384 } 8385 Binder.restoreCallingIdentity(ident); 8386 } 8387 8388 return null; 8389 } 8390 8391 // ========================================================= 8392 // GLOBAL MANAGEMENT 8393 // ========================================================= 8394 8395 final ProcessRecord newProcessRecordLocked(ApplicationInfo info, String customProcess, 8396 boolean isolated) { 8397 String proc = customProcess != null ? customProcess : info.processName; 8398 BatteryStatsImpl.Uid.Proc ps = null; 8399 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 8400 int uid = info.uid; 8401 if (isolated) { 8402 int userId = UserHandle.getUserId(uid); 8403 int stepsLeft = Process.LAST_ISOLATED_UID - Process.FIRST_ISOLATED_UID + 1; 8404 while (true) { 8405 if (mNextIsolatedProcessUid < Process.FIRST_ISOLATED_UID 8406 || mNextIsolatedProcessUid > Process.LAST_ISOLATED_UID) { 8407 mNextIsolatedProcessUid = Process.FIRST_ISOLATED_UID; 8408 } 8409 uid = UserHandle.getUid(userId, mNextIsolatedProcessUid); 8410 mNextIsolatedProcessUid++; 8411 if (mIsolatedProcesses.indexOfKey(uid) < 0) { 8412 // No process for this uid, use it. 8413 break; 8414 } 8415 stepsLeft--; 8416 if (stepsLeft <= 0) { 8417 return null; 8418 } 8419 } 8420 } 8421 return new ProcessRecord(stats, info, proc, uid); 8422 } 8423 8424 final ProcessRecord addAppLocked(ApplicationInfo info, boolean isolated) { 8425 ProcessRecord app; 8426 if (!isolated) { 8427 app = getProcessRecordLocked(info.processName, info.uid, true); 8428 } else { 8429 app = null; 8430 } 8431 8432 if (app == null) { 8433 app = newProcessRecordLocked(info, null, isolated); 8434 mProcessNames.put(info.processName, app.uid, app); 8435 if (isolated) { 8436 mIsolatedProcesses.put(app.uid, app); 8437 } 8438 updateLruProcessLocked(app, false, null); 8439 updateOomAdjLocked(); 8440 } 8441 8442 // This package really, really can not be stopped. 8443 try { 8444 AppGlobals.getPackageManager().setPackageStoppedState( 8445 info.packageName, false, UserHandle.getUserId(app.uid)); 8446 } catch (RemoteException e) { 8447 } catch (IllegalArgumentException e) { 8448 Slog.w(TAG, "Failed trying to unstop package " 8449 + info.packageName + ": " + e); 8450 } 8451 8452 if ((info.flags&(ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) 8453 == (ApplicationInfo.FLAG_SYSTEM|ApplicationInfo.FLAG_PERSISTENT)) { 8454 app.persistent = true; 8455 app.maxAdj = ProcessList.PERSISTENT_PROC_ADJ; 8456 } 8457 if (app.thread == null && mPersistentStartingProcesses.indexOf(app) < 0) { 8458 mPersistentStartingProcesses.add(app); 8459 startProcessLocked(app, "added application", app.processName); 8460 } 8461 8462 return app; 8463 } 8464 8465 public void unhandledBack() { 8466 enforceCallingPermission(android.Manifest.permission.FORCE_BACK, 8467 "unhandledBack()"); 8468 8469 synchronized(this) { 8470 final long origId = Binder.clearCallingIdentity(); 8471 try { 8472 getFocusedStack().unhandledBackLocked(); 8473 } finally { 8474 Binder.restoreCallingIdentity(origId); 8475 } 8476 } 8477 } 8478 8479 public ParcelFileDescriptor openContentUri(Uri uri) throws RemoteException { 8480 enforceNotIsolatedCaller("openContentUri"); 8481 final int userId = UserHandle.getCallingUserId(); 8482 String name = uri.getAuthority(); 8483 ContentProviderHolder cph = getContentProviderExternalUnchecked(name, null, userId); 8484 ParcelFileDescriptor pfd = null; 8485 if (cph != null) { 8486 // We record the binder invoker's uid in thread-local storage before 8487 // going to the content provider to open the file. Later, in the code 8488 // that handles all permissions checks, we look for this uid and use 8489 // that rather than the Activity Manager's own uid. The effect is that 8490 // we do the check against the caller's permissions even though it looks 8491 // to the content provider like the Activity Manager itself is making 8492 // the request. 8493 sCallerIdentity.set(new Identity( 8494 Binder.getCallingPid(), Binder.getCallingUid())); 8495 try { 8496 pfd = cph.provider.openFile(null, uri, "r", null); 8497 } catch (FileNotFoundException e) { 8498 // do nothing; pfd will be returned null 8499 } finally { 8500 // Ensure that whatever happens, we clean up the identity state 8501 sCallerIdentity.remove(); 8502 } 8503 8504 // We've got the fd now, so we're done with the provider. 8505 removeContentProviderExternalUnchecked(name, null, userId); 8506 } else { 8507 Slog.d(TAG, "Failed to get provider for authority '" + name + "'"); 8508 } 8509 return pfd; 8510 } 8511 8512 // Actually is sleeping or shutting down or whatever else in the future 8513 // is an inactive state. 8514 public boolean isSleepingOrShuttingDown() { 8515 return mSleeping || mShuttingDown; 8516 } 8517 8518 public boolean isSleeping() { 8519 return mSleeping; 8520 } 8521 8522 void goingToSleep() { 8523 synchronized(this) { 8524 mWentToSleep = true; 8525 updateEventDispatchingLocked(); 8526 goToSleepIfNeededLocked(); 8527 } 8528 } 8529 8530 void finishRunningVoiceLocked() { 8531 if (mRunningVoice) { 8532 mRunningVoice = false; 8533 goToSleepIfNeededLocked(); 8534 } 8535 } 8536 8537 void goToSleepIfNeededLocked() { 8538 if (mWentToSleep && !mRunningVoice) { 8539 if (!mSleeping) { 8540 mSleeping = true; 8541 mStackSupervisor.goingToSleepLocked(); 8542 8543 // Initialize the wake times of all processes. 8544 checkExcessivePowerUsageLocked(false); 8545 mHandler.removeMessages(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 8546 Message nmsg = mHandler.obtainMessage(CHECK_EXCESSIVE_WAKE_LOCKS_MSG); 8547 mHandler.sendMessageDelayed(nmsg, POWER_CHECK_DELAY); 8548 } 8549 } 8550 } 8551 8552 @Override 8553 public boolean shutdown(int timeout) { 8554 if (checkCallingPermission(android.Manifest.permission.SHUTDOWN) 8555 != PackageManager.PERMISSION_GRANTED) { 8556 throw new SecurityException("Requires permission " 8557 + android.Manifest.permission.SHUTDOWN); 8558 } 8559 8560 boolean timedout = false; 8561 8562 synchronized(this) { 8563 mShuttingDown = true; 8564 updateEventDispatchingLocked(); 8565 timedout = mStackSupervisor.shutdownLocked(timeout); 8566 } 8567 8568 mAppOpsService.shutdown(); 8569 mUsageStatsService.shutdown(); 8570 mBatteryStatsService.shutdown(); 8571 synchronized (this) { 8572 mProcessStats.shutdownLocked(); 8573 } 8574 8575 return timedout; 8576 } 8577 8578 public final void activitySlept(IBinder token) { 8579 if (localLOGV) Slog.v(TAG, "Activity slept: token=" + token); 8580 8581 final long origId = Binder.clearCallingIdentity(); 8582 8583 synchronized (this) { 8584 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 8585 if (r != null) { 8586 mStackSupervisor.activitySleptLocked(r); 8587 } 8588 } 8589 8590 Binder.restoreCallingIdentity(origId); 8591 } 8592 8593 void logLockScreen(String msg) { 8594 if (DEBUG_LOCKSCREEN) Slog.d(TAG, Debug.getCallers(2) + ":" + msg + 8595 " mLockScreenShown=" + mLockScreenShown + " mWentToSleep=" + 8596 mWentToSleep + " mSleeping=" + mSleeping + " mDismissKeyguardOnNextActivity=" + 8597 mStackSupervisor.mDismissKeyguardOnNextActivity); 8598 } 8599 8600 private void comeOutOfSleepIfNeededLocked() { 8601 if ((!mWentToSleep && !mLockScreenShown) || mRunningVoice) { 8602 if (mSleeping) { 8603 mSleeping = false; 8604 mStackSupervisor.comeOutOfSleepIfNeededLocked(); 8605 } 8606 } 8607 } 8608 8609 void wakingUp() { 8610 synchronized(this) { 8611 mWentToSleep = false; 8612 updateEventDispatchingLocked(); 8613 comeOutOfSleepIfNeededLocked(); 8614 } 8615 } 8616 8617 void startRunningVoiceLocked() { 8618 if (!mRunningVoice) { 8619 mRunningVoice = true; 8620 comeOutOfSleepIfNeededLocked(); 8621 } 8622 } 8623 8624 private void updateEventDispatchingLocked() { 8625 mWindowManager.setEventDispatching(mBooted && !mWentToSleep && !mShuttingDown); 8626 } 8627 8628 public void setLockScreenShown(boolean shown) { 8629 if (checkCallingPermission(android.Manifest.permission.DEVICE_POWER) 8630 != PackageManager.PERMISSION_GRANTED) { 8631 throw new SecurityException("Requires permission " 8632 + android.Manifest.permission.DEVICE_POWER); 8633 } 8634 8635 synchronized(this) { 8636 long ident = Binder.clearCallingIdentity(); 8637 try { 8638 if (DEBUG_LOCKSCREEN) logLockScreen(" shown=" + shown); 8639 mLockScreenShown = shown; 8640 comeOutOfSleepIfNeededLocked(); 8641 } finally { 8642 Binder.restoreCallingIdentity(ident); 8643 } 8644 } 8645 } 8646 8647 public void stopAppSwitches() { 8648 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 8649 != PackageManager.PERMISSION_GRANTED) { 8650 throw new SecurityException("Requires permission " 8651 + android.Manifest.permission.STOP_APP_SWITCHES); 8652 } 8653 8654 synchronized(this) { 8655 mAppSwitchesAllowedTime = SystemClock.uptimeMillis() 8656 + APP_SWITCH_DELAY_TIME; 8657 mDidAppSwitch = false; 8658 mHandler.removeMessages(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 8659 Message msg = mHandler.obtainMessage(DO_PENDING_ACTIVITY_LAUNCHES_MSG); 8660 mHandler.sendMessageDelayed(msg, APP_SWITCH_DELAY_TIME); 8661 } 8662 } 8663 8664 public void resumeAppSwitches() { 8665 if (checkCallingPermission(android.Manifest.permission.STOP_APP_SWITCHES) 8666 != PackageManager.PERMISSION_GRANTED) { 8667 throw new SecurityException("Requires permission " 8668 + android.Manifest.permission.STOP_APP_SWITCHES); 8669 } 8670 8671 synchronized(this) { 8672 // Note that we don't execute any pending app switches... we will 8673 // let those wait until either the timeout, or the next start 8674 // activity request. 8675 mAppSwitchesAllowedTime = 0; 8676 } 8677 } 8678 8679 boolean checkAppSwitchAllowedLocked(int callingPid, int callingUid, 8680 String name) { 8681 if (mAppSwitchesAllowedTime < SystemClock.uptimeMillis()) { 8682 return true; 8683 } 8684 8685 final int perm = checkComponentPermission( 8686 android.Manifest.permission.STOP_APP_SWITCHES, callingPid, 8687 callingUid, -1, true); 8688 if (perm == PackageManager.PERMISSION_GRANTED) { 8689 return true; 8690 } 8691 8692 Slog.w(TAG, name + " request from " + callingUid + " stopped"); 8693 return false; 8694 } 8695 8696 public void setDebugApp(String packageName, boolean waitForDebugger, 8697 boolean persistent) { 8698 enforceCallingPermission(android.Manifest.permission.SET_DEBUG_APP, 8699 "setDebugApp()"); 8700 8701 long ident = Binder.clearCallingIdentity(); 8702 try { 8703 // Note that this is not really thread safe if there are multiple 8704 // callers into it at the same time, but that's not a situation we 8705 // care about. 8706 if (persistent) { 8707 final ContentResolver resolver = mContext.getContentResolver(); 8708 Settings.Global.putString( 8709 resolver, Settings.Global.DEBUG_APP, 8710 packageName); 8711 Settings.Global.putInt( 8712 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 8713 waitForDebugger ? 1 : 0); 8714 } 8715 8716 synchronized (this) { 8717 if (!persistent) { 8718 mOrigDebugApp = mDebugApp; 8719 mOrigWaitForDebugger = mWaitForDebugger; 8720 } 8721 mDebugApp = packageName; 8722 mWaitForDebugger = waitForDebugger; 8723 mDebugTransient = !persistent; 8724 if (packageName != null) { 8725 forceStopPackageLocked(packageName, -1, false, false, true, true, 8726 false, UserHandle.USER_ALL, "set debug app"); 8727 } 8728 } 8729 } finally { 8730 Binder.restoreCallingIdentity(ident); 8731 } 8732 } 8733 8734 void setOpenGlTraceApp(ApplicationInfo app, String processName) { 8735 synchronized (this) { 8736 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 8737 if (!isDebuggable) { 8738 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 8739 throw new SecurityException("Process not debuggable: " + app.packageName); 8740 } 8741 } 8742 8743 mOpenGlTraceApp = processName; 8744 } 8745 } 8746 8747 void setProfileApp(ApplicationInfo app, String processName, String profileFile, 8748 ParcelFileDescriptor profileFd, boolean autoStopProfiler) { 8749 synchronized (this) { 8750 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 8751 if (!isDebuggable) { 8752 if ((app.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 8753 throw new SecurityException("Process not debuggable: " + app.packageName); 8754 } 8755 } 8756 mProfileApp = processName; 8757 mProfileFile = profileFile; 8758 if (mProfileFd != null) { 8759 try { 8760 mProfileFd.close(); 8761 } catch (IOException e) { 8762 } 8763 mProfileFd = null; 8764 } 8765 mProfileFd = profileFd; 8766 mProfileType = 0; 8767 mAutoStopProfiler = autoStopProfiler; 8768 } 8769 } 8770 8771 @Override 8772 public void setAlwaysFinish(boolean enabled) { 8773 enforceCallingPermission(android.Manifest.permission.SET_ALWAYS_FINISH, 8774 "setAlwaysFinish()"); 8775 8776 Settings.Global.putInt( 8777 mContext.getContentResolver(), 8778 Settings.Global.ALWAYS_FINISH_ACTIVITIES, enabled ? 1 : 0); 8779 8780 synchronized (this) { 8781 mAlwaysFinishActivities = enabled; 8782 } 8783 } 8784 8785 @Override 8786 public void setActivityController(IActivityController controller) { 8787 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 8788 "setActivityController()"); 8789 synchronized (this) { 8790 mController = controller; 8791 Watchdog.getInstance().setActivityController(controller); 8792 } 8793 } 8794 8795 @Override 8796 public void setUserIsMonkey(boolean userIsMonkey) { 8797 synchronized (this) { 8798 synchronized (mPidsSelfLocked) { 8799 final int callingPid = Binder.getCallingPid(); 8800 ProcessRecord precessRecord = mPidsSelfLocked.get(callingPid); 8801 if (precessRecord == null) { 8802 throw new SecurityException("Unknown process: " + callingPid); 8803 } 8804 if (precessRecord.instrumentationUiAutomationConnection == null) { 8805 throw new SecurityException("Only an instrumentation process " 8806 + "with a UiAutomation can call setUserIsMonkey"); 8807 } 8808 } 8809 mUserIsMonkey = userIsMonkey; 8810 } 8811 } 8812 8813 @Override 8814 public boolean isUserAMonkey() { 8815 synchronized (this) { 8816 // If there is a controller also implies the user is a monkey. 8817 return (mUserIsMonkey || mController != null); 8818 } 8819 } 8820 8821 public void requestBugReport() { 8822 enforceCallingPermission(android.Manifest.permission.DUMP, "requestBugReport"); 8823 SystemProperties.set("ctl.start", "bugreport"); 8824 } 8825 8826 public static long getInputDispatchingTimeoutLocked(ActivityRecord r) { 8827 return r != null ? getInputDispatchingTimeoutLocked(r.app) : KEY_DISPATCHING_TIMEOUT; 8828 } 8829 8830 public static long getInputDispatchingTimeoutLocked(ProcessRecord r) { 8831 if (r != null && (r.instrumentationClass != null || r.usingWrapper)) { 8832 return INSTRUMENTATION_KEY_DISPATCHING_TIMEOUT; 8833 } 8834 return KEY_DISPATCHING_TIMEOUT; 8835 } 8836 8837 @Override 8838 public long inputDispatchingTimedOut(int pid, final boolean aboveSystem, String reason) { 8839 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 8840 != PackageManager.PERMISSION_GRANTED) { 8841 throw new SecurityException("Requires permission " 8842 + android.Manifest.permission.FILTER_EVENTS); 8843 } 8844 ProcessRecord proc; 8845 long timeout; 8846 synchronized (this) { 8847 synchronized (mPidsSelfLocked) { 8848 proc = mPidsSelfLocked.get(pid); 8849 } 8850 timeout = getInputDispatchingTimeoutLocked(proc); 8851 } 8852 8853 if (!inputDispatchingTimedOut(proc, null, null, aboveSystem, reason)) { 8854 return -1; 8855 } 8856 8857 return timeout; 8858 } 8859 8860 /** 8861 * Handle input dispatching timeouts. 8862 * Returns whether input dispatching should be aborted or not. 8863 */ 8864 public boolean inputDispatchingTimedOut(final ProcessRecord proc, 8865 final ActivityRecord activity, final ActivityRecord parent, 8866 final boolean aboveSystem, String reason) { 8867 if (checkCallingPermission(android.Manifest.permission.FILTER_EVENTS) 8868 != PackageManager.PERMISSION_GRANTED) { 8869 throw new SecurityException("Requires permission " 8870 + android.Manifest.permission.FILTER_EVENTS); 8871 } 8872 8873 final String annotation; 8874 if (reason == null) { 8875 annotation = "Input dispatching timed out"; 8876 } else { 8877 annotation = "Input dispatching timed out (" + reason + ")"; 8878 } 8879 8880 if (proc != null) { 8881 synchronized (this) { 8882 if (proc.debugging) { 8883 return false; 8884 } 8885 8886 if (mDidDexOpt) { 8887 // Give more time since we were dexopting. 8888 mDidDexOpt = false; 8889 return false; 8890 } 8891 8892 if (proc.instrumentationClass != null) { 8893 Bundle info = new Bundle(); 8894 info.putString("shortMsg", "keyDispatchingTimedOut"); 8895 info.putString("longMsg", annotation); 8896 finishInstrumentationLocked(proc, Activity.RESULT_CANCELED, info); 8897 return true; 8898 } 8899 } 8900 mHandler.post(new Runnable() { 8901 @Override 8902 public void run() { 8903 appNotResponding(proc, activity, parent, aboveSystem, annotation); 8904 } 8905 }); 8906 } 8907 8908 return true; 8909 } 8910 8911 public Bundle getAssistContextExtras(int requestType) { 8912 enforceCallingPermission(android.Manifest.permission.GET_TOP_ACTIVITY_INFO, 8913 "getAssistContextExtras()"); 8914 PendingAssistExtras pae; 8915 Bundle extras = new Bundle(); 8916 synchronized (this) { 8917 ActivityRecord activity = getFocusedStack().mResumedActivity; 8918 if (activity == null) { 8919 Slog.w(TAG, "getAssistContextExtras failed: no resumed activity"); 8920 return null; 8921 } 8922 extras.putString(Intent.EXTRA_ASSIST_PACKAGE, activity.packageName); 8923 if (activity.app == null || activity.app.thread == null) { 8924 Slog.w(TAG, "getAssistContextExtras failed: no process for " + activity); 8925 return extras; 8926 } 8927 if (activity.app.pid == Binder.getCallingPid()) { 8928 Slog.w(TAG, "getAssistContextExtras failed: request process same as " + activity); 8929 return extras; 8930 } 8931 pae = new PendingAssistExtras(activity); 8932 try { 8933 activity.app.thread.requestAssistContextExtras(activity.appToken, pae, 8934 requestType); 8935 mPendingAssistExtras.add(pae); 8936 mHandler.postDelayed(pae, PENDING_ASSIST_EXTRAS_TIMEOUT); 8937 } catch (RemoteException e) { 8938 Slog.w(TAG, "getAssistContextExtras failed: crash calling " + activity); 8939 return extras; 8940 } 8941 } 8942 synchronized (pae) { 8943 while (!pae.haveResult) { 8944 try { 8945 pae.wait(); 8946 } catch (InterruptedException e) { 8947 } 8948 } 8949 if (pae.result != null) { 8950 extras.putBundle(Intent.EXTRA_ASSIST_CONTEXT, pae.result); 8951 } 8952 } 8953 synchronized (this) { 8954 mPendingAssistExtras.remove(pae); 8955 mHandler.removeCallbacks(pae); 8956 } 8957 return extras; 8958 } 8959 8960 public void reportAssistContextExtras(IBinder token, Bundle extras) { 8961 PendingAssistExtras pae = (PendingAssistExtras)token; 8962 synchronized (pae) { 8963 pae.result = extras; 8964 pae.haveResult = true; 8965 pae.notifyAll(); 8966 } 8967 } 8968 8969 public void registerProcessObserver(IProcessObserver observer) { 8970 enforceCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER, 8971 "registerProcessObserver()"); 8972 synchronized (this) { 8973 mProcessObservers.register(observer); 8974 } 8975 } 8976 8977 @Override 8978 public void unregisterProcessObserver(IProcessObserver observer) { 8979 synchronized (this) { 8980 mProcessObservers.unregister(observer); 8981 } 8982 } 8983 8984 @Override 8985 public boolean convertFromTranslucent(IBinder token) { 8986 final long origId = Binder.clearCallingIdentity(); 8987 try { 8988 synchronized (this) { 8989 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 8990 if (r == null) { 8991 return false; 8992 } 8993 if (r.changeWindowTranslucency(true)) { 8994 mWindowManager.setAppFullscreen(token, true); 8995 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 8996 return true; 8997 } 8998 return false; 8999 } 9000 } finally { 9001 Binder.restoreCallingIdentity(origId); 9002 } 9003 } 9004 9005 @Override 9006 public boolean convertToTranslucent(IBinder token) { 9007 final long origId = Binder.clearCallingIdentity(); 9008 try { 9009 synchronized (this) { 9010 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9011 if (r == null) { 9012 return false; 9013 } 9014 if (r.changeWindowTranslucency(false)) { 9015 r.task.stack.convertToTranslucent(r); 9016 mWindowManager.setAppFullscreen(token, false); 9017 mStackSupervisor.ensureActivitiesVisibleLocked(null, 0); 9018 return true; 9019 } 9020 return false; 9021 } 9022 } finally { 9023 Binder.restoreCallingIdentity(origId); 9024 } 9025 } 9026 9027 @Override 9028 public void setImmersive(IBinder token, boolean immersive) { 9029 synchronized(this) { 9030 final ActivityRecord r = ActivityRecord.isInStackLocked(token); 9031 if (r == null) { 9032 throw new IllegalArgumentException(); 9033 } 9034 r.immersive = immersive; 9035 9036 // update associated state if we're frontmost 9037 if (r == mFocusedActivity) { 9038 if (DEBUG_IMMERSIVE) { 9039 Slog.d(TAG, "Frontmost changed immersion: "+ r); 9040 } 9041 applyUpdateLockStateLocked(r); 9042 } 9043 } 9044 } 9045 9046 @Override 9047 public boolean isImmersive(IBinder token) { 9048 synchronized (this) { 9049 ActivityRecord r = ActivityRecord.isInStackLocked(token); 9050 if (r == null) { 9051 throw new IllegalArgumentException(); 9052 } 9053 return r.immersive; 9054 } 9055 } 9056 9057 public boolean isTopActivityImmersive() { 9058 enforceNotIsolatedCaller("startActivity"); 9059 synchronized (this) { 9060 ActivityRecord r = getFocusedStack().topRunningActivityLocked(null); 9061 return (r != null) ? r.immersive : false; 9062 } 9063 } 9064 9065 public final void enterSafeMode() { 9066 synchronized(this) { 9067 // It only makes sense to do this before the system is ready 9068 // and started launching other packages. 9069 if (!mSystemReady) { 9070 try { 9071 AppGlobals.getPackageManager().enterSafeMode(); 9072 } catch (RemoteException e) { 9073 } 9074 } 9075 9076 mSafeMode = true; 9077 } 9078 } 9079 9080 public final void showSafeModeOverlay() { 9081 View v = LayoutInflater.from(mContext).inflate( 9082 com.android.internal.R.layout.safe_mode, null); 9083 WindowManager.LayoutParams lp = new WindowManager.LayoutParams(); 9084 lp.type = WindowManager.LayoutParams.TYPE_SECURE_SYSTEM_OVERLAY; 9085 lp.width = WindowManager.LayoutParams.WRAP_CONTENT; 9086 lp.height = WindowManager.LayoutParams.WRAP_CONTENT; 9087 lp.gravity = Gravity.BOTTOM | Gravity.START; 9088 lp.format = v.getBackground().getOpacity(); 9089 lp.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE 9090 | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE; 9091 lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS; 9092 ((WindowManager)mContext.getSystemService( 9093 Context.WINDOW_SERVICE)).addView(v, lp); 9094 } 9095 9096 public void noteWakeupAlarm(IIntentSender sender, int sourceUid, String sourcePkg) { 9097 if (!(sender instanceof PendingIntentRecord)) { 9098 return; 9099 } 9100 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 9101 synchronized (stats) { 9102 if (mBatteryStatsService.isOnBattery()) { 9103 mBatteryStatsService.enforceCallingPermission(); 9104 PendingIntentRecord rec = (PendingIntentRecord)sender; 9105 int MY_UID = Binder.getCallingUid(); 9106 int uid = rec.uid == MY_UID ? Process.SYSTEM_UID : rec.uid; 9107 BatteryStatsImpl.Uid.Pkg pkg = 9108 stats.getPackageStatsLocked(sourceUid >= 0 ? sourceUid : uid, 9109 sourcePkg != null ? sourcePkg : rec.key.packageName); 9110 pkg.incWakeupsLocked(); 9111 } 9112 } 9113 } 9114 9115 public boolean killPids(int[] pids, String pReason, boolean secure) { 9116 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9117 throw new SecurityException("killPids only available to the system"); 9118 } 9119 String reason = (pReason == null) ? "Unknown" : pReason; 9120 // XXX Note: don't acquire main activity lock here, because the window 9121 // manager calls in with its locks held. 9122 9123 boolean killed = false; 9124 synchronized (mPidsSelfLocked) { 9125 int[] types = new int[pids.length]; 9126 int worstType = 0; 9127 for (int i=0; i<pids.length; i++) { 9128 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 9129 if (proc != null) { 9130 int type = proc.setAdj; 9131 types[i] = type; 9132 if (type > worstType) { 9133 worstType = type; 9134 } 9135 } 9136 } 9137 9138 // If the worst oom_adj is somewhere in the cached proc LRU range, 9139 // then constrain it so we will kill all cached procs. 9140 if (worstType < ProcessList.CACHED_APP_MAX_ADJ 9141 && worstType > ProcessList.CACHED_APP_MIN_ADJ) { 9142 worstType = ProcessList.CACHED_APP_MIN_ADJ; 9143 } 9144 9145 // If this is not a secure call, don't let it kill processes that 9146 // are important. 9147 if (!secure && worstType < ProcessList.SERVICE_ADJ) { 9148 worstType = ProcessList.SERVICE_ADJ; 9149 } 9150 9151 Slog.w(TAG, "Killing processes " + reason + " at adjustment " + worstType); 9152 for (int i=0; i<pids.length; i++) { 9153 ProcessRecord proc = mPidsSelfLocked.get(pids[i]); 9154 if (proc == null) { 9155 continue; 9156 } 9157 int adj = proc.setAdj; 9158 if (adj >= worstType && !proc.killedByAm) { 9159 killUnneededProcessLocked(proc, reason); 9160 killed = true; 9161 } 9162 } 9163 } 9164 return killed; 9165 } 9166 9167 @Override 9168 public void killUid(int uid, String reason) { 9169 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9170 throw new SecurityException("killUid only available to the system"); 9171 } 9172 synchronized (this) { 9173 killPackageProcessesLocked(null, UserHandle.getAppId(uid), UserHandle.getUserId(uid), 9174 ProcessList.FOREGROUND_APP_ADJ-1, false, true, true, false, 9175 reason != null ? reason : "kill uid"); 9176 } 9177 } 9178 9179 @Override 9180 public boolean killProcessesBelowForeground(String reason) { 9181 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9182 throw new SecurityException("killProcessesBelowForeground() only available to system"); 9183 } 9184 9185 return killProcessesBelowAdj(ProcessList.FOREGROUND_APP_ADJ, reason); 9186 } 9187 9188 private boolean killProcessesBelowAdj(int belowAdj, String reason) { 9189 if (Binder.getCallingUid() != Process.SYSTEM_UID) { 9190 throw new SecurityException("killProcessesBelowAdj() only available to system"); 9191 } 9192 9193 boolean killed = false; 9194 synchronized (mPidsSelfLocked) { 9195 final int size = mPidsSelfLocked.size(); 9196 for (int i = 0; i < size; i++) { 9197 final int pid = mPidsSelfLocked.keyAt(i); 9198 final ProcessRecord proc = mPidsSelfLocked.valueAt(i); 9199 if (proc == null) continue; 9200 9201 final int adj = proc.setAdj; 9202 if (adj > belowAdj && !proc.killedByAm) { 9203 killUnneededProcessLocked(proc, reason); 9204 killed = true; 9205 } 9206 } 9207 } 9208 return killed; 9209 } 9210 9211 @Override 9212 public void hang(final IBinder who, boolean allowRestart) { 9213 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9214 != PackageManager.PERMISSION_GRANTED) { 9215 throw new SecurityException("Requires permission " 9216 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9217 } 9218 9219 final IBinder.DeathRecipient death = new DeathRecipient() { 9220 @Override 9221 public void binderDied() { 9222 synchronized (this) { 9223 notifyAll(); 9224 } 9225 } 9226 }; 9227 9228 try { 9229 who.linkToDeath(death, 0); 9230 } catch (RemoteException e) { 9231 Slog.w(TAG, "hang: given caller IBinder is already dead."); 9232 return; 9233 } 9234 9235 synchronized (this) { 9236 Watchdog.getInstance().setAllowRestart(allowRestart); 9237 Slog.i(TAG, "Hanging system process at request of pid " + Binder.getCallingPid()); 9238 synchronized (death) { 9239 while (who.isBinderAlive()) { 9240 try { 9241 death.wait(); 9242 } catch (InterruptedException e) { 9243 } 9244 } 9245 } 9246 Watchdog.getInstance().setAllowRestart(true); 9247 } 9248 } 9249 9250 @Override 9251 public void restart() { 9252 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9253 != PackageManager.PERMISSION_GRANTED) { 9254 throw new SecurityException("Requires permission " 9255 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9256 } 9257 9258 Log.i(TAG, "Sending shutdown broadcast..."); 9259 9260 BroadcastReceiver br = new BroadcastReceiver() { 9261 @Override public void onReceive(Context context, Intent intent) { 9262 // Now the broadcast is done, finish up the low-level shutdown. 9263 Log.i(TAG, "Shutting down activity manager..."); 9264 shutdown(10000); 9265 Log.i(TAG, "Shutdown complete, restarting!"); 9266 Process.killProcess(Process.myPid()); 9267 System.exit(10); 9268 } 9269 }; 9270 9271 // First send the high-level shut down broadcast. 9272 Intent intent = new Intent(Intent.ACTION_SHUTDOWN); 9273 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 9274 intent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 9275 /* For now we are not doing a clean shutdown, because things seem to get unhappy. 9276 mContext.sendOrderedBroadcastAsUser(intent, 9277 UserHandle.ALL, null, br, mHandler, 0, null, null); 9278 */ 9279 br.onReceive(mContext, intent); 9280 } 9281 9282 private long getLowRamTimeSinceIdle(long now) { 9283 return mLowRamTimeSinceLastIdle + (mLowRamStartTime > 0 ? (now-mLowRamStartTime) : 0); 9284 } 9285 9286 @Override 9287 public void performIdleMaintenance() { 9288 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 9289 != PackageManager.PERMISSION_GRANTED) { 9290 throw new SecurityException("Requires permission " 9291 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 9292 } 9293 9294 synchronized (this) { 9295 final long now = SystemClock.uptimeMillis(); 9296 final long timeSinceLastIdle = now - mLastIdleTime; 9297 final long lowRamSinceLastIdle = getLowRamTimeSinceIdle(now); 9298 mLastIdleTime = now; 9299 mLowRamTimeSinceLastIdle = 0; 9300 if (mLowRamStartTime != 0) { 9301 mLowRamStartTime = now; 9302 } 9303 9304 StringBuilder sb = new StringBuilder(128); 9305 sb.append("Idle maintenance over "); 9306 TimeUtils.formatDuration(timeSinceLastIdle, sb); 9307 sb.append(" low RAM for "); 9308 TimeUtils.formatDuration(lowRamSinceLastIdle, sb); 9309 Slog.i(TAG, sb.toString()); 9310 9311 // If at least 1/3 of our time since the last idle period has been spent 9312 // with RAM low, then we want to kill processes. 9313 boolean doKilling = lowRamSinceLastIdle > (timeSinceLastIdle/3); 9314 9315 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 9316 ProcessRecord proc = mLruProcesses.get(i); 9317 if (proc.notCachedSinceIdle) { 9318 if (proc.setProcState > ActivityManager.PROCESS_STATE_TOP 9319 && proc.setProcState <= ActivityManager.PROCESS_STATE_SERVICE) { 9320 if (doKilling && proc.initialIdlePss != 0 9321 && proc.lastPss > ((proc.initialIdlePss*3)/2)) { 9322 killUnneededProcessLocked(proc, "idle maint (pss " + proc.lastPss 9323 + " from " + proc.initialIdlePss + ")"); 9324 } 9325 } 9326 } else if (proc.setProcState < ActivityManager.PROCESS_STATE_HOME) { 9327 proc.notCachedSinceIdle = true; 9328 proc.initialIdlePss = 0; 9329 proc.nextPssTime = ProcessList.computeNextPssTime(proc.curProcState, true, 9330 isSleeping(), now); 9331 } 9332 } 9333 9334 mHandler.removeMessages(REQUEST_ALL_PSS_MSG); 9335 mHandler.sendEmptyMessageDelayed(REQUEST_ALL_PSS_MSG, 2*60*1000); 9336 } 9337 } 9338 9339 private void retrieveSettings() { 9340 final ContentResolver resolver = mContext.getContentResolver(); 9341 String debugApp = Settings.Global.getString( 9342 resolver, Settings.Global.DEBUG_APP); 9343 boolean waitForDebugger = Settings.Global.getInt( 9344 resolver, Settings.Global.WAIT_FOR_DEBUGGER, 0) != 0; 9345 boolean alwaysFinishActivities = Settings.Global.getInt( 9346 resolver, Settings.Global.ALWAYS_FINISH_ACTIVITIES, 0) != 0; 9347 boolean forceRtl = Settings.Global.getInt( 9348 resolver, Settings.Global.DEVELOPMENT_FORCE_RTL, 0) != 0; 9349 // Transfer any global setting for forcing RTL layout, into a System Property 9350 SystemProperties.set(Settings.Global.DEVELOPMENT_FORCE_RTL, forceRtl ? "1":"0"); 9351 9352 Configuration configuration = new Configuration(); 9353 Settings.System.getConfiguration(resolver, configuration); 9354 if (forceRtl) { 9355 // This will take care of setting the correct layout direction flags 9356 configuration.setLayoutDirection(configuration.locale); 9357 } 9358 9359 synchronized (this) { 9360 mDebugApp = mOrigDebugApp = debugApp; 9361 mWaitForDebugger = mOrigWaitForDebugger = waitForDebugger; 9362 mAlwaysFinishActivities = alwaysFinishActivities; 9363 // This happens before any activities are started, so we can 9364 // change mConfiguration in-place. 9365 updateConfigurationLocked(configuration, null, false, true); 9366 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Initial config: " + mConfiguration); 9367 } 9368 } 9369 9370 public boolean testIsSystemReady() { 9371 // no need to synchronize(this) just to read & return the value 9372 return mSystemReady; 9373 } 9374 9375 private static File getCalledPreBootReceiversFile() { 9376 File dataDir = Environment.getDataDirectory(); 9377 File systemDir = new File(dataDir, "system"); 9378 File fname = new File(systemDir, "called_pre_boots.dat"); 9379 return fname; 9380 } 9381 9382 static final int LAST_DONE_VERSION = 10000; 9383 9384 private static ArrayList<ComponentName> readLastDonePreBootReceivers() { 9385 ArrayList<ComponentName> lastDoneReceivers = new ArrayList<ComponentName>(); 9386 File file = getCalledPreBootReceiversFile(); 9387 FileInputStream fis = null; 9388 try { 9389 fis = new FileInputStream(file); 9390 DataInputStream dis = new DataInputStream(new BufferedInputStream(fis, 2048)); 9391 int fvers = dis.readInt(); 9392 if (fvers == LAST_DONE_VERSION) { 9393 String vers = dis.readUTF(); 9394 String codename = dis.readUTF(); 9395 String build = dis.readUTF(); 9396 if (android.os.Build.VERSION.RELEASE.equals(vers) 9397 && android.os.Build.VERSION.CODENAME.equals(codename) 9398 && android.os.Build.VERSION.INCREMENTAL.equals(build)) { 9399 int num = dis.readInt(); 9400 while (num > 0) { 9401 num--; 9402 String pkg = dis.readUTF(); 9403 String cls = dis.readUTF(); 9404 lastDoneReceivers.add(new ComponentName(pkg, cls)); 9405 } 9406 } 9407 } 9408 } catch (FileNotFoundException e) { 9409 } catch (IOException e) { 9410 Slog.w(TAG, "Failure reading last done pre-boot receivers", e); 9411 } finally { 9412 if (fis != null) { 9413 try { 9414 fis.close(); 9415 } catch (IOException e) { 9416 } 9417 } 9418 } 9419 return lastDoneReceivers; 9420 } 9421 9422 private static void writeLastDonePreBootReceivers(ArrayList<ComponentName> list) { 9423 File file = getCalledPreBootReceiversFile(); 9424 FileOutputStream fos = null; 9425 DataOutputStream dos = null; 9426 try { 9427 Slog.i(TAG, "Writing new set of last done pre-boot receivers..."); 9428 fos = new FileOutputStream(file); 9429 dos = new DataOutputStream(new BufferedOutputStream(fos, 2048)); 9430 dos.writeInt(LAST_DONE_VERSION); 9431 dos.writeUTF(android.os.Build.VERSION.RELEASE); 9432 dos.writeUTF(android.os.Build.VERSION.CODENAME); 9433 dos.writeUTF(android.os.Build.VERSION.INCREMENTAL); 9434 dos.writeInt(list.size()); 9435 for (int i=0; i<list.size(); i++) { 9436 dos.writeUTF(list.get(i).getPackageName()); 9437 dos.writeUTF(list.get(i).getClassName()); 9438 } 9439 } catch (IOException e) { 9440 Slog.w(TAG, "Failure writing last done pre-boot receivers", e); 9441 file.delete(); 9442 } finally { 9443 FileUtils.sync(fos); 9444 if (dos != null) { 9445 try { 9446 dos.close(); 9447 } catch (IOException e) { 9448 // TODO Auto-generated catch block 9449 e.printStackTrace(); 9450 } 9451 } 9452 } 9453 } 9454 9455 public void systemReady(final Runnable goingCallback) { 9456 synchronized(this) { 9457 if (mSystemReady) { 9458 if (goingCallback != null) goingCallback.run(); 9459 return; 9460 } 9461 9462 // Check to see if there are any update receivers to run. 9463 if (!mDidUpdate) { 9464 if (mWaitingUpdate) { 9465 return; 9466 } 9467 Intent intent = new Intent(Intent.ACTION_PRE_BOOT_COMPLETED); 9468 List<ResolveInfo> ris = null; 9469 try { 9470 ris = AppGlobals.getPackageManager().queryIntentReceivers( 9471 intent, null, 0, 0); 9472 } catch (RemoteException e) { 9473 } 9474 if (ris != null) { 9475 for (int i=ris.size()-1; i>=0; i--) { 9476 if ((ris.get(i).activityInfo.applicationInfo.flags 9477 &ApplicationInfo.FLAG_SYSTEM) == 0) { 9478 ris.remove(i); 9479 } 9480 } 9481 intent.addFlags(Intent.FLAG_RECEIVER_BOOT_UPGRADE); 9482 9483 ArrayList<ComponentName> lastDoneReceivers = readLastDonePreBootReceivers(); 9484 9485 final ArrayList<ComponentName> doneReceivers = new ArrayList<ComponentName>(); 9486 for (int i=0; i<ris.size(); i++) { 9487 ActivityInfo ai = ris.get(i).activityInfo; 9488 ComponentName comp = new ComponentName(ai.packageName, ai.name); 9489 if (lastDoneReceivers.contains(comp)) { 9490 // We already did the pre boot receiver for this app with the current 9491 // platform version, so don't do it again... 9492 ris.remove(i); 9493 i--; 9494 // ...however, do keep it as one that has been done, so we don't 9495 // forget about it when rewriting the file of last done receivers. 9496 doneReceivers.add(comp); 9497 } 9498 } 9499 9500 final int[] users = getUsersLocked(); 9501 for (int i=0; i<ris.size(); i++) { 9502 ActivityInfo ai = ris.get(i).activityInfo; 9503 ComponentName comp = new ComponentName(ai.packageName, ai.name); 9504 doneReceivers.add(comp); 9505 intent.setComponent(comp); 9506 for (int j=0; j<users.length; j++) { 9507 IIntentReceiver finisher = null; 9508 if (i == ris.size()-1 && j == users.length-1) { 9509 finisher = new IIntentReceiver.Stub() { 9510 public void performReceive(Intent intent, int resultCode, 9511 String data, Bundle extras, boolean ordered, 9512 boolean sticky, int sendingUser) { 9513 // The raw IIntentReceiver interface is called 9514 // with the AM lock held, so redispatch to 9515 // execute our code without the lock. 9516 mHandler.post(new Runnable() { 9517 public void run() { 9518 synchronized (ActivityManagerService.this) { 9519 mDidUpdate = true; 9520 } 9521 writeLastDonePreBootReceivers(doneReceivers); 9522 showBootMessage(mContext.getText( 9523 R.string.android_upgrading_complete), 9524 false); 9525 systemReady(goingCallback); 9526 } 9527 }); 9528 } 9529 }; 9530 } 9531 Slog.i(TAG, "Sending system update to " + intent.getComponent() 9532 + " for user " + users[j]); 9533 broadcastIntentLocked(null, null, intent, null, finisher, 9534 0, null, null, null, AppOpsManager.OP_NONE, 9535 true, false, MY_PID, Process.SYSTEM_UID, 9536 users[j]); 9537 if (finisher != null) { 9538 mWaitingUpdate = true; 9539 } 9540 } 9541 } 9542 } 9543 if (mWaitingUpdate) { 9544 return; 9545 } 9546 mDidUpdate = true; 9547 } 9548 9549 mAppOpsService.systemReady(); 9550 mSystemReady = true; 9551 } 9552 9553 ArrayList<ProcessRecord> procsToKill = null; 9554 synchronized(mPidsSelfLocked) { 9555 for (int i=mPidsSelfLocked.size()-1; i>=0; i--) { 9556 ProcessRecord proc = mPidsSelfLocked.valueAt(i); 9557 if (!isAllowedWhileBooting(proc.info)){ 9558 if (procsToKill == null) { 9559 procsToKill = new ArrayList<ProcessRecord>(); 9560 } 9561 procsToKill.add(proc); 9562 } 9563 } 9564 } 9565 9566 synchronized(this) { 9567 if (procsToKill != null) { 9568 for (int i=procsToKill.size()-1; i>=0; i--) { 9569 ProcessRecord proc = procsToKill.get(i); 9570 Slog.i(TAG, "Removing system update proc: " + proc); 9571 removeProcessLocked(proc, true, false, "system update done"); 9572 } 9573 } 9574 9575 // Now that we have cleaned up any update processes, we 9576 // are ready to start launching real processes and know that 9577 // we won't trample on them any more. 9578 mProcessesReady = true; 9579 } 9580 9581 Slog.i(TAG, "System now ready"); 9582 EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_AMS_READY, 9583 SystemClock.uptimeMillis()); 9584 9585 synchronized(this) { 9586 // Make sure we have no pre-ready processes sitting around. 9587 9588 if (mFactoryTest == FactoryTest.FACTORY_TEST_LOW_LEVEL) { 9589 ResolveInfo ri = mContext.getPackageManager() 9590 .resolveActivity(new Intent(Intent.ACTION_FACTORY_TEST), 9591 STOCK_PM_FLAGS); 9592 CharSequence errorMsg = null; 9593 if (ri != null) { 9594 ActivityInfo ai = ri.activityInfo; 9595 ApplicationInfo app = ai.applicationInfo; 9596 if ((app.flags&ApplicationInfo.FLAG_SYSTEM) != 0) { 9597 mTopAction = Intent.ACTION_FACTORY_TEST; 9598 mTopData = null; 9599 mTopComponent = new ComponentName(app.packageName, 9600 ai.name); 9601 } else { 9602 errorMsg = mContext.getResources().getText( 9603 com.android.internal.R.string.factorytest_not_system); 9604 } 9605 } else { 9606 errorMsg = mContext.getResources().getText( 9607 com.android.internal.R.string.factorytest_no_action); 9608 } 9609 if (errorMsg != null) { 9610 mTopAction = null; 9611 mTopData = null; 9612 mTopComponent = null; 9613 Message msg = Message.obtain(); 9614 msg.what = SHOW_FACTORY_ERROR_MSG; 9615 msg.getData().putCharSequence("msg", errorMsg); 9616 mHandler.sendMessage(msg); 9617 } 9618 } 9619 } 9620 9621 retrieveSettings(); 9622 9623 synchronized (this) { 9624 readGrantedUriPermissionsLocked(); 9625 } 9626 9627 if (goingCallback != null) goingCallback.run(); 9628 9629 mSystemServiceManager.startUser(mCurrentUserId); 9630 9631 synchronized (this) { 9632 if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) { 9633 try { 9634 List apps = AppGlobals.getPackageManager(). 9635 getPersistentApplications(STOCK_PM_FLAGS); 9636 if (apps != null) { 9637 int N = apps.size(); 9638 int i; 9639 for (i=0; i<N; i++) { 9640 ApplicationInfo info 9641 = (ApplicationInfo)apps.get(i); 9642 if (info != null && 9643 !info.packageName.equals("android")) { 9644 addAppLocked(info, false); 9645 } 9646 } 9647 } 9648 } catch (RemoteException ex) { 9649 // pm is in same process, this will never happen. 9650 } 9651 } 9652 9653 // Start up initial activity. 9654 mBooting = true; 9655 9656 try { 9657 if (AppGlobals.getPackageManager().hasSystemUidErrors()) { 9658 Message msg = Message.obtain(); 9659 msg.what = SHOW_UID_ERROR_MSG; 9660 mHandler.sendMessage(msg); 9661 } 9662 } catch (RemoteException e) { 9663 } 9664 9665 long ident = Binder.clearCallingIdentity(); 9666 try { 9667 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 9668 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 9669 | Intent.FLAG_RECEIVER_FOREGROUND); 9670 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 9671 broadcastIntentLocked(null, null, intent, 9672 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 9673 false, false, MY_PID, Process.SYSTEM_UID, mCurrentUserId); 9674 intent = new Intent(Intent.ACTION_USER_STARTING); 9675 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 9676 intent.putExtra(Intent.EXTRA_USER_HANDLE, mCurrentUserId); 9677 broadcastIntentLocked(null, null, intent, 9678 null, new IIntentReceiver.Stub() { 9679 @Override 9680 public void performReceive(Intent intent, int resultCode, String data, 9681 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 9682 throws RemoteException { 9683 } 9684 }, 0, null, null, 9685 android.Manifest.permission.INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 9686 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 9687 } catch (Throwable t) { 9688 Slog.wtf(TAG, "Failed sending first user broadcasts", t); 9689 } finally { 9690 Binder.restoreCallingIdentity(ident); 9691 } 9692 mStackSupervisor.resumeTopActivitiesLocked(); 9693 sendUserSwitchBroadcastsLocked(-1, mCurrentUserId); 9694 } 9695 } 9696 9697 private boolean makeAppCrashingLocked(ProcessRecord app, 9698 String shortMsg, String longMsg, String stackTrace) { 9699 app.crashing = true; 9700 app.crashingReport = generateProcessError(app, 9701 ActivityManager.ProcessErrorStateInfo.CRASHED, null, shortMsg, longMsg, stackTrace); 9702 startAppProblemLocked(app); 9703 app.stopFreezingAllLocked(); 9704 return handleAppCrashLocked(app, shortMsg, longMsg, stackTrace); 9705 } 9706 9707 private void makeAppNotRespondingLocked(ProcessRecord app, 9708 String activity, String shortMsg, String longMsg) { 9709 app.notResponding = true; 9710 app.notRespondingReport = generateProcessError(app, 9711 ActivityManager.ProcessErrorStateInfo.NOT_RESPONDING, 9712 activity, shortMsg, longMsg, null); 9713 startAppProblemLocked(app); 9714 app.stopFreezingAllLocked(); 9715 } 9716 9717 /** 9718 * Generate a process error record, suitable for attachment to a ProcessRecord. 9719 * 9720 * @param app The ProcessRecord in which the error occurred. 9721 * @param condition Crashing, Application Not Responding, etc. Values are defined in 9722 * ActivityManager.AppErrorStateInfo 9723 * @param activity The activity associated with the crash, if known. 9724 * @param shortMsg Short message describing the crash. 9725 * @param longMsg Long message describing the crash. 9726 * @param stackTrace Full crash stack trace, may be null. 9727 * 9728 * @return Returns a fully-formed AppErrorStateInfo record. 9729 */ 9730 private ActivityManager.ProcessErrorStateInfo generateProcessError(ProcessRecord app, 9731 int condition, String activity, String shortMsg, String longMsg, String stackTrace) { 9732 ActivityManager.ProcessErrorStateInfo report = new ActivityManager.ProcessErrorStateInfo(); 9733 9734 report.condition = condition; 9735 report.processName = app.processName; 9736 report.pid = app.pid; 9737 report.uid = app.info.uid; 9738 report.tag = activity; 9739 report.shortMsg = shortMsg; 9740 report.longMsg = longMsg; 9741 report.stackTrace = stackTrace; 9742 9743 return report; 9744 } 9745 9746 void killAppAtUsersRequest(ProcessRecord app, Dialog fromDialog) { 9747 synchronized (this) { 9748 app.crashing = false; 9749 app.crashingReport = null; 9750 app.notResponding = false; 9751 app.notRespondingReport = null; 9752 if (app.anrDialog == fromDialog) { 9753 app.anrDialog = null; 9754 } 9755 if (app.waitDialog == fromDialog) { 9756 app.waitDialog = null; 9757 } 9758 if (app.pid > 0 && app.pid != MY_PID) { 9759 handleAppCrashLocked(app, null, null, null); 9760 killUnneededProcessLocked(app, "user request after error"); 9761 } 9762 } 9763 } 9764 9765 private boolean handleAppCrashLocked(ProcessRecord app, String shortMsg, String longMsg, 9766 String stackTrace) { 9767 long now = SystemClock.uptimeMillis(); 9768 9769 Long crashTime; 9770 if (!app.isolated) { 9771 crashTime = mProcessCrashTimes.get(app.info.processName, app.uid); 9772 } else { 9773 crashTime = null; 9774 } 9775 if (crashTime != null && now < crashTime+ProcessList.MIN_CRASH_INTERVAL) { 9776 // This process loses! 9777 Slog.w(TAG, "Process " + app.info.processName 9778 + " has crashed too many times: killing!"); 9779 EventLog.writeEvent(EventLogTags.AM_PROCESS_CRASHED_TOO_MUCH, 9780 app.userId, app.info.processName, app.uid); 9781 mStackSupervisor.handleAppCrashLocked(app); 9782 if (!app.persistent) { 9783 // We don't want to start this process again until the user 9784 // explicitly does so... but for persistent process, we really 9785 // need to keep it running. If a persistent process is actually 9786 // repeatedly crashing, then badness for everyone. 9787 EventLog.writeEvent(EventLogTags.AM_PROC_BAD, app.userId, app.uid, 9788 app.info.processName); 9789 if (!app.isolated) { 9790 // XXX We don't have a way to mark isolated processes 9791 // as bad, since they don't have a peristent identity. 9792 mBadProcesses.put(app.info.processName, app.uid, 9793 new BadProcessInfo(now, shortMsg, longMsg, stackTrace)); 9794 mProcessCrashTimes.remove(app.info.processName, app.uid); 9795 } 9796 app.bad = true; 9797 app.removed = true; 9798 // Don't let services in this process be restarted and potentially 9799 // annoy the user repeatedly. Unless it is persistent, since those 9800 // processes run critical code. 9801 removeProcessLocked(app, false, false, "crash"); 9802 mStackSupervisor.resumeTopActivitiesLocked(); 9803 return false; 9804 } 9805 mStackSupervisor.resumeTopActivitiesLocked(); 9806 } else { 9807 mStackSupervisor.finishTopRunningActivityLocked(app); 9808 } 9809 9810 // Bump up the crash count of any services currently running in the proc. 9811 for (int i=app.services.size()-1; i>=0; i--) { 9812 // Any services running in the application need to be placed 9813 // back in the pending list. 9814 ServiceRecord sr = app.services.valueAt(i); 9815 sr.crashCount++; 9816 } 9817 9818 // If the crashing process is what we consider to be the "home process" and it has been 9819 // replaced by a third-party app, clear the package preferred activities from packages 9820 // with a home activity running in the process to prevent a repeatedly crashing app 9821 // from blocking the user to manually clear the list. 9822 final ArrayList<ActivityRecord> activities = app.activities; 9823 if (app == mHomeProcess && activities.size() > 0 9824 && (mHomeProcess.info.flags & ApplicationInfo.FLAG_SYSTEM) == 0) { 9825 for (int activityNdx = activities.size() - 1; activityNdx >= 0; --activityNdx) { 9826 final ActivityRecord r = activities.get(activityNdx); 9827 if (r.isHomeActivity()) { 9828 Log.i(TAG, "Clearing package preferred activities from " + r.packageName); 9829 try { 9830 ActivityThread.getPackageManager() 9831 .clearPackagePreferredActivities(r.packageName); 9832 } catch (RemoteException c) { 9833 // pm is in same process, this will never happen. 9834 } 9835 } 9836 } 9837 } 9838 9839 if (!app.isolated) { 9840 // XXX Can't keep track of crash times for isolated processes, 9841 // because they don't have a perisistent identity. 9842 mProcessCrashTimes.put(app.info.processName, app.uid, now); 9843 } 9844 9845 return true; 9846 } 9847 9848 void startAppProblemLocked(ProcessRecord app) { 9849 if (app.userId == mCurrentUserId) { 9850 app.errorReportReceiver = ApplicationErrorReport.getErrorReportReceiver( 9851 mContext, app.info.packageName, app.info.flags); 9852 } else { 9853 // If this app is not running under the current user, then we 9854 // can't give it a report button because that would require 9855 // launching the report UI under a different user. 9856 app.errorReportReceiver = null; 9857 } 9858 skipCurrentReceiverLocked(app); 9859 } 9860 9861 void skipCurrentReceiverLocked(ProcessRecord app) { 9862 for (BroadcastQueue queue : mBroadcastQueues) { 9863 queue.skipCurrentReceiverLocked(app); 9864 } 9865 } 9866 9867 /** 9868 * Used by {@link com.android.internal.os.RuntimeInit} to report when an application crashes. 9869 * The application process will exit immediately after this call returns. 9870 * @param app object of the crashing app, null for the system server 9871 * @param crashInfo describing the exception 9872 */ 9873 public void handleApplicationCrash(IBinder app, ApplicationErrorReport.CrashInfo crashInfo) { 9874 ProcessRecord r = findAppProcess(app, "Crash"); 9875 final String processName = app == null ? "system_server" 9876 : (r == null ? "unknown" : r.processName); 9877 9878 handleApplicationCrashInner("crash", r, processName, crashInfo); 9879 } 9880 9881 /* Native crash reporting uses this inner version because it needs to be somewhat 9882 * decoupled from the AM-managed cleanup lifecycle 9883 */ 9884 void handleApplicationCrashInner(String eventType, ProcessRecord r, String processName, 9885 ApplicationErrorReport.CrashInfo crashInfo) { 9886 EventLog.writeEvent(EventLogTags.AM_CRASH, Binder.getCallingPid(), 9887 UserHandle.getUserId(Binder.getCallingUid()), processName, 9888 r == null ? -1 : r.info.flags, 9889 crashInfo.exceptionClassName, 9890 crashInfo.exceptionMessage, 9891 crashInfo.throwFileName, 9892 crashInfo.throwLineNumber); 9893 9894 addErrorToDropBox(eventType, r, processName, null, null, null, null, null, crashInfo); 9895 9896 crashApplication(r, crashInfo); 9897 } 9898 9899 public void handleApplicationStrictModeViolation( 9900 IBinder app, 9901 int violationMask, 9902 StrictMode.ViolationInfo info) { 9903 ProcessRecord r = findAppProcess(app, "StrictMode"); 9904 if (r == null) { 9905 return; 9906 } 9907 9908 if ((violationMask & StrictMode.PENALTY_DROPBOX) != 0) { 9909 Integer stackFingerprint = info.hashCode(); 9910 boolean logIt = true; 9911 synchronized (mAlreadyLoggedViolatedStacks) { 9912 if (mAlreadyLoggedViolatedStacks.contains(stackFingerprint)) { 9913 logIt = false; 9914 // TODO: sub-sample into EventLog for these, with 9915 // the info.durationMillis? Then we'd get 9916 // the relative pain numbers, without logging all 9917 // the stack traces repeatedly. We'd want to do 9918 // likewise in the client code, which also does 9919 // dup suppression, before the Binder call. 9920 } else { 9921 if (mAlreadyLoggedViolatedStacks.size() >= MAX_DUP_SUPPRESSED_STACKS) { 9922 mAlreadyLoggedViolatedStacks.clear(); 9923 } 9924 mAlreadyLoggedViolatedStacks.add(stackFingerprint); 9925 } 9926 } 9927 if (logIt) { 9928 logStrictModeViolationToDropBox(r, info); 9929 } 9930 } 9931 9932 if ((violationMask & StrictMode.PENALTY_DIALOG) != 0) { 9933 AppErrorResult result = new AppErrorResult(); 9934 synchronized (this) { 9935 final long origId = Binder.clearCallingIdentity(); 9936 9937 Message msg = Message.obtain(); 9938 msg.what = SHOW_STRICT_MODE_VIOLATION_MSG; 9939 HashMap<String, Object> data = new HashMap<String, Object>(); 9940 data.put("result", result); 9941 data.put("app", r); 9942 data.put("violationMask", violationMask); 9943 data.put("info", info); 9944 msg.obj = data; 9945 mHandler.sendMessage(msg); 9946 9947 Binder.restoreCallingIdentity(origId); 9948 } 9949 int res = result.get(); 9950 Slog.w(TAG, "handleApplicationStrictModeViolation; res=" + res); 9951 } 9952 } 9953 9954 // Depending on the policy in effect, there could be a bunch of 9955 // these in quick succession so we try to batch these together to 9956 // minimize disk writes, number of dropbox entries, and maximize 9957 // compression, by having more fewer, larger records. 9958 private void logStrictModeViolationToDropBox( 9959 ProcessRecord process, 9960 StrictMode.ViolationInfo info) { 9961 if (info == null) { 9962 return; 9963 } 9964 final boolean isSystemApp = process == null || 9965 (process.info.flags & (ApplicationInfo.FLAG_SYSTEM | 9966 ApplicationInfo.FLAG_UPDATED_SYSTEM_APP)) != 0; 9967 final String processName = process == null ? "unknown" : process.processName; 9968 final String dropboxTag = isSystemApp ? "system_app_strictmode" : "data_app_strictmode"; 9969 final DropBoxManager dbox = (DropBoxManager) 9970 mContext.getSystemService(Context.DROPBOX_SERVICE); 9971 9972 // Exit early if the dropbox isn't configured to accept this report type. 9973 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 9974 9975 boolean bufferWasEmpty; 9976 boolean needsFlush; 9977 final StringBuilder sb = isSystemApp ? mStrictModeBuffer : new StringBuilder(1024); 9978 synchronized (sb) { 9979 bufferWasEmpty = sb.length() == 0; 9980 appendDropBoxProcessHeaders(process, processName, sb); 9981 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 9982 sb.append("System-App: ").append(isSystemApp).append("\n"); 9983 sb.append("Uptime-Millis: ").append(info.violationUptimeMillis).append("\n"); 9984 if (info.violationNumThisLoop != 0) { 9985 sb.append("Loop-Violation-Number: ").append(info.violationNumThisLoop).append("\n"); 9986 } 9987 if (info.numAnimationsRunning != 0) { 9988 sb.append("Animations-Running: ").append(info.numAnimationsRunning).append("\n"); 9989 } 9990 if (info.broadcastIntentAction != null) { 9991 sb.append("Broadcast-Intent-Action: ").append(info.broadcastIntentAction).append("\n"); 9992 } 9993 if (info.durationMillis != -1) { 9994 sb.append("Duration-Millis: ").append(info.durationMillis).append("\n"); 9995 } 9996 if (info.numInstances != -1) { 9997 sb.append("Instance-Count: ").append(info.numInstances).append("\n"); 9998 } 9999 if (info.tags != null) { 10000 for (String tag : info.tags) { 10001 sb.append("Span-Tag: ").append(tag).append("\n"); 10002 } 10003 } 10004 sb.append("\n"); 10005 if (info.crashInfo != null && info.crashInfo.stackTrace != null) { 10006 sb.append(info.crashInfo.stackTrace); 10007 } 10008 sb.append("\n"); 10009 10010 // Only buffer up to ~64k. Various logging bits truncate 10011 // things at 128k. 10012 needsFlush = (sb.length() > 64 * 1024); 10013 } 10014 10015 // Flush immediately if the buffer's grown too large, or this 10016 // is a non-system app. Non-system apps are isolated with a 10017 // different tag & policy and not batched. 10018 // 10019 // Batching is useful during internal testing with 10020 // StrictMode settings turned up high. Without batching, 10021 // thousands of separate files could be created on boot. 10022 if (!isSystemApp || needsFlush) { 10023 new Thread("Error dump: " + dropboxTag) { 10024 @Override 10025 public void run() { 10026 String report; 10027 synchronized (sb) { 10028 report = sb.toString(); 10029 sb.delete(0, sb.length()); 10030 sb.trimToSize(); 10031 } 10032 if (report.length() != 0) { 10033 dbox.addText(dropboxTag, report); 10034 } 10035 } 10036 }.start(); 10037 return; 10038 } 10039 10040 // System app batching: 10041 if (!bufferWasEmpty) { 10042 // An existing dropbox-writing thread is outstanding, so 10043 // we don't need to start it up. The existing thread will 10044 // catch the buffer appends we just did. 10045 return; 10046 } 10047 10048 // Worker thread to both batch writes and to avoid blocking the caller on I/O. 10049 // (After this point, we shouldn't access AMS internal data structures.) 10050 new Thread("Error dump: " + dropboxTag) { 10051 @Override 10052 public void run() { 10053 // 5 second sleep to let stacks arrive and be batched together 10054 try { 10055 Thread.sleep(5000); // 5 seconds 10056 } catch (InterruptedException e) {} 10057 10058 String errorReport; 10059 synchronized (mStrictModeBuffer) { 10060 errorReport = mStrictModeBuffer.toString(); 10061 if (errorReport.length() == 0) { 10062 return; 10063 } 10064 mStrictModeBuffer.delete(0, mStrictModeBuffer.length()); 10065 mStrictModeBuffer.trimToSize(); 10066 } 10067 dbox.addText(dropboxTag, errorReport); 10068 } 10069 }.start(); 10070 } 10071 10072 /** 10073 * Used by {@link Log} via {@link com.android.internal.os.RuntimeInit} to report serious errors. 10074 * @param app object of the crashing app, null for the system server 10075 * @param tag reported by the caller 10076 * @param crashInfo describing the context of the error 10077 * @return true if the process should exit immediately (WTF is fatal) 10078 */ 10079 public boolean handleApplicationWtf(IBinder app, String tag, 10080 ApplicationErrorReport.CrashInfo crashInfo) { 10081 ProcessRecord r = findAppProcess(app, "WTF"); 10082 final String processName = app == null ? "system_server" 10083 : (r == null ? "unknown" : r.processName); 10084 10085 EventLog.writeEvent(EventLogTags.AM_WTF, 10086 UserHandle.getUserId(Binder.getCallingUid()), Binder.getCallingPid(), 10087 processName, 10088 r == null ? -1 : r.info.flags, 10089 tag, crashInfo.exceptionMessage); 10090 10091 addErrorToDropBox("wtf", r, processName, null, null, tag, null, null, crashInfo); 10092 10093 if (r != null && r.pid != Process.myPid() && 10094 Settings.Global.getInt(mContext.getContentResolver(), 10095 Settings.Global.WTF_IS_FATAL, 0) != 0) { 10096 crashApplication(r, crashInfo); 10097 return true; 10098 } else { 10099 return false; 10100 } 10101 } 10102 10103 /** 10104 * @param app object of some object (as stored in {@link com.android.internal.os.RuntimeInit}) 10105 * @return the corresponding {@link ProcessRecord} object, or null if none could be found 10106 */ 10107 private ProcessRecord findAppProcess(IBinder app, String reason) { 10108 if (app == null) { 10109 return null; 10110 } 10111 10112 synchronized (this) { 10113 final int NP = mProcessNames.getMap().size(); 10114 for (int ip=0; ip<NP; ip++) { 10115 SparseArray<ProcessRecord> apps = mProcessNames.getMap().valueAt(ip); 10116 final int NA = apps.size(); 10117 for (int ia=0; ia<NA; ia++) { 10118 ProcessRecord p = apps.valueAt(ia); 10119 if (p.thread != null && p.thread.asBinder() == app) { 10120 return p; 10121 } 10122 } 10123 } 10124 10125 Slog.w(TAG, "Can't find mystery application for " + reason 10126 + " from pid=" + Binder.getCallingPid() 10127 + " uid=" + Binder.getCallingUid() + ": " + app); 10128 return null; 10129 } 10130 } 10131 10132 /** 10133 * Utility function for addErrorToDropBox and handleStrictModeViolation's logging 10134 * to append various headers to the dropbox log text. 10135 */ 10136 private void appendDropBoxProcessHeaders(ProcessRecord process, String processName, 10137 StringBuilder sb) { 10138 // Watchdog thread ends up invoking this function (with 10139 // a null ProcessRecord) to add the stack file to dropbox. 10140 // Do not acquire a lock on this (am) in such cases, as it 10141 // could cause a potential deadlock, if and when watchdog 10142 // is invoked due to unavailability of lock on am and it 10143 // would prevent watchdog from killing system_server. 10144 if (process == null) { 10145 sb.append("Process: ").append(processName).append("\n"); 10146 return; 10147 } 10148 // Note: ProcessRecord 'process' is guarded by the service 10149 // instance. (notably process.pkgList, which could otherwise change 10150 // concurrently during execution of this method) 10151 synchronized (this) { 10152 sb.append("Process: ").append(processName).append("\n"); 10153 int flags = process.info.flags; 10154 IPackageManager pm = AppGlobals.getPackageManager(); 10155 sb.append("Flags: 0x").append(Integer.toString(flags, 16)).append("\n"); 10156 for (int ip=0; ip<process.pkgList.size(); ip++) { 10157 String pkg = process.pkgList.keyAt(ip); 10158 sb.append("Package: ").append(pkg); 10159 try { 10160 PackageInfo pi = pm.getPackageInfo(pkg, 0, UserHandle.getCallingUserId()); 10161 if (pi != null) { 10162 sb.append(" v").append(pi.versionCode); 10163 if (pi.versionName != null) { 10164 sb.append(" (").append(pi.versionName).append(")"); 10165 } 10166 } 10167 } catch (RemoteException e) { 10168 Slog.e(TAG, "Error getting package info: " + pkg, e); 10169 } 10170 sb.append("\n"); 10171 } 10172 } 10173 } 10174 10175 private static String processClass(ProcessRecord process) { 10176 if (process == null || process.pid == MY_PID) { 10177 return "system_server"; 10178 } else if ((process.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0) { 10179 return "system_app"; 10180 } else { 10181 return "data_app"; 10182 } 10183 } 10184 10185 /** 10186 * Write a description of an error (crash, WTF, ANR) to the drop box. 10187 * @param eventType to include in the drop box tag ("crash", "wtf", etc.) 10188 * @param process which caused the error, null means the system server 10189 * @param activity which triggered the error, null if unknown 10190 * @param parent activity related to the error, null if unknown 10191 * @param subject line related to the error, null if absent 10192 * @param report in long form describing the error, null if absent 10193 * @param logFile to include in the report, null if none 10194 * @param crashInfo giving an application stack trace, null if absent 10195 */ 10196 public void addErrorToDropBox(String eventType, 10197 ProcessRecord process, String processName, ActivityRecord activity, 10198 ActivityRecord parent, String subject, 10199 final String report, final File logFile, 10200 final ApplicationErrorReport.CrashInfo crashInfo) { 10201 // NOTE -- this must never acquire the ActivityManagerService lock, 10202 // otherwise the watchdog may be prevented from resetting the system. 10203 10204 final String dropboxTag = processClass(process) + "_" + eventType; 10205 final DropBoxManager dbox = (DropBoxManager) 10206 mContext.getSystemService(Context.DROPBOX_SERVICE); 10207 10208 // Exit early if the dropbox isn't configured to accept this report type. 10209 if (dbox == null || !dbox.isTagEnabled(dropboxTag)) return; 10210 10211 final StringBuilder sb = new StringBuilder(1024); 10212 appendDropBoxProcessHeaders(process, processName, sb); 10213 if (activity != null) { 10214 sb.append("Activity: ").append(activity.shortComponentName).append("\n"); 10215 } 10216 if (parent != null && parent.app != null && parent.app.pid != process.pid) { 10217 sb.append("Parent-Process: ").append(parent.app.processName).append("\n"); 10218 } 10219 if (parent != null && parent != activity) { 10220 sb.append("Parent-Activity: ").append(parent.shortComponentName).append("\n"); 10221 } 10222 if (subject != null) { 10223 sb.append("Subject: ").append(subject).append("\n"); 10224 } 10225 sb.append("Build: ").append(Build.FINGERPRINT).append("\n"); 10226 if (Debug.isDebuggerConnected()) { 10227 sb.append("Debugger: Connected\n"); 10228 } 10229 sb.append("\n"); 10230 10231 // Do the rest in a worker thread to avoid blocking the caller on I/O 10232 // (After this point, we shouldn't access AMS internal data structures.) 10233 Thread worker = new Thread("Error dump: " + dropboxTag) { 10234 @Override 10235 public void run() { 10236 if (report != null) { 10237 sb.append(report); 10238 } 10239 if (logFile != null) { 10240 try { 10241 sb.append(FileUtils.readTextFile(logFile, DROPBOX_MAX_SIZE, 10242 "\n\n[[TRUNCATED]]")); 10243 } catch (IOException e) { 10244 Slog.e(TAG, "Error reading " + logFile, e); 10245 } 10246 } 10247 if (crashInfo != null && crashInfo.stackTrace != null) { 10248 sb.append(crashInfo.stackTrace); 10249 } 10250 10251 String setting = Settings.Global.ERROR_LOGCAT_PREFIX + dropboxTag; 10252 int lines = Settings.Global.getInt(mContext.getContentResolver(), setting, 0); 10253 if (lines > 0) { 10254 sb.append("\n"); 10255 10256 // Merge several logcat streams, and take the last N lines 10257 InputStreamReader input = null; 10258 try { 10259 java.lang.Process logcat = new ProcessBuilder("/system/bin/logcat", 10260 "-v", "time", "-b", "events", "-b", "system", "-b", "main", 10261 "-t", String.valueOf(lines)).redirectErrorStream(true).start(); 10262 10263 try { logcat.getOutputStream().close(); } catch (IOException e) {} 10264 try { logcat.getErrorStream().close(); } catch (IOException e) {} 10265 input = new InputStreamReader(logcat.getInputStream()); 10266 10267 int num; 10268 char[] buf = new char[8192]; 10269 while ((num = input.read(buf)) > 0) sb.append(buf, 0, num); 10270 } catch (IOException e) { 10271 Slog.e(TAG, "Error running logcat", e); 10272 } finally { 10273 if (input != null) try { input.close(); } catch (IOException e) {} 10274 } 10275 } 10276 10277 dbox.addText(dropboxTag, sb.toString()); 10278 } 10279 }; 10280 10281 if (process == null) { 10282 // If process is null, we are being called from some internal code 10283 // and may be about to die -- run this synchronously. 10284 worker.run(); 10285 } else { 10286 worker.start(); 10287 } 10288 } 10289 10290 /** 10291 * Bring up the "unexpected error" dialog box for a crashing app. 10292 * Deal with edge cases (intercepts from instrumented applications, 10293 * ActivityController, error intent receivers, that sort of thing). 10294 * @param r the application crashing 10295 * @param crashInfo describing the failure 10296 */ 10297 private void crashApplication(ProcessRecord r, ApplicationErrorReport.CrashInfo crashInfo) { 10298 long timeMillis = System.currentTimeMillis(); 10299 String shortMsg = crashInfo.exceptionClassName; 10300 String longMsg = crashInfo.exceptionMessage; 10301 String stackTrace = crashInfo.stackTrace; 10302 if (shortMsg != null && longMsg != null) { 10303 longMsg = shortMsg + ": " + longMsg; 10304 } else if (shortMsg != null) { 10305 longMsg = shortMsg; 10306 } 10307 10308 AppErrorResult result = new AppErrorResult(); 10309 synchronized (this) { 10310 if (mController != null) { 10311 try { 10312 String name = r != null ? r.processName : null; 10313 int pid = r != null ? r.pid : Binder.getCallingPid(); 10314 if (!mController.appCrashed(name, pid, 10315 shortMsg, longMsg, timeMillis, crashInfo.stackTrace)) { 10316 Slog.w(TAG, "Force-killing crashed app " + name 10317 + " at watcher's request"); 10318 Process.killProcess(pid); 10319 return; 10320 } 10321 } catch (RemoteException e) { 10322 mController = null; 10323 Watchdog.getInstance().setActivityController(null); 10324 } 10325 } 10326 10327 final long origId = Binder.clearCallingIdentity(); 10328 10329 // If this process is running instrumentation, finish it. 10330 if (r != null && r.instrumentationClass != null) { 10331 Slog.w(TAG, "Error in app " + r.processName 10332 + " running instrumentation " + r.instrumentationClass + ":"); 10333 if (shortMsg != null) Slog.w(TAG, " " + shortMsg); 10334 if (longMsg != null) Slog.w(TAG, " " + longMsg); 10335 Bundle info = new Bundle(); 10336 info.putString("shortMsg", shortMsg); 10337 info.putString("longMsg", longMsg); 10338 finishInstrumentationLocked(r, Activity.RESULT_CANCELED, info); 10339 Binder.restoreCallingIdentity(origId); 10340 return; 10341 } 10342 10343 // If we can't identify the process or it's already exceeded its crash quota, 10344 // quit right away without showing a crash dialog. 10345 if (r == null || !makeAppCrashingLocked(r, shortMsg, longMsg, stackTrace)) { 10346 Binder.restoreCallingIdentity(origId); 10347 return; 10348 } 10349 10350 Message msg = Message.obtain(); 10351 msg.what = SHOW_ERROR_MSG; 10352 HashMap data = new HashMap(); 10353 data.put("result", result); 10354 data.put("app", r); 10355 msg.obj = data; 10356 mHandler.sendMessage(msg); 10357 10358 Binder.restoreCallingIdentity(origId); 10359 } 10360 10361 int res = result.get(); 10362 10363 Intent appErrorIntent = null; 10364 synchronized (this) { 10365 if (r != null && !r.isolated) { 10366 // XXX Can't keep track of crash time for isolated processes, 10367 // since they don't have a persistent identity. 10368 mProcessCrashTimes.put(r.info.processName, r.uid, 10369 SystemClock.uptimeMillis()); 10370 } 10371 if (res == AppErrorDialog.FORCE_QUIT_AND_REPORT) { 10372 appErrorIntent = createAppErrorIntentLocked(r, timeMillis, crashInfo); 10373 } 10374 } 10375 10376 if (appErrorIntent != null) { 10377 try { 10378 mContext.startActivityAsUser(appErrorIntent, new UserHandle(r.userId)); 10379 } catch (ActivityNotFoundException e) { 10380 Slog.w(TAG, "bug report receiver dissappeared", e); 10381 } 10382 } 10383 } 10384 10385 Intent createAppErrorIntentLocked(ProcessRecord r, 10386 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 10387 ApplicationErrorReport report = createAppErrorReportLocked(r, timeMillis, crashInfo); 10388 if (report == null) { 10389 return null; 10390 } 10391 Intent result = new Intent(Intent.ACTION_APP_ERROR); 10392 result.setComponent(r.errorReportReceiver); 10393 result.putExtra(Intent.EXTRA_BUG_REPORT, report); 10394 result.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 10395 return result; 10396 } 10397 10398 private ApplicationErrorReport createAppErrorReportLocked(ProcessRecord r, 10399 long timeMillis, ApplicationErrorReport.CrashInfo crashInfo) { 10400 if (r.errorReportReceiver == null) { 10401 return null; 10402 } 10403 10404 if (!r.crashing && !r.notResponding && !r.forceCrashReport) { 10405 return null; 10406 } 10407 10408 ApplicationErrorReport report = new ApplicationErrorReport(); 10409 report.packageName = r.info.packageName; 10410 report.installerPackageName = r.errorReportReceiver.getPackageName(); 10411 report.processName = r.processName; 10412 report.time = timeMillis; 10413 report.systemApp = (r.info.flags & ApplicationInfo.FLAG_SYSTEM) != 0; 10414 10415 if (r.crashing || r.forceCrashReport) { 10416 report.type = ApplicationErrorReport.TYPE_CRASH; 10417 report.crashInfo = crashInfo; 10418 } else if (r.notResponding) { 10419 report.type = ApplicationErrorReport.TYPE_ANR; 10420 report.anrInfo = new ApplicationErrorReport.AnrInfo(); 10421 10422 report.anrInfo.activity = r.notRespondingReport.tag; 10423 report.anrInfo.cause = r.notRespondingReport.shortMsg; 10424 report.anrInfo.info = r.notRespondingReport.longMsg; 10425 } 10426 10427 return report; 10428 } 10429 10430 public List<ActivityManager.ProcessErrorStateInfo> getProcessesInErrorState() { 10431 enforceNotIsolatedCaller("getProcessesInErrorState"); 10432 // assume our apps are happy - lazy create the list 10433 List<ActivityManager.ProcessErrorStateInfo> errList = null; 10434 10435 final boolean allUsers = ActivityManager.checkUidPermission( 10436 android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, 10437 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 10438 int userId = UserHandle.getUserId(Binder.getCallingUid()); 10439 10440 synchronized (this) { 10441 10442 // iterate across all processes 10443 for (int i=mLruProcesses.size()-1; i>=0; i--) { 10444 ProcessRecord app = mLruProcesses.get(i); 10445 if (!allUsers && app.userId != userId) { 10446 continue; 10447 } 10448 if ((app.thread != null) && (app.crashing || app.notResponding)) { 10449 // This one's in trouble, so we'll generate a report for it 10450 // crashes are higher priority (in case there's a crash *and* an anr) 10451 ActivityManager.ProcessErrorStateInfo report = null; 10452 if (app.crashing) { 10453 report = app.crashingReport; 10454 } else if (app.notResponding) { 10455 report = app.notRespondingReport; 10456 } 10457 10458 if (report != null) { 10459 if (errList == null) { 10460 errList = new ArrayList<ActivityManager.ProcessErrorStateInfo>(1); 10461 } 10462 errList.add(report); 10463 } else { 10464 Slog.w(TAG, "Missing app error report, app = " + app.processName + 10465 " crashing = " + app.crashing + 10466 " notResponding = " + app.notResponding); 10467 } 10468 } 10469 } 10470 } 10471 10472 return errList; 10473 } 10474 10475 static int oomAdjToImportance(int adj, ActivityManager.RunningAppProcessInfo currApp) { 10476 if (adj >= ProcessList.CACHED_APP_MIN_ADJ) { 10477 if (currApp != null) { 10478 currApp.lru = adj - ProcessList.CACHED_APP_MIN_ADJ + 1; 10479 } 10480 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND; 10481 } else if (adj >= ProcessList.SERVICE_B_ADJ) { 10482 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_SERVICE; 10483 } else if (adj >= ProcessList.HOME_APP_ADJ) { 10484 if (currApp != null) { 10485 currApp.lru = 0; 10486 } 10487 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_BACKGROUND; 10488 } else if (adj >= ProcessList.SERVICE_ADJ) { 10489 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_SERVICE; 10490 } else if (adj >= ProcessList.HEAVY_WEIGHT_APP_ADJ) { 10491 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_CANT_SAVE_STATE; 10492 } else if (adj >= ProcessList.PERCEPTIBLE_APP_ADJ) { 10493 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_PERCEPTIBLE; 10494 } else if (adj >= ProcessList.VISIBLE_APP_ADJ) { 10495 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_VISIBLE; 10496 } else { 10497 return ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND; 10498 } 10499 } 10500 10501 private void fillInProcMemInfo(ProcessRecord app, 10502 ActivityManager.RunningAppProcessInfo outInfo) { 10503 outInfo.pid = app.pid; 10504 outInfo.uid = app.info.uid; 10505 if (mHeavyWeightProcess == app) { 10506 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_CANT_SAVE_STATE; 10507 } 10508 if (app.persistent) { 10509 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_PERSISTENT; 10510 } 10511 if (app.activities.size() > 0) { 10512 outInfo.flags |= ActivityManager.RunningAppProcessInfo.FLAG_HAS_ACTIVITIES; 10513 } 10514 outInfo.lastTrimLevel = app.trimMemoryLevel; 10515 int adj = app.curAdj; 10516 outInfo.importance = oomAdjToImportance(adj, outInfo); 10517 outInfo.importanceReasonCode = app.adjTypeCode; 10518 outInfo.processState = app.curProcState; 10519 } 10520 10521 public List<ActivityManager.RunningAppProcessInfo> getRunningAppProcesses() { 10522 enforceNotIsolatedCaller("getRunningAppProcesses"); 10523 // Lazy instantiation of list 10524 List<ActivityManager.RunningAppProcessInfo> runList = null; 10525 final boolean allUsers = ActivityManager.checkUidPermission( 10526 android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, 10527 Binder.getCallingUid()) == PackageManager.PERMISSION_GRANTED; 10528 int userId = UserHandle.getUserId(Binder.getCallingUid()); 10529 synchronized (this) { 10530 // Iterate across all processes 10531 for (int i=mLruProcesses.size()-1; i>=0; i--) { 10532 ProcessRecord app = mLruProcesses.get(i); 10533 if (!allUsers && app.userId != userId) { 10534 continue; 10535 } 10536 if ((app.thread != null) && (!app.crashing && !app.notResponding)) { 10537 // Generate process state info for running application 10538 ActivityManager.RunningAppProcessInfo currApp = 10539 new ActivityManager.RunningAppProcessInfo(app.processName, 10540 app.pid, app.getPackageList()); 10541 fillInProcMemInfo(app, currApp); 10542 if (app.adjSource instanceof ProcessRecord) { 10543 currApp.importanceReasonPid = ((ProcessRecord)app.adjSource).pid; 10544 currApp.importanceReasonImportance = oomAdjToImportance( 10545 app.adjSourceOom, null); 10546 } else if (app.adjSource instanceof ActivityRecord) { 10547 ActivityRecord r = (ActivityRecord)app.adjSource; 10548 if (r.app != null) currApp.importanceReasonPid = r.app.pid; 10549 } 10550 if (app.adjTarget instanceof ComponentName) { 10551 currApp.importanceReasonComponent = (ComponentName)app.adjTarget; 10552 } 10553 //Slog.v(TAG, "Proc " + app.processName + ": imp=" + currApp.importance 10554 // + " lru=" + currApp.lru); 10555 if (runList == null) { 10556 runList = new ArrayList<ActivityManager.RunningAppProcessInfo>(); 10557 } 10558 runList.add(currApp); 10559 } 10560 } 10561 } 10562 return runList; 10563 } 10564 10565 public List<ApplicationInfo> getRunningExternalApplications() { 10566 enforceNotIsolatedCaller("getRunningExternalApplications"); 10567 List<ActivityManager.RunningAppProcessInfo> runningApps = getRunningAppProcesses(); 10568 List<ApplicationInfo> retList = new ArrayList<ApplicationInfo>(); 10569 if (runningApps != null && runningApps.size() > 0) { 10570 Set<String> extList = new HashSet<String>(); 10571 for (ActivityManager.RunningAppProcessInfo app : runningApps) { 10572 if (app.pkgList != null) { 10573 for (String pkg : app.pkgList) { 10574 extList.add(pkg); 10575 } 10576 } 10577 } 10578 IPackageManager pm = AppGlobals.getPackageManager(); 10579 for (String pkg : extList) { 10580 try { 10581 ApplicationInfo info = pm.getApplicationInfo(pkg, 0, UserHandle.getCallingUserId()); 10582 if ((info.flags & ApplicationInfo.FLAG_EXTERNAL_STORAGE) != 0) { 10583 retList.add(info); 10584 } 10585 } catch (RemoteException e) { 10586 } 10587 } 10588 } 10589 return retList; 10590 } 10591 10592 @Override 10593 public void getMyMemoryState(ActivityManager.RunningAppProcessInfo outInfo) { 10594 enforceNotIsolatedCaller("getMyMemoryState"); 10595 synchronized (this) { 10596 ProcessRecord proc; 10597 synchronized (mPidsSelfLocked) { 10598 proc = mPidsSelfLocked.get(Binder.getCallingPid()); 10599 } 10600 fillInProcMemInfo(proc, outInfo); 10601 } 10602 } 10603 10604 @Override 10605 protected void dump(FileDescriptor fd, PrintWriter pw, String[] args) { 10606 if (checkCallingPermission(android.Manifest.permission.DUMP) 10607 != PackageManager.PERMISSION_GRANTED) { 10608 pw.println("Permission Denial: can't dump ActivityManager from from pid=" 10609 + Binder.getCallingPid() 10610 + ", uid=" + Binder.getCallingUid() 10611 + " without permission " 10612 + android.Manifest.permission.DUMP); 10613 return; 10614 } 10615 10616 boolean dumpAll = false; 10617 boolean dumpClient = false; 10618 String dumpPackage = null; 10619 10620 int opti = 0; 10621 while (opti < args.length) { 10622 String opt = args[opti]; 10623 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 10624 break; 10625 } 10626 opti++; 10627 if ("-a".equals(opt)) { 10628 dumpAll = true; 10629 } else if ("-c".equals(opt)) { 10630 dumpClient = true; 10631 } else if ("-h".equals(opt)) { 10632 pw.println("Activity manager dump options:"); 10633 pw.println(" [-a] [-c] [-h] [cmd] ..."); 10634 pw.println(" cmd may be one of:"); 10635 pw.println(" a[ctivities]: activity stack state"); 10636 pw.println(" b[roadcasts] [PACKAGE_NAME] [history [-s]]: broadcast state"); 10637 pw.println(" i[ntents] [PACKAGE_NAME]: pending intent state"); 10638 pw.println(" p[rocesses] [PACKAGE_NAME]: process state"); 10639 pw.println(" o[om]: out of memory management"); 10640 pw.println(" prov[iders] [COMP_SPEC ...]: content provider state"); 10641 pw.println(" provider [COMP_SPEC]: provider client-side state"); 10642 pw.println(" s[ervices] [COMP_SPEC ...]: service state"); 10643 pw.println(" service [COMP_SPEC]: service client-side state"); 10644 pw.println(" package [PACKAGE_NAME]: all state related to given package"); 10645 pw.println(" all: dump all activities"); 10646 pw.println(" top: dump the top activity"); 10647 pw.println(" cmd may also be a COMP_SPEC to dump activities."); 10648 pw.println(" COMP_SPEC may be a component name (com.foo/.myApp),"); 10649 pw.println(" a partial substring in a component name, a"); 10650 pw.println(" hex object identifier."); 10651 pw.println(" -a: include all available server state."); 10652 pw.println(" -c: include client state."); 10653 return; 10654 } else { 10655 pw.println("Unknown argument: " + opt + "; use -h for help"); 10656 } 10657 } 10658 10659 long origId = Binder.clearCallingIdentity(); 10660 boolean more = false; 10661 // Is the caller requesting to dump a particular piece of data? 10662 if (opti < args.length) { 10663 String cmd = args[opti]; 10664 opti++; 10665 if ("activities".equals(cmd) || "a".equals(cmd)) { 10666 synchronized (this) { 10667 dumpActivitiesLocked(fd, pw, args, opti, true, dumpClient, null); 10668 } 10669 } else if ("broadcasts".equals(cmd) || "b".equals(cmd)) { 10670 String[] newArgs; 10671 String name; 10672 if (opti >= args.length) { 10673 name = null; 10674 newArgs = EMPTY_STRING_ARRAY; 10675 } else { 10676 name = args[opti]; 10677 opti++; 10678 newArgs = new String[args.length - opti]; 10679 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 10680 args.length - opti); 10681 } 10682 synchronized (this) { 10683 dumpBroadcastsLocked(fd, pw, args, opti, true, name); 10684 } 10685 } else if ("intents".equals(cmd) || "i".equals(cmd)) { 10686 String[] newArgs; 10687 String name; 10688 if (opti >= args.length) { 10689 name = null; 10690 newArgs = EMPTY_STRING_ARRAY; 10691 } else { 10692 name = args[opti]; 10693 opti++; 10694 newArgs = new String[args.length - opti]; 10695 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 10696 args.length - opti); 10697 } 10698 synchronized (this) { 10699 dumpPendingIntentsLocked(fd, pw, args, opti, true, name); 10700 } 10701 } else if ("processes".equals(cmd) || "p".equals(cmd)) { 10702 String[] newArgs; 10703 String name; 10704 if (opti >= args.length) { 10705 name = null; 10706 newArgs = EMPTY_STRING_ARRAY; 10707 } else { 10708 name = args[opti]; 10709 opti++; 10710 newArgs = new String[args.length - opti]; 10711 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 10712 args.length - opti); 10713 } 10714 synchronized (this) { 10715 dumpProcessesLocked(fd, pw, args, opti, true, name); 10716 } 10717 } else if ("oom".equals(cmd) || "o".equals(cmd)) { 10718 synchronized (this) { 10719 dumpOomLocked(fd, pw, args, opti, true); 10720 } 10721 } else if ("provider".equals(cmd)) { 10722 String[] newArgs; 10723 String name; 10724 if (opti >= args.length) { 10725 name = null; 10726 newArgs = EMPTY_STRING_ARRAY; 10727 } else { 10728 name = args[opti]; 10729 opti++; 10730 newArgs = new String[args.length - opti]; 10731 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, args.length - opti); 10732 } 10733 if (!dumpProvider(fd, pw, name, newArgs, 0, dumpAll)) { 10734 pw.println("No providers match: " + name); 10735 pw.println("Use -h for help."); 10736 } 10737 } else if ("providers".equals(cmd) || "prov".equals(cmd)) { 10738 synchronized (this) { 10739 dumpProvidersLocked(fd, pw, args, opti, true, null); 10740 } 10741 } else if ("service".equals(cmd)) { 10742 String[] newArgs; 10743 String name; 10744 if (opti >= args.length) { 10745 name = null; 10746 newArgs = EMPTY_STRING_ARRAY; 10747 } else { 10748 name = args[opti]; 10749 opti++; 10750 newArgs = new String[args.length - opti]; 10751 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 10752 args.length - opti); 10753 } 10754 if (!mServices.dumpService(fd, pw, name, newArgs, 0, dumpAll)) { 10755 pw.println("No services match: " + name); 10756 pw.println("Use -h for help."); 10757 } 10758 } else if ("package".equals(cmd)) { 10759 String[] newArgs; 10760 if (opti >= args.length) { 10761 pw.println("package: no package name specified"); 10762 pw.println("Use -h for help."); 10763 } else { 10764 dumpPackage = args[opti]; 10765 opti++; 10766 newArgs = new String[args.length - opti]; 10767 if (args.length > 2) System.arraycopy(args, opti, newArgs, 0, 10768 args.length - opti); 10769 args = newArgs; 10770 opti = 0; 10771 more = true; 10772 } 10773 } else if ("services".equals(cmd) || "s".equals(cmd)) { 10774 synchronized (this) { 10775 mServices.dumpServicesLocked(fd, pw, args, opti, true, dumpClient, null); 10776 } 10777 } else { 10778 // Dumping a single activity? 10779 if (!dumpActivity(fd, pw, cmd, args, opti, dumpAll)) { 10780 pw.println("Bad activity command, or no activities match: " + cmd); 10781 pw.println("Use -h for help."); 10782 } 10783 } 10784 if (!more) { 10785 Binder.restoreCallingIdentity(origId); 10786 return; 10787 } 10788 } 10789 10790 // No piece of data specified, dump everything. 10791 synchronized (this) { 10792 dumpPendingIntentsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 10793 pw.println(); 10794 if (dumpAll) { 10795 pw.println("-------------------------------------------------------------------------------"); 10796 } 10797 dumpBroadcastsLocked(fd, pw, args, opti, dumpAll, dumpPackage); 10798 pw.println(); 10799 if (dumpAll) { 10800 pw.println("-------------------------------------------------------------------------------"); 10801 } 10802 dumpProvidersLocked(fd, pw, args, opti, dumpAll, dumpPackage); 10803 pw.println(); 10804 if (dumpAll) { 10805 pw.println("-------------------------------------------------------------------------------"); 10806 } 10807 mServices.dumpServicesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 10808 pw.println(); 10809 if (dumpAll) { 10810 pw.println("-------------------------------------------------------------------------------"); 10811 } 10812 dumpActivitiesLocked(fd, pw, args, opti, dumpAll, dumpClient, dumpPackage); 10813 pw.println(); 10814 if (dumpAll) { 10815 pw.println("-------------------------------------------------------------------------------"); 10816 } 10817 dumpProcessesLocked(fd, pw, args, opti, dumpAll, dumpPackage); 10818 } 10819 Binder.restoreCallingIdentity(origId); 10820 } 10821 10822 void dumpActivitiesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 10823 int opti, boolean dumpAll, boolean dumpClient, String dumpPackage) { 10824 pw.println("ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)"); 10825 10826 boolean printedAnything = mStackSupervisor.dumpActivitiesLocked(fd, pw, dumpAll, dumpClient, 10827 dumpPackage); 10828 boolean needSep = printedAnything; 10829 10830 boolean printed = ActivityStackSupervisor.printThisActivity(pw, mFocusedActivity, 10831 dumpPackage, needSep, " mFocusedActivity: "); 10832 if (printed) { 10833 printedAnything = true; 10834 needSep = false; 10835 } 10836 10837 if (dumpPackage == null) { 10838 if (needSep) { 10839 pw.println(); 10840 } 10841 needSep = true; 10842 printedAnything = true; 10843 mStackSupervisor.dump(pw, " "); 10844 } 10845 10846 if (mRecentTasks.size() > 0) { 10847 boolean printedHeader = false; 10848 10849 final int N = mRecentTasks.size(); 10850 for (int i=0; i<N; i++) { 10851 TaskRecord tr = mRecentTasks.get(i); 10852 if (dumpPackage != null) { 10853 if (tr.realActivity == null || 10854 !dumpPackage.equals(tr.realActivity)) { 10855 continue; 10856 } 10857 } 10858 if (!printedHeader) { 10859 if (needSep) { 10860 pw.println(); 10861 } 10862 pw.println(" Recent tasks:"); 10863 printedHeader = true; 10864 printedAnything = true; 10865 } 10866 pw.print(" * Recent #"); pw.print(i); pw.print(": "); 10867 pw.println(tr); 10868 if (dumpAll) { 10869 mRecentTasks.get(i).dump(pw, " "); 10870 } 10871 } 10872 } 10873 10874 if (!printedAnything) { 10875 pw.println(" (nothing)"); 10876 } 10877 } 10878 10879 void dumpProcessesLocked(FileDescriptor fd, PrintWriter pw, String[] args, 10880 int opti, boolean dumpAll, String dumpPackage) { 10881 boolean needSep = false; 10882 boolean printedAnything = false; 10883 int numPers = 0; 10884 10885 pw.println("ACTIVITY MANAGER RUNNING PROCESSES (dumpsys activity processes)"); 10886 10887 if (dumpAll) { 10888 final int NP = mProcessNames.getMap().size(); 10889 for (int ip=0; ip<NP; ip++) { 10890 SparseArray<ProcessRecord> procs = mProcessNames.getMap().valueAt(ip); 10891 final int NA = procs.size(); 10892 for (int ia=0; ia<NA; ia++) { 10893 ProcessRecord r = procs.valueAt(ia); 10894 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 10895 continue; 10896 } 10897 if (!needSep) { 10898 pw.println(" All known processes:"); 10899 needSep = true; 10900 printedAnything = true; 10901 } 10902 pw.print(r.persistent ? " *PERS*" : " *APP*"); 10903 pw.print(" UID "); pw.print(procs.keyAt(ia)); 10904 pw.print(" "); pw.println(r); 10905 r.dump(pw, " "); 10906 if (r.persistent) { 10907 numPers++; 10908 } 10909 } 10910 } 10911 } 10912 10913 if (mIsolatedProcesses.size() > 0) { 10914 boolean printed = false; 10915 for (int i=0; i<mIsolatedProcesses.size(); i++) { 10916 ProcessRecord r = mIsolatedProcesses.valueAt(i); 10917 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 10918 continue; 10919 } 10920 if (!printed) { 10921 if (needSep) { 10922 pw.println(); 10923 } 10924 pw.println(" Isolated process list (sorted by uid):"); 10925 printedAnything = true; 10926 printed = true; 10927 needSep = true; 10928 } 10929 pw.println(String.format("%sIsolated #%2d: %s", 10930 " ", i, r.toString())); 10931 } 10932 } 10933 10934 if (mLruProcesses.size() > 0) { 10935 if (needSep) { 10936 pw.println(); 10937 } 10938 pw.print(" Process LRU list (sorted by oom_adj, "); pw.print(mLruProcesses.size()); 10939 pw.print(" total, non-act at "); 10940 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 10941 pw.print(", non-svc at "); 10942 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 10943 pw.println("):"); 10944 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", false, dumpPackage); 10945 needSep = true; 10946 printedAnything = true; 10947 } 10948 10949 if (dumpAll || dumpPackage != null) { 10950 synchronized (mPidsSelfLocked) { 10951 boolean printed = false; 10952 for (int i=0; i<mPidsSelfLocked.size(); i++) { 10953 ProcessRecord r = mPidsSelfLocked.valueAt(i); 10954 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 10955 continue; 10956 } 10957 if (!printed) { 10958 if (needSep) pw.println(); 10959 needSep = true; 10960 pw.println(" PID mappings:"); 10961 printed = true; 10962 printedAnything = true; 10963 } 10964 pw.print(" PID #"); pw.print(mPidsSelfLocked.keyAt(i)); 10965 pw.print(": "); pw.println(mPidsSelfLocked.valueAt(i)); 10966 } 10967 } 10968 } 10969 10970 if (mForegroundProcesses.size() > 0) { 10971 synchronized (mPidsSelfLocked) { 10972 boolean printed = false; 10973 for (int i=0; i<mForegroundProcesses.size(); i++) { 10974 ProcessRecord r = mPidsSelfLocked.get( 10975 mForegroundProcesses.valueAt(i).pid); 10976 if (dumpPackage != null && (r == null 10977 || !r.pkgList.containsKey(dumpPackage))) { 10978 continue; 10979 } 10980 if (!printed) { 10981 if (needSep) pw.println(); 10982 needSep = true; 10983 pw.println(" Foreground Processes:"); 10984 printed = true; 10985 printedAnything = true; 10986 } 10987 pw.print(" PID #"); pw.print(mForegroundProcesses.keyAt(i)); 10988 pw.print(": "); pw.println(mForegroundProcesses.valueAt(i)); 10989 } 10990 } 10991 } 10992 10993 if (mPersistentStartingProcesses.size() > 0) { 10994 if (needSep) pw.println(); 10995 needSep = true; 10996 printedAnything = true; 10997 pw.println(" Persisent processes that are starting:"); 10998 dumpProcessList(pw, this, mPersistentStartingProcesses, " ", 10999 "Starting Norm", "Restarting PERS", dumpPackage); 11000 } 11001 11002 if (mRemovedProcesses.size() > 0) { 11003 if (needSep) pw.println(); 11004 needSep = true; 11005 printedAnything = true; 11006 pw.println(" Processes that are being removed:"); 11007 dumpProcessList(pw, this, mRemovedProcesses, " ", 11008 "Removed Norm", "Removed PERS", dumpPackage); 11009 } 11010 11011 if (mProcessesOnHold.size() > 0) { 11012 if (needSep) pw.println(); 11013 needSep = true; 11014 printedAnything = true; 11015 pw.println(" Processes that are on old until the system is ready:"); 11016 dumpProcessList(pw, this, mProcessesOnHold, " ", 11017 "OnHold Norm", "OnHold PERS", dumpPackage); 11018 } 11019 11020 needSep = dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, dumpPackage); 11021 11022 if (mProcessCrashTimes.getMap().size() > 0) { 11023 boolean printed = false; 11024 long now = SystemClock.uptimeMillis(); 11025 final ArrayMap<String, SparseArray<Long>> pmap = mProcessCrashTimes.getMap(); 11026 final int NP = pmap.size(); 11027 for (int ip=0; ip<NP; ip++) { 11028 String pname = pmap.keyAt(ip); 11029 SparseArray<Long> uids = pmap.valueAt(ip); 11030 final int N = uids.size(); 11031 for (int i=0; i<N; i++) { 11032 int puid = uids.keyAt(i); 11033 ProcessRecord r = mProcessNames.get(pname, puid); 11034 if (dumpPackage != null && (r == null 11035 || !r.pkgList.containsKey(dumpPackage))) { 11036 continue; 11037 } 11038 if (!printed) { 11039 if (needSep) pw.println(); 11040 needSep = true; 11041 pw.println(" Time since processes crashed:"); 11042 printed = true; 11043 printedAnything = true; 11044 } 11045 pw.print(" Process "); pw.print(pname); 11046 pw.print(" uid "); pw.print(puid); 11047 pw.print(": last crashed "); 11048 TimeUtils.formatDuration(now-uids.valueAt(i), pw); 11049 pw.println(" ago"); 11050 } 11051 } 11052 } 11053 11054 if (mBadProcesses.getMap().size() > 0) { 11055 boolean printed = false; 11056 final ArrayMap<String, SparseArray<BadProcessInfo>> pmap = mBadProcesses.getMap(); 11057 final int NP = pmap.size(); 11058 for (int ip=0; ip<NP; ip++) { 11059 String pname = pmap.keyAt(ip); 11060 SparseArray<BadProcessInfo> uids = pmap.valueAt(ip); 11061 final int N = uids.size(); 11062 for (int i=0; i<N; i++) { 11063 int puid = uids.keyAt(i); 11064 ProcessRecord r = mProcessNames.get(pname, puid); 11065 if (dumpPackage != null && (r == null 11066 || !r.pkgList.containsKey(dumpPackage))) { 11067 continue; 11068 } 11069 if (!printed) { 11070 if (needSep) pw.println(); 11071 needSep = true; 11072 pw.println(" Bad processes:"); 11073 printedAnything = true; 11074 } 11075 BadProcessInfo info = uids.valueAt(i); 11076 pw.print(" Bad process "); pw.print(pname); 11077 pw.print(" uid "); pw.print(puid); 11078 pw.print(": crashed at time "); pw.println(info.time); 11079 if (info.shortMsg != null) { 11080 pw.print(" Short msg: "); pw.println(info.shortMsg); 11081 } 11082 if (info.longMsg != null) { 11083 pw.print(" Long msg: "); pw.println(info.longMsg); 11084 } 11085 if (info.stack != null) { 11086 pw.println(" Stack:"); 11087 int lastPos = 0; 11088 for (int pos=0; pos<info.stack.length(); pos++) { 11089 if (info.stack.charAt(pos) == '\n') { 11090 pw.print(" "); 11091 pw.write(info.stack, lastPos, pos-lastPos); 11092 pw.println(); 11093 lastPos = pos+1; 11094 } 11095 } 11096 if (lastPos < info.stack.length()) { 11097 pw.print(" "); 11098 pw.write(info.stack, lastPos, info.stack.length()-lastPos); 11099 pw.println(); 11100 } 11101 } 11102 } 11103 } 11104 } 11105 11106 if (dumpPackage == null) { 11107 pw.println(); 11108 needSep = false; 11109 pw.println(" mStartedUsers:"); 11110 for (int i=0; i<mStartedUsers.size(); i++) { 11111 UserStartedState uss = mStartedUsers.valueAt(i); 11112 pw.print(" User #"); pw.print(uss.mHandle.getIdentifier()); 11113 pw.print(": "); uss.dump("", pw); 11114 } 11115 pw.print(" mStartedUserArray: ["); 11116 for (int i=0; i<mStartedUserArray.length; i++) { 11117 if (i > 0) pw.print(", "); 11118 pw.print(mStartedUserArray[i]); 11119 } 11120 pw.println("]"); 11121 pw.print(" mUserLru: ["); 11122 for (int i=0; i<mUserLru.size(); i++) { 11123 if (i > 0) pw.print(", "); 11124 pw.print(mUserLru.get(i)); 11125 } 11126 pw.println("]"); 11127 if (dumpAll) { 11128 pw.print(" mStartedUserArray: "); pw.println(Arrays.toString(mStartedUserArray)); 11129 } 11130 } 11131 if (mHomeProcess != null && (dumpPackage == null 11132 || mHomeProcess.pkgList.containsKey(dumpPackage))) { 11133 if (needSep) { 11134 pw.println(); 11135 needSep = false; 11136 } 11137 pw.println(" mHomeProcess: " + mHomeProcess); 11138 } 11139 if (mPreviousProcess != null && (dumpPackage == null 11140 || mPreviousProcess.pkgList.containsKey(dumpPackage))) { 11141 if (needSep) { 11142 pw.println(); 11143 needSep = false; 11144 } 11145 pw.println(" mPreviousProcess: " + mPreviousProcess); 11146 } 11147 if (dumpAll) { 11148 StringBuilder sb = new StringBuilder(128); 11149 sb.append(" mPreviousProcessVisibleTime: "); 11150 TimeUtils.formatDuration(mPreviousProcessVisibleTime, sb); 11151 pw.println(sb); 11152 } 11153 if (mHeavyWeightProcess != null && (dumpPackage == null 11154 || mHeavyWeightProcess.pkgList.containsKey(dumpPackage))) { 11155 if (needSep) { 11156 pw.println(); 11157 needSep = false; 11158 } 11159 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 11160 } 11161 if (dumpPackage == null) { 11162 pw.println(" mConfiguration: " + mConfiguration); 11163 } 11164 if (dumpAll) { 11165 pw.println(" mConfigWillChange: " + getFocusedStack().mConfigWillChange); 11166 if (mCompatModePackages.getPackages().size() > 0) { 11167 boolean printed = false; 11168 for (Map.Entry<String, Integer> entry 11169 : mCompatModePackages.getPackages().entrySet()) { 11170 String pkg = entry.getKey(); 11171 int mode = entry.getValue(); 11172 if (dumpPackage != null && !dumpPackage.equals(pkg)) { 11173 continue; 11174 } 11175 if (!printed) { 11176 pw.println(" mScreenCompatPackages:"); 11177 printed = true; 11178 } 11179 pw.print(" "); pw.print(pkg); pw.print(": "); 11180 pw.print(mode); pw.println(); 11181 } 11182 } 11183 } 11184 if (dumpPackage == null) { 11185 if (mSleeping || mWentToSleep || mLockScreenShown) { 11186 pw.println(" mSleeping=" + mSleeping + " mWentToSleep=" + mWentToSleep 11187 + " mLockScreenShown " + mLockScreenShown); 11188 } 11189 if (mShuttingDown || mRunningVoice) { 11190 pw.print(" mShuttingDown=" + mShuttingDown + " mRunningVoice=" + mRunningVoice); 11191 } 11192 } 11193 if (mDebugApp != null || mOrigDebugApp != null || mDebugTransient 11194 || mOrigWaitForDebugger) { 11195 if (dumpPackage == null || dumpPackage.equals(mDebugApp) 11196 || dumpPackage.equals(mOrigDebugApp)) { 11197 if (needSep) { 11198 pw.println(); 11199 needSep = false; 11200 } 11201 pw.println(" mDebugApp=" + mDebugApp + "/orig=" + mOrigDebugApp 11202 + " mDebugTransient=" + mDebugTransient 11203 + " mOrigWaitForDebugger=" + mOrigWaitForDebugger); 11204 } 11205 } 11206 if (mOpenGlTraceApp != null) { 11207 if (dumpPackage == null || dumpPackage.equals(mOpenGlTraceApp)) { 11208 if (needSep) { 11209 pw.println(); 11210 needSep = false; 11211 } 11212 pw.println(" mOpenGlTraceApp=" + mOpenGlTraceApp); 11213 } 11214 } 11215 if (mProfileApp != null || mProfileProc != null || mProfileFile != null 11216 || mProfileFd != null) { 11217 if (dumpPackage == null || dumpPackage.equals(mProfileApp)) { 11218 if (needSep) { 11219 pw.println(); 11220 needSep = false; 11221 } 11222 pw.println(" mProfileApp=" + mProfileApp + " mProfileProc=" + mProfileProc); 11223 pw.println(" mProfileFile=" + mProfileFile + " mProfileFd=" + mProfileFd); 11224 pw.println(" mProfileType=" + mProfileType + " mAutoStopProfiler=" 11225 + mAutoStopProfiler); 11226 } 11227 } 11228 if (dumpPackage == null) { 11229 if (mAlwaysFinishActivities || mController != null) { 11230 pw.println(" mAlwaysFinishActivities=" + mAlwaysFinishActivities 11231 + " mController=" + mController); 11232 } 11233 if (dumpAll) { 11234 pw.println(" Total persistent processes: " + numPers); 11235 pw.println(" mProcessesReady=" + mProcessesReady 11236 + " mSystemReady=" + mSystemReady); 11237 pw.println(" mBooting=" + mBooting 11238 + " mBooted=" + mBooted 11239 + " mFactoryTest=" + mFactoryTest); 11240 pw.print(" mLastPowerCheckRealtime="); 11241 TimeUtils.formatDuration(mLastPowerCheckRealtime, pw); 11242 pw.println(""); 11243 pw.print(" mLastPowerCheckUptime="); 11244 TimeUtils.formatDuration(mLastPowerCheckUptime, pw); 11245 pw.println(""); 11246 pw.println(" mGoingToSleep=" + mStackSupervisor.mGoingToSleep); 11247 pw.println(" mLaunchingActivity=" + mStackSupervisor.mLaunchingActivity); 11248 pw.println(" mAdjSeq=" + mAdjSeq + " mLruSeq=" + mLruSeq); 11249 pw.println(" mNumNonCachedProcs=" + mNumNonCachedProcs 11250 + " (" + mLruProcesses.size() + " total)" 11251 + " mNumCachedHiddenProcs=" + mNumCachedHiddenProcs 11252 + " mNumServiceProcs=" + mNumServiceProcs 11253 + " mNewNumServiceProcs=" + mNewNumServiceProcs); 11254 pw.println(" mAllowLowerMemLevel=" + mAllowLowerMemLevel 11255 + " mLastMemoryLevel" + mLastMemoryLevel 11256 + " mLastNumProcesses" + mLastNumProcesses); 11257 long now = SystemClock.uptimeMillis(); 11258 pw.print(" mLastIdleTime="); 11259 TimeUtils.formatDuration(now, mLastIdleTime, pw); 11260 pw.print(" mLowRamSinceLastIdle="); 11261 TimeUtils.formatDuration(getLowRamTimeSinceIdle(now), pw); 11262 pw.println(); 11263 } 11264 } 11265 11266 if (!printedAnything) { 11267 pw.println(" (nothing)"); 11268 } 11269 } 11270 11271 boolean dumpProcessesToGc(FileDescriptor fd, PrintWriter pw, String[] args, 11272 int opti, boolean needSep, boolean dumpAll, String dumpPackage) { 11273 if (mProcessesToGc.size() > 0) { 11274 boolean printed = false; 11275 long now = SystemClock.uptimeMillis(); 11276 for (int i=0; i<mProcessesToGc.size(); i++) { 11277 ProcessRecord proc = mProcessesToGc.get(i); 11278 if (dumpPackage != null && !dumpPackage.equals(proc.info.packageName)) { 11279 continue; 11280 } 11281 if (!printed) { 11282 if (needSep) pw.println(); 11283 needSep = true; 11284 pw.println(" Processes that are waiting to GC:"); 11285 printed = true; 11286 } 11287 pw.print(" Process "); pw.println(proc); 11288 pw.print(" lowMem="); pw.print(proc.reportLowMemory); 11289 pw.print(", last gced="); 11290 pw.print(now-proc.lastRequestedGc); 11291 pw.print(" ms ago, last lowMem="); 11292 pw.print(now-proc.lastLowMemory); 11293 pw.println(" ms ago"); 11294 11295 } 11296 } 11297 return needSep; 11298 } 11299 11300 void printOomLevel(PrintWriter pw, String name, int adj) { 11301 pw.print(" "); 11302 if (adj >= 0) { 11303 pw.print(' '); 11304 if (adj < 10) pw.print(' '); 11305 } else { 11306 if (adj > -10) pw.print(' '); 11307 } 11308 pw.print(adj); 11309 pw.print(": "); 11310 pw.print(name); 11311 pw.print(" ("); 11312 pw.print(mProcessList.getMemLevel(adj)/1024); 11313 pw.println(" kB)"); 11314 } 11315 11316 boolean dumpOomLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11317 int opti, boolean dumpAll) { 11318 boolean needSep = false; 11319 11320 if (mLruProcesses.size() > 0) { 11321 if (needSep) pw.println(); 11322 needSep = true; 11323 pw.println(" OOM levels:"); 11324 printOomLevel(pw, "SYSTEM_ADJ", ProcessList.SYSTEM_ADJ); 11325 printOomLevel(pw, "PERSISTENT_PROC_ADJ", ProcessList.PERSISTENT_PROC_ADJ); 11326 printOomLevel(pw, "FOREGROUND_APP_ADJ", ProcessList.FOREGROUND_APP_ADJ); 11327 printOomLevel(pw, "VISIBLE_APP_ADJ", ProcessList.VISIBLE_APP_ADJ); 11328 printOomLevel(pw, "PERCEPTIBLE_APP_ADJ", ProcessList.PERCEPTIBLE_APP_ADJ); 11329 printOomLevel(pw, "BACKUP_APP_ADJ", ProcessList.BACKUP_APP_ADJ); 11330 printOomLevel(pw, "HEAVY_WEIGHT_APP_ADJ", ProcessList.HEAVY_WEIGHT_APP_ADJ); 11331 printOomLevel(pw, "SERVICE_ADJ", ProcessList.SERVICE_ADJ); 11332 printOomLevel(pw, "HOME_APP_ADJ", ProcessList.HOME_APP_ADJ); 11333 printOomLevel(pw, "PREVIOUS_APP_ADJ", ProcessList.PREVIOUS_APP_ADJ); 11334 printOomLevel(pw, "SERVICE_B_ADJ", ProcessList.SERVICE_B_ADJ); 11335 printOomLevel(pw, "CACHED_APP_MIN_ADJ", ProcessList.CACHED_APP_MIN_ADJ); 11336 printOomLevel(pw, "CACHED_APP_MAX_ADJ", ProcessList.CACHED_APP_MAX_ADJ); 11337 11338 if (needSep) pw.println(); 11339 pw.print(" Process OOM control ("); pw.print(mLruProcesses.size()); 11340 pw.print(" total, non-act at "); 11341 pw.print(mLruProcesses.size()-mLruProcessActivityStart); 11342 pw.print(", non-svc at "); 11343 pw.print(mLruProcesses.size()-mLruProcessServiceStart); 11344 pw.println("):"); 11345 dumpProcessOomList(pw, this, mLruProcesses, " ", "Proc", "PERS", true, null); 11346 needSep = true; 11347 } 11348 11349 dumpProcessesToGc(fd, pw, args, opti, needSep, dumpAll, null); 11350 11351 pw.println(); 11352 pw.println(" mHomeProcess: " + mHomeProcess); 11353 pw.println(" mPreviousProcess: " + mPreviousProcess); 11354 if (mHeavyWeightProcess != null) { 11355 pw.println(" mHeavyWeightProcess: " + mHeavyWeightProcess); 11356 } 11357 11358 return true; 11359 } 11360 11361 /** 11362 * There are three ways to call this: 11363 * - no provider specified: dump all the providers 11364 * - a flattened component name that matched an existing provider was specified as the 11365 * first arg: dump that one provider 11366 * - the first arg isn't the flattened component name of an existing provider: 11367 * dump all providers whose component contains the first arg as a substring 11368 */ 11369 protected boolean dumpProvider(FileDescriptor fd, PrintWriter pw, String name, String[] args, 11370 int opti, boolean dumpAll) { 11371 return mProviderMap.dumpProvider(fd, pw, name, args, opti, dumpAll); 11372 } 11373 11374 static class ItemMatcher { 11375 ArrayList<ComponentName> components; 11376 ArrayList<String> strings; 11377 ArrayList<Integer> objects; 11378 boolean all; 11379 11380 ItemMatcher() { 11381 all = true; 11382 } 11383 11384 void build(String name) { 11385 ComponentName componentName = ComponentName.unflattenFromString(name); 11386 if (componentName != null) { 11387 if (components == null) { 11388 components = new ArrayList<ComponentName>(); 11389 } 11390 components.add(componentName); 11391 all = false; 11392 } else { 11393 int objectId = 0; 11394 // Not a '/' separated full component name; maybe an object ID? 11395 try { 11396 objectId = Integer.parseInt(name, 16); 11397 if (objects == null) { 11398 objects = new ArrayList<Integer>(); 11399 } 11400 objects.add(objectId); 11401 all = false; 11402 } catch (RuntimeException e) { 11403 // Not an integer; just do string match. 11404 if (strings == null) { 11405 strings = new ArrayList<String>(); 11406 } 11407 strings.add(name); 11408 all = false; 11409 } 11410 } 11411 } 11412 11413 int build(String[] args, int opti) { 11414 for (; opti<args.length; opti++) { 11415 String name = args[opti]; 11416 if ("--".equals(name)) { 11417 return opti+1; 11418 } 11419 build(name); 11420 } 11421 return opti; 11422 } 11423 11424 boolean match(Object object, ComponentName comp) { 11425 if (all) { 11426 return true; 11427 } 11428 if (components != null) { 11429 for (int i=0; i<components.size(); i++) { 11430 if (components.get(i).equals(comp)) { 11431 return true; 11432 } 11433 } 11434 } 11435 if (objects != null) { 11436 for (int i=0; i<objects.size(); i++) { 11437 if (System.identityHashCode(object) == objects.get(i)) { 11438 return true; 11439 } 11440 } 11441 } 11442 if (strings != null) { 11443 String flat = comp.flattenToString(); 11444 for (int i=0; i<strings.size(); i++) { 11445 if (flat.contains(strings.get(i))) { 11446 return true; 11447 } 11448 } 11449 } 11450 return false; 11451 } 11452 } 11453 11454 /** 11455 * There are three things that cmd can be: 11456 * - a flattened component name that matches an existing activity 11457 * - the cmd arg isn't the flattened component name of an existing activity: 11458 * dump all activity whose component contains the cmd as a substring 11459 * - A hex number of the ActivityRecord object instance. 11460 */ 11461 protected boolean dumpActivity(FileDescriptor fd, PrintWriter pw, String name, String[] args, 11462 int opti, boolean dumpAll) { 11463 ArrayList<ActivityRecord> activities; 11464 11465 synchronized (this) { 11466 activities = mStackSupervisor.getDumpActivitiesLocked(name); 11467 } 11468 11469 if (activities.size() <= 0) { 11470 return false; 11471 } 11472 11473 String[] newArgs = new String[args.length - opti]; 11474 System.arraycopy(args, opti, newArgs, 0, args.length - opti); 11475 11476 TaskRecord lastTask = null; 11477 boolean needSep = false; 11478 for (int i=activities.size()-1; i>=0; i--) { 11479 ActivityRecord r = activities.get(i); 11480 if (needSep) { 11481 pw.println(); 11482 } 11483 needSep = true; 11484 synchronized (this) { 11485 if (lastTask != r.task) { 11486 lastTask = r.task; 11487 pw.print("TASK "); pw.print(lastTask.affinity); 11488 pw.print(" id="); pw.println(lastTask.taskId); 11489 if (dumpAll) { 11490 lastTask.dump(pw, " "); 11491 } 11492 } 11493 } 11494 dumpActivity(" ", fd, pw, activities.get(i), newArgs, dumpAll); 11495 } 11496 return true; 11497 } 11498 11499 /** 11500 * Invokes IApplicationThread.dumpActivity() on the thread of the specified activity if 11501 * there is a thread associated with the activity. 11502 */ 11503 private void dumpActivity(String prefix, FileDescriptor fd, PrintWriter pw, 11504 final ActivityRecord r, String[] args, boolean dumpAll) { 11505 String innerPrefix = prefix + " "; 11506 synchronized (this) { 11507 pw.print(prefix); pw.print("ACTIVITY "); pw.print(r.shortComponentName); 11508 pw.print(" "); pw.print(Integer.toHexString(System.identityHashCode(r))); 11509 pw.print(" pid="); 11510 if (r.app != null) pw.println(r.app.pid); 11511 else pw.println("(not running)"); 11512 if (dumpAll) { 11513 r.dump(pw, innerPrefix); 11514 } 11515 } 11516 if (r.app != null && r.app.thread != null) { 11517 // flush anything that is already in the PrintWriter since the thread is going 11518 // to write to the file descriptor directly 11519 pw.flush(); 11520 try { 11521 TransferPipe tp = new TransferPipe(); 11522 try { 11523 r.app.thread.dumpActivity(tp.getWriteFd().getFileDescriptor(), 11524 r.appToken, innerPrefix, args); 11525 tp.go(fd); 11526 } finally { 11527 tp.kill(); 11528 } 11529 } catch (IOException e) { 11530 pw.println(innerPrefix + "Failure while dumping the activity: " + e); 11531 } catch (RemoteException e) { 11532 pw.println(innerPrefix + "Got a RemoteException while dumping the activity"); 11533 } 11534 } 11535 } 11536 11537 void dumpBroadcastsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11538 int opti, boolean dumpAll, String dumpPackage) { 11539 boolean needSep = false; 11540 boolean onlyHistory = false; 11541 boolean printedAnything = false; 11542 11543 if ("history".equals(dumpPackage)) { 11544 if (opti < args.length && "-s".equals(args[opti])) { 11545 dumpAll = false; 11546 } 11547 onlyHistory = true; 11548 dumpPackage = null; 11549 } 11550 11551 pw.println("ACTIVITY MANAGER BROADCAST STATE (dumpsys activity broadcasts)"); 11552 if (!onlyHistory && dumpAll) { 11553 if (mRegisteredReceivers.size() > 0) { 11554 boolean printed = false; 11555 Iterator it = mRegisteredReceivers.values().iterator(); 11556 while (it.hasNext()) { 11557 ReceiverList r = (ReceiverList)it.next(); 11558 if (dumpPackage != null && (r.app == null || 11559 !dumpPackage.equals(r.app.info.packageName))) { 11560 continue; 11561 } 11562 if (!printed) { 11563 pw.println(" Registered Receivers:"); 11564 needSep = true; 11565 printed = true; 11566 printedAnything = true; 11567 } 11568 pw.print(" * "); pw.println(r); 11569 r.dump(pw, " "); 11570 } 11571 } 11572 11573 if (mReceiverResolver.dump(pw, needSep ? 11574 "\n Receiver Resolver Table:" : " Receiver Resolver Table:", 11575 " ", dumpPackage, false)) { 11576 needSep = true; 11577 printedAnything = true; 11578 } 11579 } 11580 11581 for (BroadcastQueue q : mBroadcastQueues) { 11582 needSep = q.dumpLocked(fd, pw, args, opti, dumpAll, dumpPackage, needSep); 11583 printedAnything |= needSep; 11584 } 11585 11586 needSep = true; 11587 11588 if (!onlyHistory && mStickyBroadcasts != null && dumpPackage == null) { 11589 for (int user=0; user<mStickyBroadcasts.size(); user++) { 11590 if (needSep) { 11591 pw.println(); 11592 } 11593 needSep = true; 11594 printedAnything = true; 11595 pw.print(" Sticky broadcasts for user "); 11596 pw.print(mStickyBroadcasts.keyAt(user)); pw.println(":"); 11597 StringBuilder sb = new StringBuilder(128); 11598 for (Map.Entry<String, ArrayList<Intent>> ent 11599 : mStickyBroadcasts.valueAt(user).entrySet()) { 11600 pw.print(" * Sticky action "); pw.print(ent.getKey()); 11601 if (dumpAll) { 11602 pw.println(":"); 11603 ArrayList<Intent> intents = ent.getValue(); 11604 final int N = intents.size(); 11605 for (int i=0; i<N; i++) { 11606 sb.setLength(0); 11607 sb.append(" Intent: "); 11608 intents.get(i).toShortString(sb, false, true, false, false); 11609 pw.println(sb.toString()); 11610 Bundle bundle = intents.get(i).getExtras(); 11611 if (bundle != null) { 11612 pw.print(" "); 11613 pw.println(bundle.toString()); 11614 } 11615 } 11616 } else { 11617 pw.println(""); 11618 } 11619 } 11620 } 11621 } 11622 11623 if (!onlyHistory && dumpAll) { 11624 pw.println(); 11625 for (BroadcastQueue queue : mBroadcastQueues) { 11626 pw.println(" mBroadcastsScheduled [" + queue.mQueueName + "]=" 11627 + queue.mBroadcastsScheduled); 11628 } 11629 pw.println(" mHandler:"); 11630 mHandler.dump(new PrintWriterPrinter(pw), " "); 11631 needSep = true; 11632 printedAnything = true; 11633 } 11634 11635 if (!printedAnything) { 11636 pw.println(" (nothing)"); 11637 } 11638 } 11639 11640 void dumpProvidersLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11641 int opti, boolean dumpAll, String dumpPackage) { 11642 boolean needSep; 11643 boolean printedAnything = false; 11644 11645 ItemMatcher matcher = new ItemMatcher(); 11646 matcher.build(args, opti); 11647 11648 pw.println("ACTIVITY MANAGER CONTENT PROVIDERS (dumpsys activity providers)"); 11649 11650 needSep = mProviderMap.dumpProvidersLocked(pw, dumpAll, dumpPackage); 11651 printedAnything |= needSep; 11652 11653 if (mLaunchingProviders.size() > 0) { 11654 boolean printed = false; 11655 for (int i=mLaunchingProviders.size()-1; i>=0; i--) { 11656 ContentProviderRecord r = mLaunchingProviders.get(i); 11657 if (dumpPackage != null && !dumpPackage.equals(r.name.getPackageName())) { 11658 continue; 11659 } 11660 if (!printed) { 11661 if (needSep) pw.println(); 11662 needSep = true; 11663 pw.println(" Launching content providers:"); 11664 printed = true; 11665 printedAnything = true; 11666 } 11667 pw.print(" Launching #"); pw.print(i); pw.print(": "); 11668 pw.println(r); 11669 } 11670 } 11671 11672 if (mGrantedUriPermissions.size() > 0) { 11673 boolean printed = false; 11674 int dumpUid = -2; 11675 if (dumpPackage != null) { 11676 try { 11677 dumpUid = mContext.getPackageManager().getPackageUid(dumpPackage, 0); 11678 } catch (NameNotFoundException e) { 11679 dumpUid = -1; 11680 } 11681 } 11682 for (int i=0; i<mGrantedUriPermissions.size(); i++) { 11683 int uid = mGrantedUriPermissions.keyAt(i); 11684 if (dumpUid >= -1 && UserHandle.getAppId(uid) != dumpUid) { 11685 continue; 11686 } 11687 final ArrayMap<GrantUri, UriPermission> perms = mGrantedUriPermissions.valueAt(i); 11688 if (!printed) { 11689 if (needSep) pw.println(); 11690 needSep = true; 11691 pw.println(" Granted Uri Permissions:"); 11692 printed = true; 11693 printedAnything = true; 11694 } 11695 pw.print(" * UID "); pw.print(uid); pw.println(" holds:"); 11696 for (UriPermission perm : perms.values()) { 11697 pw.print(" "); pw.println(perm); 11698 if (dumpAll) { 11699 perm.dump(pw, " "); 11700 } 11701 } 11702 } 11703 } 11704 11705 if (!printedAnything) { 11706 pw.println(" (nothing)"); 11707 } 11708 } 11709 11710 void dumpPendingIntentsLocked(FileDescriptor fd, PrintWriter pw, String[] args, 11711 int opti, boolean dumpAll, String dumpPackage) { 11712 boolean printed = false; 11713 11714 pw.println("ACTIVITY MANAGER PENDING INTENTS (dumpsys activity intents)"); 11715 11716 if (mIntentSenderRecords.size() > 0) { 11717 Iterator<WeakReference<PendingIntentRecord>> it 11718 = mIntentSenderRecords.values().iterator(); 11719 while (it.hasNext()) { 11720 WeakReference<PendingIntentRecord> ref = it.next(); 11721 PendingIntentRecord rec = ref != null ? ref.get(): null; 11722 if (dumpPackage != null && (rec == null 11723 || !dumpPackage.equals(rec.key.packageName))) { 11724 continue; 11725 } 11726 printed = true; 11727 if (rec != null) { 11728 pw.print(" * "); pw.println(rec); 11729 if (dumpAll) { 11730 rec.dump(pw, " "); 11731 } 11732 } else { 11733 pw.print(" * "); pw.println(ref); 11734 } 11735 } 11736 } 11737 11738 if (!printed) { 11739 pw.println(" (nothing)"); 11740 } 11741 } 11742 11743 private static final int dumpProcessList(PrintWriter pw, 11744 ActivityManagerService service, List list, 11745 String prefix, String normalLabel, String persistentLabel, 11746 String dumpPackage) { 11747 int numPers = 0; 11748 final int N = list.size()-1; 11749 for (int i=N; i>=0; i--) { 11750 ProcessRecord r = (ProcessRecord)list.get(i); 11751 if (dumpPackage != null && !dumpPackage.equals(r.info.packageName)) { 11752 continue; 11753 } 11754 pw.println(String.format("%s%s #%2d: %s", 11755 prefix, (r.persistent ? persistentLabel : normalLabel), 11756 i, r.toString())); 11757 if (r.persistent) { 11758 numPers++; 11759 } 11760 } 11761 return numPers; 11762 } 11763 11764 private static final boolean dumpProcessOomList(PrintWriter pw, 11765 ActivityManagerService service, List<ProcessRecord> origList, 11766 String prefix, String normalLabel, String persistentLabel, 11767 boolean inclDetails, String dumpPackage) { 11768 11769 ArrayList<Pair<ProcessRecord, Integer>> list 11770 = new ArrayList<Pair<ProcessRecord, Integer>>(origList.size()); 11771 for (int i=0; i<origList.size(); i++) { 11772 ProcessRecord r = origList.get(i); 11773 if (dumpPackage != null && !r.pkgList.containsKey(dumpPackage)) { 11774 continue; 11775 } 11776 list.add(new Pair<ProcessRecord, Integer>(origList.get(i), i)); 11777 } 11778 11779 if (list.size() <= 0) { 11780 return false; 11781 } 11782 11783 Comparator<Pair<ProcessRecord, Integer>> comparator 11784 = new Comparator<Pair<ProcessRecord, Integer>>() { 11785 @Override 11786 public int compare(Pair<ProcessRecord, Integer> object1, 11787 Pair<ProcessRecord, Integer> object2) { 11788 if (object1.first.setAdj != object2.first.setAdj) { 11789 return object1.first.setAdj > object2.first.setAdj ? -1 : 1; 11790 } 11791 if (object1.second.intValue() != object2.second.intValue()) { 11792 return object1.second.intValue() > object2.second.intValue() ? -1 : 1; 11793 } 11794 return 0; 11795 } 11796 }; 11797 11798 Collections.sort(list, comparator); 11799 11800 final long curRealtime = SystemClock.elapsedRealtime(); 11801 final long realtimeSince = curRealtime - service.mLastPowerCheckRealtime; 11802 final long curUptime = SystemClock.uptimeMillis(); 11803 final long uptimeSince = curUptime - service.mLastPowerCheckUptime; 11804 11805 for (int i=list.size()-1; i>=0; i--) { 11806 ProcessRecord r = list.get(i).first; 11807 String oomAdj = ProcessList.makeOomAdjString(r.setAdj); 11808 char schedGroup; 11809 switch (r.setSchedGroup) { 11810 case Process.THREAD_GROUP_BG_NONINTERACTIVE: 11811 schedGroup = 'B'; 11812 break; 11813 case Process.THREAD_GROUP_DEFAULT: 11814 schedGroup = 'F'; 11815 break; 11816 default: 11817 schedGroup = '?'; 11818 break; 11819 } 11820 char foreground; 11821 if (r.foregroundActivities) { 11822 foreground = 'A'; 11823 } else if (r.foregroundServices) { 11824 foreground = 'S'; 11825 } else { 11826 foreground = ' '; 11827 } 11828 String procState = ProcessList.makeProcStateString(r.curProcState); 11829 pw.print(prefix); 11830 pw.print(r.persistent ? persistentLabel : normalLabel); 11831 pw.print(" #"); 11832 int num = (origList.size()-1)-list.get(i).second; 11833 if (num < 10) pw.print(' '); 11834 pw.print(num); 11835 pw.print(": "); 11836 pw.print(oomAdj); 11837 pw.print(' '); 11838 pw.print(schedGroup); 11839 pw.print('/'); 11840 pw.print(foreground); 11841 pw.print('/'); 11842 pw.print(procState); 11843 pw.print(" trm:"); 11844 if (r.trimMemoryLevel < 10) pw.print(' '); 11845 pw.print(r.trimMemoryLevel); 11846 pw.print(' '); 11847 pw.print(r.toShortString()); 11848 pw.print(" ("); 11849 pw.print(r.adjType); 11850 pw.println(')'); 11851 if (r.adjSource != null || r.adjTarget != null) { 11852 pw.print(prefix); 11853 pw.print(" "); 11854 if (r.adjTarget instanceof ComponentName) { 11855 pw.print(((ComponentName)r.adjTarget).flattenToShortString()); 11856 } else if (r.adjTarget != null) { 11857 pw.print(r.adjTarget.toString()); 11858 } else { 11859 pw.print("{null}"); 11860 } 11861 pw.print("<="); 11862 if (r.adjSource instanceof ProcessRecord) { 11863 pw.print("Proc{"); 11864 pw.print(((ProcessRecord)r.adjSource).toShortString()); 11865 pw.println("}"); 11866 } else if (r.adjSource != null) { 11867 pw.println(r.adjSource.toString()); 11868 } else { 11869 pw.println("{null}"); 11870 } 11871 } 11872 if (inclDetails) { 11873 pw.print(prefix); 11874 pw.print(" "); 11875 pw.print("oom: max="); pw.print(r.maxAdj); 11876 pw.print(" curRaw="); pw.print(r.curRawAdj); 11877 pw.print(" setRaw="); pw.print(r.setRawAdj); 11878 pw.print(" cur="); pw.print(r.curAdj); 11879 pw.print(" set="); pw.println(r.setAdj); 11880 pw.print(prefix); 11881 pw.print(" "); 11882 pw.print("state: cur="); pw.print(ProcessList.makeProcStateString(r.curProcState)); 11883 pw.print(" set="); pw.print(ProcessList.makeProcStateString(r.setProcState)); 11884 pw.print(" lastPss="); pw.print(r.lastPss); 11885 pw.print(" lastCachedPss="); pw.println(r.lastCachedPss); 11886 pw.print(prefix); 11887 pw.print(" "); 11888 pw.print("keeping="); pw.print(r.keeping); 11889 pw.print(" cached="); pw.print(r.cached); 11890 pw.print(" empty="); pw.print(r.empty); 11891 pw.print(" hasAboveClient="); pw.println(r.hasAboveClient); 11892 11893 if (!r.keeping) { 11894 if (r.lastWakeTime != 0) { 11895 long wtime; 11896 BatteryStatsImpl stats = service.mBatteryStatsService.getActiveStatistics(); 11897 synchronized (stats) { 11898 wtime = stats.getProcessWakeTime(r.info.uid, 11899 r.pid, curRealtime); 11900 } 11901 long timeUsed = wtime - r.lastWakeTime; 11902 pw.print(prefix); 11903 pw.print(" "); 11904 pw.print("keep awake over "); 11905 TimeUtils.formatDuration(realtimeSince, pw); 11906 pw.print(" used "); 11907 TimeUtils.formatDuration(timeUsed, pw); 11908 pw.print(" ("); 11909 pw.print((timeUsed*100)/realtimeSince); 11910 pw.println("%)"); 11911 } 11912 if (r.lastCpuTime != 0) { 11913 long timeUsed = r.curCpuTime - r.lastCpuTime; 11914 pw.print(prefix); 11915 pw.print(" "); 11916 pw.print("run cpu over "); 11917 TimeUtils.formatDuration(uptimeSince, pw); 11918 pw.print(" used "); 11919 TimeUtils.formatDuration(timeUsed, pw); 11920 pw.print(" ("); 11921 pw.print((timeUsed*100)/uptimeSince); 11922 pw.println("%)"); 11923 } 11924 } 11925 } 11926 } 11927 return true; 11928 } 11929 11930 ArrayList<ProcessRecord> collectProcesses(PrintWriter pw, int start, String[] args) { 11931 ArrayList<ProcessRecord> procs; 11932 synchronized (this) { 11933 if (args != null && args.length > start 11934 && args[start].charAt(0) != '-') { 11935 procs = new ArrayList<ProcessRecord>(); 11936 int pid = -1; 11937 try { 11938 pid = Integer.parseInt(args[start]); 11939 } catch (NumberFormatException e) { 11940 } 11941 for (int i=mLruProcesses.size()-1; i>=0; i--) { 11942 ProcessRecord proc = mLruProcesses.get(i); 11943 if (proc.pid == pid) { 11944 procs.add(proc); 11945 } else if (proc.processName.equals(args[start])) { 11946 procs.add(proc); 11947 } 11948 } 11949 if (procs.size() <= 0) { 11950 return null; 11951 } 11952 } else { 11953 procs = new ArrayList<ProcessRecord>(mLruProcesses); 11954 } 11955 } 11956 return procs; 11957 } 11958 11959 final void dumpGraphicsHardwareUsage(FileDescriptor fd, 11960 PrintWriter pw, String[] args) { 11961 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 11962 if (procs == null) { 11963 pw.println("No process found for: " + args[0]); 11964 return; 11965 } 11966 11967 long uptime = SystemClock.uptimeMillis(); 11968 long realtime = SystemClock.elapsedRealtime(); 11969 pw.println("Applications Graphics Acceleration Info:"); 11970 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 11971 11972 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 11973 ProcessRecord r = procs.get(i); 11974 if (r.thread != null) { 11975 pw.println("\n** Graphics info for pid " + r.pid + " [" + r.processName + "] **"); 11976 pw.flush(); 11977 try { 11978 TransferPipe tp = new TransferPipe(); 11979 try { 11980 r.thread.dumpGfxInfo(tp.getWriteFd().getFileDescriptor(), args); 11981 tp.go(fd); 11982 } finally { 11983 tp.kill(); 11984 } 11985 } catch (IOException e) { 11986 pw.println("Failure while dumping the app: " + r); 11987 pw.flush(); 11988 } catch (RemoteException e) { 11989 pw.println("Got a RemoteException while dumping the app " + r); 11990 pw.flush(); 11991 } 11992 } 11993 } 11994 } 11995 11996 final void dumpDbInfo(FileDescriptor fd, PrintWriter pw, String[] args) { 11997 ArrayList<ProcessRecord> procs = collectProcesses(pw, 0, args); 11998 if (procs == null) { 11999 pw.println("No process found for: " + args[0]); 12000 return; 12001 } 12002 12003 pw.println("Applications Database Info:"); 12004 12005 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12006 ProcessRecord r = procs.get(i); 12007 if (r.thread != null) { 12008 pw.println("\n** Database info for pid " + r.pid + " [" + r.processName + "] **"); 12009 pw.flush(); 12010 try { 12011 TransferPipe tp = new TransferPipe(); 12012 try { 12013 r.thread.dumpDbInfo(tp.getWriteFd().getFileDescriptor(), args); 12014 tp.go(fd); 12015 } finally { 12016 tp.kill(); 12017 } 12018 } catch (IOException e) { 12019 pw.println("Failure while dumping the app: " + r); 12020 pw.flush(); 12021 } catch (RemoteException e) { 12022 pw.println("Got a RemoteException while dumping the app " + r); 12023 pw.flush(); 12024 } 12025 } 12026 } 12027 } 12028 12029 final static class MemItem { 12030 final boolean isProc; 12031 final String label; 12032 final String shortLabel; 12033 final long pss; 12034 final int id; 12035 final boolean hasActivities; 12036 ArrayList<MemItem> subitems; 12037 12038 public MemItem(String _label, String _shortLabel, long _pss, int _id, 12039 boolean _hasActivities) { 12040 isProc = true; 12041 label = _label; 12042 shortLabel = _shortLabel; 12043 pss = _pss; 12044 id = _id; 12045 hasActivities = _hasActivities; 12046 } 12047 12048 public MemItem(String _label, String _shortLabel, long _pss, int _id) { 12049 isProc = false; 12050 label = _label; 12051 shortLabel = _shortLabel; 12052 pss = _pss; 12053 id = _id; 12054 hasActivities = false; 12055 } 12056 } 12057 12058 static final void dumpMemItems(PrintWriter pw, String prefix, String tag, 12059 ArrayList<MemItem> items, boolean sort, boolean isCompact) { 12060 if (sort && !isCompact) { 12061 Collections.sort(items, new Comparator<MemItem>() { 12062 @Override 12063 public int compare(MemItem lhs, MemItem rhs) { 12064 if (lhs.pss < rhs.pss) { 12065 return 1; 12066 } else if (lhs.pss > rhs.pss) { 12067 return -1; 12068 } 12069 return 0; 12070 } 12071 }); 12072 } 12073 12074 for (int i=0; i<items.size(); i++) { 12075 MemItem mi = items.get(i); 12076 if (!isCompact) { 12077 pw.print(prefix); pw.printf("%7d kB: ", mi.pss); pw.println(mi.label); 12078 } else if (mi.isProc) { 12079 pw.print("proc,"); pw.print(tag); pw.print(","); pw.print(mi.shortLabel); 12080 pw.print(","); pw.print(mi.id); pw.print(","); pw.print(mi.pss); 12081 pw.println(mi.hasActivities ? ",a" : ",e"); 12082 } else { 12083 pw.print(tag); pw.print(","); pw.print(mi.shortLabel); pw.print(","); 12084 pw.println(mi.pss); 12085 } 12086 if (mi.subitems != null) { 12087 dumpMemItems(pw, prefix + " ", mi.shortLabel, mi.subitems, 12088 true, isCompact); 12089 } 12090 } 12091 } 12092 12093 // These are in KB. 12094 static final long[] DUMP_MEM_BUCKETS = new long[] { 12095 5*1024, 7*1024, 10*1024, 15*1024, 20*1024, 30*1024, 40*1024, 80*1024, 12096 120*1024, 160*1024, 200*1024, 12097 250*1024, 300*1024, 350*1024, 400*1024, 500*1024, 600*1024, 800*1024, 12098 1*1024*1024, 2*1024*1024, 5*1024*1024, 10*1024*1024, 20*1024*1024 12099 }; 12100 12101 static final void appendMemBucket(StringBuilder out, long memKB, String label, 12102 boolean stackLike) { 12103 int start = label.lastIndexOf('.'); 12104 if (start >= 0) start++; 12105 else start = 0; 12106 int end = label.length(); 12107 for (int i=0; i<DUMP_MEM_BUCKETS.length; i++) { 12108 if (DUMP_MEM_BUCKETS[i] >= memKB) { 12109 long bucket = DUMP_MEM_BUCKETS[i]/1024; 12110 out.append(bucket); 12111 out.append(stackLike ? "MB." : "MB "); 12112 out.append(label, start, end); 12113 return; 12114 } 12115 } 12116 out.append(memKB/1024); 12117 out.append(stackLike ? "MB." : "MB "); 12118 out.append(label, start, end); 12119 } 12120 12121 static final int[] DUMP_MEM_OOM_ADJ = new int[] { 12122 ProcessList.NATIVE_ADJ, 12123 ProcessList.SYSTEM_ADJ, ProcessList.PERSISTENT_PROC_ADJ, ProcessList.FOREGROUND_APP_ADJ, 12124 ProcessList.VISIBLE_APP_ADJ, ProcessList.PERCEPTIBLE_APP_ADJ, 12125 ProcessList.BACKUP_APP_ADJ, ProcessList.HEAVY_WEIGHT_APP_ADJ, 12126 ProcessList.SERVICE_ADJ, ProcessList.HOME_APP_ADJ, 12127 ProcessList.PREVIOUS_APP_ADJ, ProcessList.SERVICE_B_ADJ, ProcessList.CACHED_APP_MAX_ADJ 12128 }; 12129 static final String[] DUMP_MEM_OOM_LABEL = new String[] { 12130 "Native", 12131 "System", "Persistent", "Foreground", 12132 "Visible", "Perceptible", 12133 "Heavy Weight", "Backup", 12134 "A Services", "Home", 12135 "Previous", "B Services", "Cached" 12136 }; 12137 static final String[] DUMP_MEM_OOM_COMPACT_LABEL = new String[] { 12138 "native", 12139 "sys", "pers", "fore", 12140 "vis", "percept", 12141 "heavy", "backup", 12142 "servicea", "home", 12143 "prev", "serviceb", "cached" 12144 }; 12145 12146 private final void dumpApplicationMemoryUsageHeader(PrintWriter pw, long uptime, 12147 long realtime, boolean isCheckinRequest, boolean isCompact) { 12148 if (isCheckinRequest || isCompact) { 12149 // short checkin version 12150 pw.print("time,"); pw.print(uptime); pw.print(","); pw.println(realtime); 12151 } else { 12152 pw.println("Applications Memory Usage (kB):"); 12153 pw.println("Uptime: " + uptime + " Realtime: " + realtime); 12154 } 12155 } 12156 12157 final void dumpApplicationMemoryUsage(FileDescriptor fd, 12158 PrintWriter pw, String prefix, String[] args, boolean brief, PrintWriter categoryPw) { 12159 boolean dumpDetails = false; 12160 boolean dumpFullDetails = false; 12161 boolean dumpDalvik = false; 12162 boolean oomOnly = false; 12163 boolean isCompact = false; 12164 boolean localOnly = false; 12165 12166 int opti = 0; 12167 while (opti < args.length) { 12168 String opt = args[opti]; 12169 if (opt == null || opt.length() <= 0 || opt.charAt(0) != '-') { 12170 break; 12171 } 12172 opti++; 12173 if ("-a".equals(opt)) { 12174 dumpDetails = true; 12175 dumpFullDetails = true; 12176 dumpDalvik = true; 12177 } else if ("-d".equals(opt)) { 12178 dumpDalvik = true; 12179 } else if ("-c".equals(opt)) { 12180 isCompact = true; 12181 } else if ("--oom".equals(opt)) { 12182 oomOnly = true; 12183 } else if ("--local".equals(opt)) { 12184 localOnly = true; 12185 } else if ("-h".equals(opt)) { 12186 pw.println("meminfo dump options: [-a] [-d] [-c] [--oom] [process]"); 12187 pw.println(" -a: include all available information for each process."); 12188 pw.println(" -d: include dalvik details when dumping process details."); 12189 pw.println(" -c: dump in a compact machine-parseable representation."); 12190 pw.println(" --oom: only show processes organized by oom adj."); 12191 pw.println(" --local: only collect details locally, don't call process."); 12192 pw.println("If [process] is specified it can be the name or "); 12193 pw.println("pid of a specific process to dump."); 12194 return; 12195 } else { 12196 pw.println("Unknown argument: " + opt + "; use -h for help"); 12197 } 12198 } 12199 12200 final boolean isCheckinRequest = scanArgs(args, "--checkin"); 12201 long uptime = SystemClock.uptimeMillis(); 12202 long realtime = SystemClock.elapsedRealtime(); 12203 final long[] tmpLong = new long[1]; 12204 12205 ArrayList<ProcessRecord> procs = collectProcesses(pw, opti, args); 12206 if (procs == null) { 12207 // No Java processes. Maybe they want to print a native process. 12208 if (args != null && args.length > opti 12209 && args[opti].charAt(0) != '-') { 12210 ArrayList<ProcessCpuTracker.Stats> nativeProcs 12211 = new ArrayList<ProcessCpuTracker.Stats>(); 12212 updateCpuStatsNow(); 12213 int findPid = -1; 12214 try { 12215 findPid = Integer.parseInt(args[opti]); 12216 } catch (NumberFormatException e) { 12217 } 12218 synchronized (mProcessCpuThread) { 12219 final int N = mProcessCpuTracker.countStats(); 12220 for (int i=0; i<N; i++) { 12221 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 12222 if (st.pid == findPid || (st.baseName != null 12223 && st.baseName.equals(args[opti]))) { 12224 nativeProcs.add(st); 12225 } 12226 } 12227 } 12228 if (nativeProcs.size() > 0) { 12229 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, 12230 isCompact); 12231 Debug.MemoryInfo mi = null; 12232 for (int i = nativeProcs.size() - 1 ; i >= 0 ; i--) { 12233 final ProcessCpuTracker.Stats r = nativeProcs.get(i); 12234 final int pid = r.pid; 12235 if (!isCheckinRequest && dumpDetails) { 12236 pw.println("\n** MEMINFO in pid " + pid + " [" + r.baseName + "] **"); 12237 } 12238 if (mi == null) { 12239 mi = new Debug.MemoryInfo(); 12240 } 12241 if (dumpDetails || (!brief && !oomOnly)) { 12242 Debug.getMemoryInfo(pid, mi); 12243 } else { 12244 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 12245 mi.dalvikPrivateDirty = (int)tmpLong[0]; 12246 } 12247 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 12248 dumpDalvik, pid, r.baseName, 0, 0, 0, 0, 0, 0); 12249 if (isCheckinRequest) { 12250 pw.println(); 12251 } 12252 } 12253 return; 12254 } 12255 } 12256 pw.println("No process found for: " + args[opti]); 12257 return; 12258 } 12259 12260 if (!brief && !oomOnly && (procs.size() == 1 || isCheckinRequest)) { 12261 dumpDetails = true; 12262 } 12263 12264 dumpApplicationMemoryUsageHeader(pw, uptime, realtime, isCheckinRequest, isCompact); 12265 12266 String[] innerArgs = new String[args.length-opti]; 12267 System.arraycopy(args, opti, innerArgs, 0, args.length-opti); 12268 12269 ArrayList<MemItem> procMems = new ArrayList<MemItem>(); 12270 final SparseArray<MemItem> procMemsMap = new SparseArray<MemItem>(); 12271 long nativePss=0, dalvikPss=0, otherPss=0; 12272 long[] miscPss = new long[Debug.MemoryInfo.NUM_OTHER_STATS]; 12273 12274 long oomPss[] = new long[DUMP_MEM_OOM_LABEL.length]; 12275 ArrayList<MemItem>[] oomProcs = (ArrayList<MemItem>[]) 12276 new ArrayList[DUMP_MEM_OOM_LABEL.length]; 12277 12278 long totalPss = 0; 12279 long cachedPss = 0; 12280 12281 Debug.MemoryInfo mi = null; 12282 for (int i = procs.size() - 1 ; i >= 0 ; i--) { 12283 final ProcessRecord r = procs.get(i); 12284 final IApplicationThread thread; 12285 final int pid; 12286 final int oomAdj; 12287 final boolean hasActivities; 12288 synchronized (this) { 12289 thread = r.thread; 12290 pid = r.pid; 12291 oomAdj = r.getSetAdjWithServices(); 12292 hasActivities = r.activities.size() > 0; 12293 } 12294 if (thread != null) { 12295 if (!isCheckinRequest && dumpDetails) { 12296 pw.println("\n** MEMINFO in pid " + pid + " [" + r.processName + "] **"); 12297 } 12298 if (mi == null) { 12299 mi = new Debug.MemoryInfo(); 12300 } 12301 if (dumpDetails || (!brief && !oomOnly)) { 12302 Debug.getMemoryInfo(pid, mi); 12303 } else { 12304 mi.dalvikPss = (int)Debug.getPss(pid, tmpLong); 12305 mi.dalvikPrivateDirty = (int)tmpLong[0]; 12306 } 12307 if (dumpDetails) { 12308 if (localOnly) { 12309 ActivityThread.dumpMemInfoTable(pw, mi, isCheckinRequest, dumpFullDetails, 12310 dumpDalvik, pid, r.processName, 0, 0, 0, 0, 0, 0); 12311 if (isCheckinRequest) { 12312 pw.println(); 12313 } 12314 } else { 12315 try { 12316 pw.flush(); 12317 thread.dumpMemInfo(fd, mi, isCheckinRequest, dumpFullDetails, 12318 dumpDalvik, innerArgs); 12319 } catch (RemoteException e) { 12320 if (!isCheckinRequest) { 12321 pw.println("Got RemoteException!"); 12322 pw.flush(); 12323 } 12324 } 12325 } 12326 } 12327 12328 final long myTotalPss = mi.getTotalPss(); 12329 final long myTotalUss = mi.getTotalUss(); 12330 12331 synchronized (this) { 12332 if (r.thread != null && oomAdj == r.getSetAdjWithServices()) { 12333 // Record this for posterity if the process has been stable. 12334 r.baseProcessTracker.addPss(myTotalPss, myTotalUss, true, r.pkgList); 12335 } 12336 } 12337 12338 if (!isCheckinRequest && mi != null) { 12339 totalPss += myTotalPss; 12340 MemItem pssItem = new MemItem(r.processName + " (pid " + pid + 12341 (hasActivities ? " / activities)" : ")"), 12342 r.processName, myTotalPss, pid, hasActivities); 12343 procMems.add(pssItem); 12344 procMemsMap.put(pid, pssItem); 12345 12346 nativePss += mi.nativePss; 12347 dalvikPss += mi.dalvikPss; 12348 otherPss += mi.otherPss; 12349 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 12350 long mem = mi.getOtherPss(j); 12351 miscPss[j] += mem; 12352 otherPss -= mem; 12353 } 12354 12355 if (oomAdj >= ProcessList.CACHED_APP_MIN_ADJ) { 12356 cachedPss += myTotalPss; 12357 } 12358 12359 for (int oomIndex=0; oomIndex<oomPss.length; oomIndex++) { 12360 if (oomAdj <= DUMP_MEM_OOM_ADJ[oomIndex] 12361 || oomIndex == (oomPss.length-1)) { 12362 oomPss[oomIndex] += myTotalPss; 12363 if (oomProcs[oomIndex] == null) { 12364 oomProcs[oomIndex] = new ArrayList<MemItem>(); 12365 } 12366 oomProcs[oomIndex].add(pssItem); 12367 break; 12368 } 12369 } 12370 } 12371 } 12372 } 12373 12374 if (!isCheckinRequest && procs.size() > 1) { 12375 // If we are showing aggregations, also look for native processes to 12376 // include so that our aggregations are more accurate. 12377 updateCpuStatsNow(); 12378 synchronized (mProcessCpuThread) { 12379 final int N = mProcessCpuTracker.countStats(); 12380 for (int i=0; i<N; i++) { 12381 ProcessCpuTracker.Stats st = mProcessCpuTracker.getStats(i); 12382 if (st.vsize > 0 && procMemsMap.indexOfKey(st.pid) < 0) { 12383 if (mi == null) { 12384 mi = new Debug.MemoryInfo(); 12385 } 12386 if (!brief && !oomOnly) { 12387 Debug.getMemoryInfo(st.pid, mi); 12388 } else { 12389 mi.nativePss = (int)Debug.getPss(st.pid, tmpLong); 12390 mi.nativePrivateDirty = (int)tmpLong[0]; 12391 } 12392 12393 final long myTotalPss = mi.getTotalPss(); 12394 totalPss += myTotalPss; 12395 12396 MemItem pssItem = new MemItem(st.name + " (pid " + st.pid + ")", 12397 st.name, myTotalPss, st.pid, false); 12398 procMems.add(pssItem); 12399 12400 nativePss += mi.nativePss; 12401 dalvikPss += mi.dalvikPss; 12402 otherPss += mi.otherPss; 12403 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 12404 long mem = mi.getOtherPss(j); 12405 miscPss[j] += mem; 12406 otherPss -= mem; 12407 } 12408 oomPss[0] += myTotalPss; 12409 if (oomProcs[0] == null) { 12410 oomProcs[0] = new ArrayList<MemItem>(); 12411 } 12412 oomProcs[0].add(pssItem); 12413 } 12414 } 12415 } 12416 12417 ArrayList<MemItem> catMems = new ArrayList<MemItem>(); 12418 12419 catMems.add(new MemItem("Native", "Native", nativePss, -1)); 12420 catMems.add(new MemItem("Dalvik", "Dalvik", dalvikPss, -2)); 12421 catMems.add(new MemItem("Unknown", "Unknown", otherPss, -3)); 12422 for (int j=0; j<Debug.MemoryInfo.NUM_OTHER_STATS; j++) { 12423 String label = Debug.MemoryInfo.getOtherLabel(j); 12424 catMems.add(new MemItem(label, label, miscPss[j], j)); 12425 } 12426 12427 ArrayList<MemItem> oomMems = new ArrayList<MemItem>(); 12428 for (int j=0; j<oomPss.length; j++) { 12429 if (oomPss[j] != 0) { 12430 String label = isCompact ? DUMP_MEM_OOM_COMPACT_LABEL[j] 12431 : DUMP_MEM_OOM_LABEL[j]; 12432 MemItem item = new MemItem(label, label, oomPss[j], 12433 DUMP_MEM_OOM_ADJ[j]); 12434 item.subitems = oomProcs[j]; 12435 oomMems.add(item); 12436 } 12437 } 12438 12439 if (!brief && !oomOnly && !isCompact) { 12440 pw.println(); 12441 pw.println("Total PSS by process:"); 12442 dumpMemItems(pw, " ", "proc", procMems, true, isCompact); 12443 pw.println(); 12444 } 12445 if (!isCompact) { 12446 pw.println("Total PSS by OOM adjustment:"); 12447 } 12448 dumpMemItems(pw, " ", "oom", oomMems, false, isCompact); 12449 if (!brief && !oomOnly) { 12450 PrintWriter out = categoryPw != null ? categoryPw : pw; 12451 if (!isCompact) { 12452 out.println(); 12453 out.println("Total PSS by category:"); 12454 } 12455 dumpMemItems(out, " ", "cat", catMems, true, isCompact); 12456 } 12457 if (!isCompact) { 12458 pw.println(); 12459 } 12460 MemInfoReader memInfo = new MemInfoReader(); 12461 memInfo.readMemInfo(); 12462 if (!brief) { 12463 if (!isCompact) { 12464 pw.print("Total RAM: "); pw.print(memInfo.getTotalSizeKb()); 12465 pw.print(" kB (status "); 12466 switch (mLastMemoryLevel) { 12467 case ProcessStats.ADJ_MEM_FACTOR_NORMAL: 12468 pw.println("normal)"); 12469 break; 12470 case ProcessStats.ADJ_MEM_FACTOR_MODERATE: 12471 pw.println("moderate)"); 12472 break; 12473 case ProcessStats.ADJ_MEM_FACTOR_LOW: 12474 pw.println("low)"); 12475 break; 12476 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 12477 pw.println("critical)"); 12478 break; 12479 default: 12480 pw.print(mLastMemoryLevel); 12481 pw.println(")"); 12482 break; 12483 } 12484 pw.print(" Free RAM: "); pw.print(cachedPss + memInfo.getCachedSizeKb() 12485 + memInfo.getFreeSizeKb()); pw.print(" kB ("); 12486 pw.print(cachedPss); pw.print(" cached pss + "); 12487 pw.print(memInfo.getCachedSizeKb()); pw.print(" cached + "); 12488 pw.print(memInfo.getFreeSizeKb()); pw.println(" free)"); 12489 } else { 12490 pw.print("ram,"); pw.print(memInfo.getTotalSizeKb()); pw.print(","); 12491 pw.print(cachedPss + memInfo.getCachedSizeKb() 12492 + memInfo.getFreeSizeKb()); pw.print(","); 12493 pw.println(totalPss - cachedPss); 12494 } 12495 } 12496 if (!isCompact) { 12497 pw.print(" Used RAM: "); pw.print(totalPss - cachedPss 12498 + memInfo.getBuffersSizeKb() + memInfo.getShmemSizeKb() 12499 + memInfo.getSlabSizeKb()); pw.print(" kB ("); 12500 pw.print(totalPss - cachedPss); pw.print(" used pss + "); 12501 pw.print(memInfo.getBuffersSizeKb()); pw.print(" buffers + "); 12502 pw.print(memInfo.getShmemSizeKb()); pw.print(" shmem + "); 12503 pw.print(memInfo.getSlabSizeKb()); pw.println(" slab)"); 12504 pw.print(" Lost RAM: "); pw.print(memInfo.getTotalSizeKb() 12505 - totalPss - memInfo.getFreeSizeKb() - memInfo.getCachedSizeKb() 12506 - memInfo.getBuffersSizeKb() - memInfo.getShmemSizeKb() 12507 - memInfo.getSlabSizeKb()); pw.println(" kB"); 12508 } 12509 if (!brief) { 12510 if (memInfo.getZramTotalSizeKb() != 0) { 12511 if (!isCompact) { 12512 pw.print(" ZRAM: "); pw.print(memInfo.getZramTotalSizeKb()); 12513 pw.print(" kB physical used for "); 12514 pw.print(memInfo.getSwapTotalSizeKb() 12515 - memInfo.getSwapFreeSizeKb()); 12516 pw.print(" kB in swap ("); 12517 pw.print(memInfo.getSwapTotalSizeKb()); 12518 pw.println(" kB total swap)"); 12519 } else { 12520 pw.print("zram,"); pw.print(memInfo.getZramTotalSizeKb()); pw.print(","); 12521 pw.print(memInfo.getSwapTotalSizeKb()); pw.print(","); 12522 pw.println(memInfo.getSwapFreeSizeKb()); 12523 } 12524 } 12525 final int[] SINGLE_LONG_FORMAT = new int[] { 12526 Process.PROC_SPACE_TERM|Process.PROC_OUT_LONG 12527 }; 12528 long[] longOut = new long[1]; 12529 Process.readProcFile("/sys/kernel/mm/ksm/pages_shared", 12530 SINGLE_LONG_FORMAT, null, longOut, null); 12531 long shared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 12532 longOut[0] = 0; 12533 Process.readProcFile("/sys/kernel/mm/ksm/pages_sharing", 12534 SINGLE_LONG_FORMAT, null, longOut, null); 12535 long sharing = longOut[0] * ProcessList.PAGE_SIZE / 1024; 12536 longOut[0] = 0; 12537 Process.readProcFile("/sys/kernel/mm/ksm/pages_unshared", 12538 SINGLE_LONG_FORMAT, null, longOut, null); 12539 long unshared = longOut[0] * ProcessList.PAGE_SIZE / 1024; 12540 longOut[0] = 0; 12541 Process.readProcFile("/sys/kernel/mm/ksm/pages_volatile", 12542 SINGLE_LONG_FORMAT, null, longOut, null); 12543 long voltile = longOut[0] * ProcessList.PAGE_SIZE / 1024; 12544 if (!isCompact) { 12545 if (sharing != 0 || shared != 0 || unshared != 0 || voltile != 0) { 12546 pw.print(" KSM: "); pw.print(sharing); 12547 pw.print(" kB saved from shared "); 12548 pw.print(shared); pw.println(" kB"); 12549 pw.print(" "); pw.print(unshared); pw.print(" kB unshared; "); 12550 pw.print(voltile); pw.println(" kB volatile"); 12551 } 12552 pw.print(" Tuning: "); 12553 pw.print(ActivityManager.staticGetMemoryClass()); 12554 pw.print(" (large "); 12555 pw.print(ActivityManager.staticGetLargeMemoryClass()); 12556 pw.print("), oom "); 12557 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 12558 pw.print(" kB"); 12559 pw.print(", restore limit "); 12560 pw.print(mProcessList.getCachedRestoreThresholdKb()); 12561 pw.print(" kB"); 12562 if (ActivityManager.isLowRamDeviceStatic()) { 12563 pw.print(" (low-ram)"); 12564 } 12565 if (ActivityManager.isHighEndGfx()) { 12566 pw.print(" (high-end-gfx)"); 12567 } 12568 pw.println(); 12569 } else { 12570 pw.print("ksm,"); pw.print(sharing); pw.print(","); 12571 pw.print(shared); pw.print(","); pw.print(unshared); pw.print(","); 12572 pw.println(voltile); 12573 pw.print("tuning,"); 12574 pw.print(ActivityManager.staticGetMemoryClass()); 12575 pw.print(','); 12576 pw.print(ActivityManager.staticGetLargeMemoryClass()); 12577 pw.print(','); 12578 pw.print(mProcessList.getMemLevel(ProcessList.CACHED_APP_MAX_ADJ)/1024); 12579 if (ActivityManager.isLowRamDeviceStatic()) { 12580 pw.print(",low-ram"); 12581 } 12582 if (ActivityManager.isHighEndGfx()) { 12583 pw.print(",high-end-gfx"); 12584 } 12585 pw.println(); 12586 } 12587 } 12588 } 12589 } 12590 12591 /** 12592 * Searches array of arguments for the specified string 12593 * @param args array of argument strings 12594 * @param value value to search for 12595 * @return true if the value is contained in the array 12596 */ 12597 private static boolean scanArgs(String[] args, String value) { 12598 if (args != null) { 12599 for (String arg : args) { 12600 if (value.equals(arg)) { 12601 return true; 12602 } 12603 } 12604 } 12605 return false; 12606 } 12607 12608 private final boolean removeDyingProviderLocked(ProcessRecord proc, 12609 ContentProviderRecord cpr, boolean always) { 12610 final boolean inLaunching = mLaunchingProviders.contains(cpr); 12611 12612 if (!inLaunching || always) { 12613 synchronized (cpr) { 12614 cpr.launchingApp = null; 12615 cpr.notifyAll(); 12616 } 12617 mProviderMap.removeProviderByClass(cpr.name, UserHandle.getUserId(cpr.uid)); 12618 String names[] = cpr.info.authority.split(";"); 12619 for (int j = 0; j < names.length; j++) { 12620 mProviderMap.removeProviderByName(names[j], UserHandle.getUserId(cpr.uid)); 12621 } 12622 } 12623 12624 for (int i=0; i<cpr.connections.size(); i++) { 12625 ContentProviderConnection conn = cpr.connections.get(i); 12626 if (conn.waiting) { 12627 // If this connection is waiting for the provider, then we don't 12628 // need to mess with its process unless we are always removing 12629 // or for some reason the provider is not currently launching. 12630 if (inLaunching && !always) { 12631 continue; 12632 } 12633 } 12634 ProcessRecord capp = conn.client; 12635 conn.dead = true; 12636 if (conn.stableCount > 0) { 12637 if (!capp.persistent && capp.thread != null 12638 && capp.pid != 0 12639 && capp.pid != MY_PID) { 12640 killUnneededProcessLocked(capp, "depends on provider " 12641 + cpr.name.flattenToShortString() 12642 + " in dying proc " + (proc != null ? proc.processName : "??")); 12643 } 12644 } else if (capp.thread != null && conn.provider.provider != null) { 12645 try { 12646 capp.thread.unstableProviderDied(conn.provider.provider.asBinder()); 12647 } catch (RemoteException e) { 12648 } 12649 // In the protocol here, we don't expect the client to correctly 12650 // clean up this connection, we'll just remove it. 12651 cpr.connections.remove(i); 12652 conn.client.conProviders.remove(conn); 12653 } 12654 } 12655 12656 if (inLaunching && always) { 12657 mLaunchingProviders.remove(cpr); 12658 } 12659 return inLaunching; 12660 } 12661 12662 /** 12663 * Main code for cleaning up a process when it has gone away. This is 12664 * called both as a result of the process dying, or directly when stopping 12665 * a process when running in single process mode. 12666 */ 12667 private final void cleanUpApplicationRecordLocked(ProcessRecord app, 12668 boolean restarting, boolean allowRestart, int index) { 12669 if (index >= 0) { 12670 removeLruProcessLocked(app); 12671 ProcessList.remove(app.pid); 12672 } 12673 12674 mProcessesToGc.remove(app); 12675 mPendingPssProcesses.remove(app); 12676 12677 // Dismiss any open dialogs. 12678 if (app.crashDialog != null && !app.forceCrashReport) { 12679 app.crashDialog.dismiss(); 12680 app.crashDialog = null; 12681 } 12682 if (app.anrDialog != null) { 12683 app.anrDialog.dismiss(); 12684 app.anrDialog = null; 12685 } 12686 if (app.waitDialog != null) { 12687 app.waitDialog.dismiss(); 12688 app.waitDialog = null; 12689 } 12690 12691 app.crashing = false; 12692 app.notResponding = false; 12693 12694 app.resetPackageList(mProcessStats); 12695 app.unlinkDeathRecipient(); 12696 app.makeInactive(mProcessStats); 12697 app.forcingToForeground = null; 12698 updateProcessForegroundLocked(app, false, false); 12699 app.foregroundActivities = false; 12700 app.hasShownUi = false; 12701 app.treatLikeActivity = false; 12702 app.hasAboveClient = false; 12703 app.hasClientActivities = false; 12704 12705 mServices.killServicesLocked(app, allowRestart); 12706 12707 boolean restart = false; 12708 12709 // Remove published content providers. 12710 for (int i=app.pubProviders.size()-1; i>=0; i--) { 12711 ContentProviderRecord cpr = app.pubProviders.valueAt(i); 12712 final boolean always = app.bad || !allowRestart; 12713 if (removeDyingProviderLocked(app, cpr, always) || always) { 12714 // We left the provider in the launching list, need to 12715 // restart it. 12716 restart = true; 12717 } 12718 12719 cpr.provider = null; 12720 cpr.proc = null; 12721 } 12722 app.pubProviders.clear(); 12723 12724 // Take care of any launching providers waiting for this process. 12725 if (checkAppInLaunchingProvidersLocked(app, false)) { 12726 restart = true; 12727 } 12728 12729 // Unregister from connected content providers. 12730 if (!app.conProviders.isEmpty()) { 12731 for (int i=0; i<app.conProviders.size(); i++) { 12732 ContentProviderConnection conn = app.conProviders.get(i); 12733 conn.provider.connections.remove(conn); 12734 } 12735 app.conProviders.clear(); 12736 } 12737 12738 // At this point there may be remaining entries in mLaunchingProviders 12739 // where we were the only one waiting, so they are no longer of use. 12740 // Look for these and clean up if found. 12741 // XXX Commented out for now. Trying to figure out a way to reproduce 12742 // the actual situation to identify what is actually going on. 12743 if (false) { 12744 for (int i=0; i<mLaunchingProviders.size(); i++) { 12745 ContentProviderRecord cpr = (ContentProviderRecord) 12746 mLaunchingProviders.get(i); 12747 if (cpr.connections.size() <= 0 && !cpr.hasExternalProcessHandles()) { 12748 synchronized (cpr) { 12749 cpr.launchingApp = null; 12750 cpr.notifyAll(); 12751 } 12752 } 12753 } 12754 } 12755 12756 skipCurrentReceiverLocked(app); 12757 12758 // Unregister any receivers. 12759 for (int i=app.receivers.size()-1; i>=0; i--) { 12760 removeReceiverLocked(app.receivers.valueAt(i)); 12761 } 12762 app.receivers.clear(); 12763 12764 // If the app is undergoing backup, tell the backup manager about it 12765 if (mBackupTarget != null && app.pid == mBackupTarget.app.pid) { 12766 if (DEBUG_BACKUP || DEBUG_CLEANUP) Slog.d(TAG, "App " 12767 + mBackupTarget.appInfo + " died during backup"); 12768 try { 12769 IBackupManager bm = IBackupManager.Stub.asInterface( 12770 ServiceManager.getService(Context.BACKUP_SERVICE)); 12771 bm.agentDisconnected(app.info.packageName); 12772 } catch (RemoteException e) { 12773 // can't happen; backup manager is local 12774 } 12775 } 12776 12777 for (int i = mPendingProcessChanges.size()-1; i>=0; i--) { 12778 ProcessChangeItem item = mPendingProcessChanges.get(i); 12779 if (item.pid == app.pid) { 12780 mPendingProcessChanges.remove(i); 12781 mAvailProcessChanges.add(item); 12782 } 12783 } 12784 mHandler.obtainMessage(DISPATCH_PROCESS_DIED, app.pid, app.info.uid, null).sendToTarget(); 12785 12786 // If the caller is restarting this app, then leave it in its 12787 // current lists and let the caller take care of it. 12788 if (restarting) { 12789 return; 12790 } 12791 12792 if (!app.persistent || app.isolated) { 12793 if (DEBUG_PROCESSES || DEBUG_CLEANUP) Slog.v(TAG, 12794 "Removing non-persistent process during cleanup: " + app); 12795 mProcessNames.remove(app.processName, app.uid); 12796 mIsolatedProcesses.remove(app.uid); 12797 if (mHeavyWeightProcess == app) { 12798 mHandler.sendMessage(mHandler.obtainMessage(CANCEL_HEAVY_NOTIFICATION_MSG, 12799 mHeavyWeightProcess.userId, 0)); 12800 mHeavyWeightProcess = null; 12801 } 12802 } else if (!app.removed) { 12803 // This app is persistent, so we need to keep its record around. 12804 // If it is not already on the pending app list, add it there 12805 // and start a new process for it. 12806 if (mPersistentStartingProcesses.indexOf(app) < 0) { 12807 mPersistentStartingProcesses.add(app); 12808 restart = true; 12809 } 12810 } 12811 if ((DEBUG_PROCESSES || DEBUG_CLEANUP) && mProcessesOnHold.contains(app)) Slog.v(TAG, 12812 "Clean-up removing on hold: " + app); 12813 mProcessesOnHold.remove(app); 12814 12815 if (app == mHomeProcess) { 12816 mHomeProcess = null; 12817 } 12818 if (app == mPreviousProcess) { 12819 mPreviousProcess = null; 12820 } 12821 12822 if (restart && !app.isolated) { 12823 // We have components that still need to be running in the 12824 // process, so re-launch it. 12825 mProcessNames.put(app.processName, app.uid, app); 12826 startProcessLocked(app, "restart", app.processName); 12827 } else if (app.pid > 0 && app.pid != MY_PID) { 12828 // Goodbye! 12829 boolean removed; 12830 synchronized (mPidsSelfLocked) { 12831 mPidsSelfLocked.remove(app.pid); 12832 mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app); 12833 } 12834 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_PROC_FINISH, 12835 app.processName, app.info.uid); 12836 if (app.isolated) { 12837 mBatteryStatsService.removeIsolatedUid(app.uid, app.info.uid); 12838 } 12839 app.setPid(0); 12840 } 12841 } 12842 12843 boolean checkAppInLaunchingProvidersLocked(ProcessRecord app, boolean alwaysBad) { 12844 // Look through the content providers we are waiting to have launched, 12845 // and if any run in this process then either schedule a restart of 12846 // the process or kill the client waiting for it if this process has 12847 // gone bad. 12848 int NL = mLaunchingProviders.size(); 12849 boolean restart = false; 12850 for (int i=0; i<NL; i++) { 12851 ContentProviderRecord cpr = mLaunchingProviders.get(i); 12852 if (cpr.launchingApp == app) { 12853 if (!alwaysBad && !app.bad) { 12854 restart = true; 12855 } else { 12856 removeDyingProviderLocked(app, cpr, true); 12857 // cpr should have been removed from mLaunchingProviders 12858 NL = mLaunchingProviders.size(); 12859 i--; 12860 } 12861 } 12862 } 12863 return restart; 12864 } 12865 12866 // ========================================================= 12867 // SERVICES 12868 // ========================================================= 12869 12870 public List<ActivityManager.RunningServiceInfo> getServices(int maxNum, 12871 int flags) { 12872 enforceNotIsolatedCaller("getServices"); 12873 synchronized (this) { 12874 return mServices.getRunningServiceInfoLocked(maxNum, flags); 12875 } 12876 } 12877 12878 public PendingIntent getRunningServiceControlPanel(ComponentName name) { 12879 enforceNotIsolatedCaller("getRunningServiceControlPanel"); 12880 synchronized (this) { 12881 return mServices.getRunningServiceControlPanelLocked(name); 12882 } 12883 } 12884 12885 public ComponentName startService(IApplicationThread caller, Intent service, 12886 String resolvedType, int userId) { 12887 enforceNotIsolatedCaller("startService"); 12888 // Refuse possible leaked file descriptors 12889 if (service != null && service.hasFileDescriptors() == true) { 12890 throw new IllegalArgumentException("File descriptors passed in Intent"); 12891 } 12892 12893 if (DEBUG_SERVICE) 12894 Slog.v(TAG, "startService: " + service + " type=" + resolvedType); 12895 synchronized(this) { 12896 final int callingPid = Binder.getCallingPid(); 12897 final int callingUid = Binder.getCallingUid(); 12898 final long origId = Binder.clearCallingIdentity(); 12899 ComponentName res = mServices.startServiceLocked(caller, service, 12900 resolvedType, callingPid, callingUid, userId); 12901 Binder.restoreCallingIdentity(origId); 12902 return res; 12903 } 12904 } 12905 12906 ComponentName startServiceInPackage(int uid, 12907 Intent service, String resolvedType, int userId) { 12908 synchronized(this) { 12909 if (DEBUG_SERVICE) 12910 Slog.v(TAG, "startServiceInPackage: " + service + " type=" + resolvedType); 12911 final long origId = Binder.clearCallingIdentity(); 12912 ComponentName res = mServices.startServiceLocked(null, service, 12913 resolvedType, -1, uid, userId); 12914 Binder.restoreCallingIdentity(origId); 12915 return res; 12916 } 12917 } 12918 12919 public int stopService(IApplicationThread caller, Intent service, 12920 String resolvedType, int userId) { 12921 enforceNotIsolatedCaller("stopService"); 12922 // Refuse possible leaked file descriptors 12923 if (service != null && service.hasFileDescriptors() == true) { 12924 throw new IllegalArgumentException("File descriptors passed in Intent"); 12925 } 12926 12927 synchronized(this) { 12928 return mServices.stopServiceLocked(caller, service, resolvedType, userId); 12929 } 12930 } 12931 12932 public IBinder peekService(Intent service, String resolvedType) { 12933 enforceNotIsolatedCaller("peekService"); 12934 // Refuse possible leaked file descriptors 12935 if (service != null && service.hasFileDescriptors() == true) { 12936 throw new IllegalArgumentException("File descriptors passed in Intent"); 12937 } 12938 synchronized(this) { 12939 return mServices.peekServiceLocked(service, resolvedType); 12940 } 12941 } 12942 12943 public boolean stopServiceToken(ComponentName className, IBinder token, 12944 int startId) { 12945 synchronized(this) { 12946 return mServices.stopServiceTokenLocked(className, token, startId); 12947 } 12948 } 12949 12950 public void setServiceForeground(ComponentName className, IBinder token, 12951 int id, Notification notification, boolean removeNotification) { 12952 synchronized(this) { 12953 mServices.setServiceForegroundLocked(className, token, id, notification, 12954 removeNotification); 12955 } 12956 } 12957 12958 public int handleIncomingUser(int callingPid, int callingUid, int userId, boolean allowAll, 12959 boolean requireFull, String name, String callerPackage) { 12960 final int callingUserId = UserHandle.getUserId(callingUid); 12961 if (callingUserId != userId) { 12962 if (callingUid != 0 && callingUid != Process.SYSTEM_UID) { 12963 if ((requireFull || checkComponentPermission( 12964 android.Manifest.permission.INTERACT_ACROSS_USERS, 12965 callingPid, callingUid, -1, true) != PackageManager.PERMISSION_GRANTED) 12966 && checkComponentPermission( 12967 android.Manifest.permission.INTERACT_ACROSS_USERS_FULL, 12968 callingPid, callingUid, -1, true) 12969 != PackageManager.PERMISSION_GRANTED) { 12970 if (userId == UserHandle.USER_CURRENT_OR_SELF) { 12971 // In this case, they would like to just execute as their 12972 // owner user instead of failing. 12973 userId = callingUserId; 12974 } else { 12975 StringBuilder builder = new StringBuilder(128); 12976 builder.append("Permission Denial: "); 12977 builder.append(name); 12978 if (callerPackage != null) { 12979 builder.append(" from "); 12980 builder.append(callerPackage); 12981 } 12982 builder.append(" asks to run as user "); 12983 builder.append(userId); 12984 builder.append(" but is calling from user "); 12985 builder.append(UserHandle.getUserId(callingUid)); 12986 builder.append("; this requires "); 12987 builder.append(android.Manifest.permission.INTERACT_ACROSS_USERS_FULL); 12988 if (!requireFull) { 12989 builder.append(" or "); 12990 builder.append(android.Manifest.permission.INTERACT_ACROSS_USERS); 12991 } 12992 String msg = builder.toString(); 12993 Slog.w(TAG, msg); 12994 throw new SecurityException(msg); 12995 } 12996 } 12997 } 12998 if (userId == UserHandle.USER_CURRENT 12999 || userId == UserHandle.USER_CURRENT_OR_SELF) { 13000 // Note that we may be accessing this outside of a lock... 13001 // shouldn't be a big deal, if this is being called outside 13002 // of a locked context there is intrinsically a race with 13003 // the value the caller will receive and someone else changing it. 13004 userId = mCurrentUserId; 13005 } 13006 if (!allowAll && userId < 0) { 13007 throw new IllegalArgumentException( 13008 "Call does not support special user #" + userId); 13009 } 13010 } 13011 return userId; 13012 } 13013 13014 boolean isSingleton(String componentProcessName, ApplicationInfo aInfo, 13015 String className, int flags) { 13016 boolean result = false; 13017 if (UserHandle.getAppId(aInfo.uid) >= Process.FIRST_APPLICATION_UID) { 13018 if ((flags&ServiceInfo.FLAG_SINGLE_USER) != 0) { 13019 if (ActivityManager.checkUidPermission( 13020 android.Manifest.permission.INTERACT_ACROSS_USERS, 13021 aInfo.uid) != PackageManager.PERMISSION_GRANTED) { 13022 ComponentName comp = new ComponentName(aInfo.packageName, className); 13023 String msg = "Permission Denial: Component " + comp.flattenToShortString() 13024 + " requests FLAG_SINGLE_USER, but app does not hold " 13025 + android.Manifest.permission.INTERACT_ACROSS_USERS; 13026 Slog.w(TAG, msg); 13027 throw new SecurityException(msg); 13028 } 13029 result = true; 13030 } 13031 } else if (componentProcessName == aInfo.packageName) { 13032 result = (aInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0; 13033 } else if ("system".equals(componentProcessName)) { 13034 result = true; 13035 } 13036 if (DEBUG_MU) { 13037 Slog.v(TAG, "isSingleton(" + componentProcessName + ", " + aInfo 13038 + ", " + className + ", 0x" + Integer.toHexString(flags) + ") = " + result); 13039 } 13040 return result; 13041 } 13042 13043 public int bindService(IApplicationThread caller, IBinder token, 13044 Intent service, String resolvedType, 13045 IServiceConnection connection, int flags, int userId) { 13046 enforceNotIsolatedCaller("bindService"); 13047 // Refuse possible leaked file descriptors 13048 if (service != null && service.hasFileDescriptors() == true) { 13049 throw new IllegalArgumentException("File descriptors passed in Intent"); 13050 } 13051 13052 synchronized(this) { 13053 return mServices.bindServiceLocked(caller, token, service, resolvedType, 13054 connection, flags, userId); 13055 } 13056 } 13057 13058 public boolean unbindService(IServiceConnection connection) { 13059 synchronized (this) { 13060 return mServices.unbindServiceLocked(connection); 13061 } 13062 } 13063 13064 public void publishService(IBinder token, Intent intent, IBinder service) { 13065 // Refuse possible leaked file descriptors 13066 if (intent != null && intent.hasFileDescriptors() == true) { 13067 throw new IllegalArgumentException("File descriptors passed in Intent"); 13068 } 13069 13070 synchronized(this) { 13071 if (!(token instanceof ServiceRecord)) { 13072 throw new IllegalArgumentException("Invalid service token"); 13073 } 13074 mServices.publishServiceLocked((ServiceRecord)token, intent, service); 13075 } 13076 } 13077 13078 public void unbindFinished(IBinder token, Intent intent, boolean doRebind) { 13079 // Refuse possible leaked file descriptors 13080 if (intent != null && intent.hasFileDescriptors() == true) { 13081 throw new IllegalArgumentException("File descriptors passed in Intent"); 13082 } 13083 13084 synchronized(this) { 13085 mServices.unbindFinishedLocked((ServiceRecord)token, intent, doRebind); 13086 } 13087 } 13088 13089 public void serviceDoneExecuting(IBinder token, int type, int startId, int res) { 13090 synchronized(this) { 13091 if (!(token instanceof ServiceRecord)) { 13092 throw new IllegalArgumentException("Invalid service token"); 13093 } 13094 mServices.serviceDoneExecutingLocked((ServiceRecord)token, type, startId, res); 13095 } 13096 } 13097 13098 // ========================================================= 13099 // BACKUP AND RESTORE 13100 // ========================================================= 13101 13102 // Cause the target app to be launched if necessary and its backup agent 13103 // instantiated. The backup agent will invoke backupAgentCreated() on the 13104 // activity manager to announce its creation. 13105 public boolean bindBackupAgent(ApplicationInfo app, int backupMode) { 13106 if (DEBUG_BACKUP) Slog.v(TAG, "bindBackupAgent: app=" + app + " mode=" + backupMode); 13107 enforceCallingPermission("android.permission.BACKUP", "bindBackupAgent"); 13108 13109 synchronized(this) { 13110 // !!! TODO: currently no check here that we're already bound 13111 BatteryStatsImpl.Uid.Pkg.Serv ss = null; 13112 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 13113 synchronized (stats) { 13114 ss = stats.getServiceStatsLocked(app.uid, app.packageName, app.name); 13115 } 13116 13117 // Backup agent is now in use, its package can't be stopped. 13118 try { 13119 AppGlobals.getPackageManager().setPackageStoppedState( 13120 app.packageName, false, UserHandle.getUserId(app.uid)); 13121 } catch (RemoteException e) { 13122 } catch (IllegalArgumentException e) { 13123 Slog.w(TAG, "Failed trying to unstop package " 13124 + app.packageName + ": " + e); 13125 } 13126 13127 BackupRecord r = new BackupRecord(ss, app, backupMode); 13128 ComponentName hostingName = (backupMode == IApplicationThread.BACKUP_MODE_INCREMENTAL) 13129 ? new ComponentName(app.packageName, app.backupAgentName) 13130 : new ComponentName("android", "FullBackupAgent"); 13131 // startProcessLocked() returns existing proc's record if it's already running 13132 ProcessRecord proc = startProcessLocked(app.processName, app, 13133 false, 0, "backup", hostingName, false, false, false); 13134 if (proc == null) { 13135 Slog.e(TAG, "Unable to start backup agent process " + r); 13136 return false; 13137 } 13138 13139 r.app = proc; 13140 mBackupTarget = r; 13141 mBackupAppName = app.packageName; 13142 13143 // Try not to kill the process during backup 13144 updateOomAdjLocked(proc); 13145 13146 // If the process is already attached, schedule the creation of the backup agent now. 13147 // If it is not yet live, this will be done when it attaches to the framework. 13148 if (proc.thread != null) { 13149 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc already running: " + proc); 13150 try { 13151 proc.thread.scheduleCreateBackupAgent(app, 13152 compatibilityInfoForPackageLocked(app), backupMode); 13153 } catch (RemoteException e) { 13154 // Will time out on the backup manager side 13155 } 13156 } else { 13157 if (DEBUG_BACKUP) Slog.v(TAG, "Agent proc not running, waiting for attach"); 13158 } 13159 // Invariants: at this point, the target app process exists and the application 13160 // is either already running or in the process of coming up. mBackupTarget and 13161 // mBackupAppName describe the app, so that when it binds back to the AM we 13162 // know that it's scheduled for a backup-agent operation. 13163 } 13164 13165 return true; 13166 } 13167 13168 @Override 13169 public void clearPendingBackup() { 13170 if (DEBUG_BACKUP) Slog.v(TAG, "clearPendingBackup"); 13171 enforceCallingPermission("android.permission.BACKUP", "clearPendingBackup"); 13172 13173 synchronized (this) { 13174 mBackupTarget = null; 13175 mBackupAppName = null; 13176 } 13177 } 13178 13179 // A backup agent has just come up 13180 public void backupAgentCreated(String agentPackageName, IBinder agent) { 13181 if (DEBUG_BACKUP) Slog.v(TAG, "backupAgentCreated: " + agentPackageName 13182 + " = " + agent); 13183 13184 synchronized(this) { 13185 if (!agentPackageName.equals(mBackupAppName)) { 13186 Slog.e(TAG, "Backup agent created for " + agentPackageName + " but not requested!"); 13187 return; 13188 } 13189 } 13190 13191 long oldIdent = Binder.clearCallingIdentity(); 13192 try { 13193 IBackupManager bm = IBackupManager.Stub.asInterface( 13194 ServiceManager.getService(Context.BACKUP_SERVICE)); 13195 bm.agentConnected(agentPackageName, agent); 13196 } catch (RemoteException e) { 13197 // can't happen; the backup manager service is local 13198 } catch (Exception e) { 13199 Slog.w(TAG, "Exception trying to deliver BackupAgent binding: "); 13200 e.printStackTrace(); 13201 } finally { 13202 Binder.restoreCallingIdentity(oldIdent); 13203 } 13204 } 13205 13206 // done with this agent 13207 public void unbindBackupAgent(ApplicationInfo appInfo) { 13208 if (DEBUG_BACKUP) Slog.v(TAG, "unbindBackupAgent: " + appInfo); 13209 if (appInfo == null) { 13210 Slog.w(TAG, "unbind backup agent for null app"); 13211 return; 13212 } 13213 13214 synchronized(this) { 13215 try { 13216 if (mBackupAppName == null) { 13217 Slog.w(TAG, "Unbinding backup agent with no active backup"); 13218 return; 13219 } 13220 13221 if (!mBackupAppName.equals(appInfo.packageName)) { 13222 Slog.e(TAG, "Unbind of " + appInfo + " but is not the current backup target"); 13223 return; 13224 } 13225 13226 // Not backing this app up any more; reset its OOM adjustment 13227 final ProcessRecord proc = mBackupTarget.app; 13228 updateOomAdjLocked(proc); 13229 13230 // If the app crashed during backup, 'thread' will be null here 13231 if (proc.thread != null) { 13232 try { 13233 proc.thread.scheduleDestroyBackupAgent(appInfo, 13234 compatibilityInfoForPackageLocked(appInfo)); 13235 } catch (Exception e) { 13236 Slog.e(TAG, "Exception when unbinding backup agent:"); 13237 e.printStackTrace(); 13238 } 13239 } 13240 } finally { 13241 mBackupTarget = null; 13242 mBackupAppName = null; 13243 } 13244 } 13245 } 13246 // ========================================================= 13247 // BROADCASTS 13248 // ========================================================= 13249 13250 private final List getStickiesLocked(String action, IntentFilter filter, 13251 List cur, int userId) { 13252 final ContentResolver resolver = mContext.getContentResolver(); 13253 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 13254 if (stickies == null) { 13255 return cur; 13256 } 13257 final ArrayList<Intent> list = stickies.get(action); 13258 if (list == null) { 13259 return cur; 13260 } 13261 int N = list.size(); 13262 for (int i=0; i<N; i++) { 13263 Intent intent = list.get(i); 13264 if (filter.match(resolver, intent, true, TAG) >= 0) { 13265 if (cur == null) { 13266 cur = new ArrayList<Intent>(); 13267 } 13268 cur.add(intent); 13269 } 13270 } 13271 return cur; 13272 } 13273 13274 boolean isPendingBroadcastProcessLocked(int pid) { 13275 return mFgBroadcastQueue.isPendingBroadcastProcessLocked(pid) 13276 || mBgBroadcastQueue.isPendingBroadcastProcessLocked(pid); 13277 } 13278 13279 void skipPendingBroadcastLocked(int pid) { 13280 Slog.w(TAG, "Unattached app died before broadcast acknowledged, skipping"); 13281 for (BroadcastQueue queue : mBroadcastQueues) { 13282 queue.skipPendingBroadcastLocked(pid); 13283 } 13284 } 13285 13286 // The app just attached; send any pending broadcasts that it should receive 13287 boolean sendPendingBroadcastsLocked(ProcessRecord app) { 13288 boolean didSomething = false; 13289 for (BroadcastQueue queue : mBroadcastQueues) { 13290 didSomething |= queue.sendPendingBroadcastsLocked(app); 13291 } 13292 return didSomething; 13293 } 13294 13295 public Intent registerReceiver(IApplicationThread caller, String callerPackage, 13296 IIntentReceiver receiver, IntentFilter filter, String permission, int userId) { 13297 enforceNotIsolatedCaller("registerReceiver"); 13298 int callingUid; 13299 int callingPid; 13300 synchronized(this) { 13301 ProcessRecord callerApp = null; 13302 if (caller != null) { 13303 callerApp = getRecordForAppLocked(caller); 13304 if (callerApp == null) { 13305 throw new SecurityException( 13306 "Unable to find app for caller " + caller 13307 + " (pid=" + Binder.getCallingPid() 13308 + ") when registering receiver " + receiver); 13309 } 13310 if (callerApp.info.uid != Process.SYSTEM_UID && 13311 !callerApp.pkgList.containsKey(callerPackage) && 13312 !"android".equals(callerPackage)) { 13313 throw new SecurityException("Given caller package " + callerPackage 13314 + " is not running in process " + callerApp); 13315 } 13316 callingUid = callerApp.info.uid; 13317 callingPid = callerApp.pid; 13318 } else { 13319 callerPackage = null; 13320 callingUid = Binder.getCallingUid(); 13321 callingPid = Binder.getCallingPid(); 13322 } 13323 13324 userId = this.handleIncomingUser(callingPid, callingUid, userId, 13325 true, true, "registerReceiver", callerPackage); 13326 13327 List allSticky = null; 13328 13329 // Look for any matching sticky broadcasts... 13330 Iterator actions = filter.actionsIterator(); 13331 if (actions != null) { 13332 while (actions.hasNext()) { 13333 String action = (String)actions.next(); 13334 allSticky = getStickiesLocked(action, filter, allSticky, 13335 UserHandle.USER_ALL); 13336 allSticky = getStickiesLocked(action, filter, allSticky, 13337 UserHandle.getUserId(callingUid)); 13338 } 13339 } else { 13340 allSticky = getStickiesLocked(null, filter, allSticky, 13341 UserHandle.USER_ALL); 13342 allSticky = getStickiesLocked(null, filter, allSticky, 13343 UserHandle.getUserId(callingUid)); 13344 } 13345 13346 // The first sticky in the list is returned directly back to 13347 // the client. 13348 Intent sticky = allSticky != null ? (Intent)allSticky.get(0) : null; 13349 13350 if (DEBUG_BROADCAST) Slog.v(TAG, "Register receiver " + filter 13351 + ": " + sticky); 13352 13353 if (receiver == null) { 13354 return sticky; 13355 } 13356 13357 ReceiverList rl 13358 = (ReceiverList)mRegisteredReceivers.get(receiver.asBinder()); 13359 if (rl == null) { 13360 rl = new ReceiverList(this, callerApp, callingPid, callingUid, 13361 userId, receiver); 13362 if (rl.app != null) { 13363 rl.app.receivers.add(rl); 13364 } else { 13365 try { 13366 receiver.asBinder().linkToDeath(rl, 0); 13367 } catch (RemoteException e) { 13368 return sticky; 13369 } 13370 rl.linkedToDeath = true; 13371 } 13372 mRegisteredReceivers.put(receiver.asBinder(), rl); 13373 } else if (rl.uid != callingUid) { 13374 throw new IllegalArgumentException( 13375 "Receiver requested to register for uid " + callingUid 13376 + " was previously registered for uid " + rl.uid); 13377 } else if (rl.pid != callingPid) { 13378 throw new IllegalArgumentException( 13379 "Receiver requested to register for pid " + callingPid 13380 + " was previously registered for pid " + rl.pid); 13381 } else if (rl.userId != userId) { 13382 throw new IllegalArgumentException( 13383 "Receiver requested to register for user " + userId 13384 + " was previously registered for user " + rl.userId); 13385 } 13386 BroadcastFilter bf = new BroadcastFilter(filter, rl, callerPackage, 13387 permission, callingUid, userId); 13388 rl.add(bf); 13389 if (!bf.debugCheck()) { 13390 Slog.w(TAG, "==> For Dynamic broadast"); 13391 } 13392 mReceiverResolver.addFilter(bf); 13393 13394 // Enqueue broadcasts for all existing stickies that match 13395 // this filter. 13396 if (allSticky != null) { 13397 ArrayList receivers = new ArrayList(); 13398 receivers.add(bf); 13399 13400 int N = allSticky.size(); 13401 for (int i=0; i<N; i++) { 13402 Intent intent = (Intent)allSticky.get(i); 13403 BroadcastQueue queue = broadcastQueueForIntent(intent); 13404 BroadcastRecord r = new BroadcastRecord(queue, intent, null, 13405 null, -1, -1, null, null, AppOpsManager.OP_NONE, receivers, null, 0, 13406 null, null, false, true, true, -1); 13407 queue.enqueueParallelBroadcastLocked(r); 13408 queue.scheduleBroadcastsLocked(); 13409 } 13410 } 13411 13412 return sticky; 13413 } 13414 } 13415 13416 public void unregisterReceiver(IIntentReceiver receiver) { 13417 if (DEBUG_BROADCAST) Slog.v(TAG, "Unregister receiver: " + receiver); 13418 13419 final long origId = Binder.clearCallingIdentity(); 13420 try { 13421 boolean doTrim = false; 13422 13423 synchronized(this) { 13424 ReceiverList rl = mRegisteredReceivers.get(receiver.asBinder()); 13425 if (rl != null) { 13426 if (rl.curBroadcast != null) { 13427 BroadcastRecord r = rl.curBroadcast; 13428 final boolean doNext = finishReceiverLocked( 13429 receiver.asBinder(), r.resultCode, r.resultData, 13430 r.resultExtras, r.resultAbort); 13431 if (doNext) { 13432 doTrim = true; 13433 r.queue.processNextBroadcast(false); 13434 } 13435 } 13436 13437 if (rl.app != null) { 13438 rl.app.receivers.remove(rl); 13439 } 13440 removeReceiverLocked(rl); 13441 if (rl.linkedToDeath) { 13442 rl.linkedToDeath = false; 13443 rl.receiver.asBinder().unlinkToDeath(rl, 0); 13444 } 13445 } 13446 } 13447 13448 // If we actually concluded any broadcasts, we might now be able 13449 // to trim the recipients' apps from our working set 13450 if (doTrim) { 13451 trimApplications(); 13452 return; 13453 } 13454 13455 } finally { 13456 Binder.restoreCallingIdentity(origId); 13457 } 13458 } 13459 13460 void removeReceiverLocked(ReceiverList rl) { 13461 mRegisteredReceivers.remove(rl.receiver.asBinder()); 13462 int N = rl.size(); 13463 for (int i=0; i<N; i++) { 13464 mReceiverResolver.removeFilter(rl.get(i)); 13465 } 13466 } 13467 13468 private final void sendPackageBroadcastLocked(int cmd, String[] packages, int userId) { 13469 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 13470 ProcessRecord r = mLruProcesses.get(i); 13471 if (r.thread != null && (userId == UserHandle.USER_ALL || r.userId == userId)) { 13472 try { 13473 r.thread.dispatchPackageBroadcast(cmd, packages); 13474 } catch (RemoteException ex) { 13475 } 13476 } 13477 } 13478 } 13479 13480 private List<ResolveInfo> collectReceiverComponents(Intent intent, String resolvedType, 13481 int[] users) { 13482 List<ResolveInfo> receivers = null; 13483 try { 13484 HashSet<ComponentName> singleUserReceivers = null; 13485 boolean scannedFirstReceivers = false; 13486 for (int user : users) { 13487 List<ResolveInfo> newReceivers = AppGlobals.getPackageManager() 13488 .queryIntentReceivers(intent, resolvedType, STOCK_PM_FLAGS, user); 13489 if (user != 0 && newReceivers != null) { 13490 // If this is not the primary user, we need to check for 13491 // any receivers that should be filtered out. 13492 for (int i=0; i<newReceivers.size(); i++) { 13493 ResolveInfo ri = newReceivers.get(i); 13494 if ((ri.activityInfo.flags&ActivityInfo.FLAG_PRIMARY_USER_ONLY) != 0) { 13495 newReceivers.remove(i); 13496 i--; 13497 } 13498 } 13499 } 13500 if (newReceivers != null && newReceivers.size() == 0) { 13501 newReceivers = null; 13502 } 13503 if (receivers == null) { 13504 receivers = newReceivers; 13505 } else if (newReceivers != null) { 13506 // We need to concatenate the additional receivers 13507 // found with what we have do far. This would be easy, 13508 // but we also need to de-dup any receivers that are 13509 // singleUser. 13510 if (!scannedFirstReceivers) { 13511 // Collect any single user receivers we had already retrieved. 13512 scannedFirstReceivers = true; 13513 for (int i=0; i<receivers.size(); i++) { 13514 ResolveInfo ri = receivers.get(i); 13515 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 13516 ComponentName cn = new ComponentName( 13517 ri.activityInfo.packageName, ri.activityInfo.name); 13518 if (singleUserReceivers == null) { 13519 singleUserReceivers = new HashSet<ComponentName>(); 13520 } 13521 singleUserReceivers.add(cn); 13522 } 13523 } 13524 } 13525 // Add the new results to the existing results, tracking 13526 // and de-dupping single user receivers. 13527 for (int i=0; i<newReceivers.size(); i++) { 13528 ResolveInfo ri = newReceivers.get(i); 13529 if ((ri.activityInfo.flags&ActivityInfo.FLAG_SINGLE_USER) != 0) { 13530 ComponentName cn = new ComponentName( 13531 ri.activityInfo.packageName, ri.activityInfo.name); 13532 if (singleUserReceivers == null) { 13533 singleUserReceivers = new HashSet<ComponentName>(); 13534 } 13535 if (!singleUserReceivers.contains(cn)) { 13536 singleUserReceivers.add(cn); 13537 receivers.add(ri); 13538 } 13539 } else { 13540 receivers.add(ri); 13541 } 13542 } 13543 } 13544 } 13545 } catch (RemoteException ex) { 13546 // pm is in same process, this will never happen. 13547 } 13548 return receivers; 13549 } 13550 13551 private final int broadcastIntentLocked(ProcessRecord callerApp, 13552 String callerPackage, Intent intent, String resolvedType, 13553 IIntentReceiver resultTo, int resultCode, String resultData, 13554 Bundle map, String requiredPermission, int appOp, 13555 boolean ordered, boolean sticky, int callingPid, int callingUid, 13556 int userId) { 13557 intent = new Intent(intent); 13558 13559 // By default broadcasts do not go to stopped apps. 13560 intent.addFlags(Intent.FLAG_EXCLUDE_STOPPED_PACKAGES); 13561 13562 if (DEBUG_BROADCAST_LIGHT) Slog.v( 13563 TAG, (sticky ? "Broadcast sticky: ": "Broadcast: ") + intent 13564 + " ordered=" + ordered + " userid=" + userId); 13565 if ((resultTo != null) && !ordered) { 13566 Slog.w(TAG, "Broadcast " + intent + " not ordered but result callback requested!"); 13567 } 13568 13569 userId = handleIncomingUser(callingPid, callingUid, userId, 13570 true, false, "broadcast", callerPackage); 13571 13572 // Make sure that the user who is receiving this broadcast is started. 13573 // If not, we will just skip it. 13574 if (userId != UserHandle.USER_ALL && mStartedUsers.get(userId) == null) { 13575 if (callingUid != Process.SYSTEM_UID || (intent.getFlags() 13576 & Intent.FLAG_RECEIVER_BOOT_UPGRADE) == 0) { 13577 Slog.w(TAG, "Skipping broadcast of " + intent 13578 + ": user " + userId + " is stopped"); 13579 return ActivityManager.BROADCAST_SUCCESS; 13580 } 13581 } 13582 13583 /* 13584 * Prevent non-system code (defined here to be non-persistent 13585 * processes) from sending protected broadcasts. 13586 */ 13587 int callingAppId = UserHandle.getAppId(callingUid); 13588 if (callingAppId == Process.SYSTEM_UID || callingAppId == Process.PHONE_UID 13589 || callingAppId == Process.SHELL_UID || callingAppId == Process.BLUETOOTH_UID || 13590 callingUid == 0) { 13591 // Always okay. 13592 } else if (callerApp == null || !callerApp.persistent) { 13593 try { 13594 if (AppGlobals.getPackageManager().isProtectedBroadcast( 13595 intent.getAction())) { 13596 String msg = "Permission Denial: not allowed to send broadcast " 13597 + intent.getAction() + " from pid=" 13598 + callingPid + ", uid=" + callingUid; 13599 Slog.w(TAG, msg); 13600 throw new SecurityException(msg); 13601 } else if (AppWidgetManager.ACTION_APPWIDGET_CONFIGURE.equals(intent.getAction())) { 13602 // Special case for compatibility: we don't want apps to send this, 13603 // but historically it has not been protected and apps may be using it 13604 // to poke their own app widget. So, instead of making it protected, 13605 // just limit it to the caller. 13606 if (callerApp == null) { 13607 String msg = "Permission Denial: not allowed to send broadcast " 13608 + intent.getAction() + " from unknown caller."; 13609 Slog.w(TAG, msg); 13610 throw new SecurityException(msg); 13611 } else if (intent.getComponent() != null) { 13612 // They are good enough to send to an explicit component... verify 13613 // it is being sent to the calling app. 13614 if (!intent.getComponent().getPackageName().equals( 13615 callerApp.info.packageName)) { 13616 String msg = "Permission Denial: not allowed to send broadcast " 13617 + intent.getAction() + " to " 13618 + intent.getComponent().getPackageName() + " from " 13619 + callerApp.info.packageName; 13620 Slog.w(TAG, msg); 13621 throw new SecurityException(msg); 13622 } 13623 } else { 13624 // Limit broadcast to their own package. 13625 intent.setPackage(callerApp.info.packageName); 13626 } 13627 } 13628 } catch (RemoteException e) { 13629 Slog.w(TAG, "Remote exception", e); 13630 return ActivityManager.BROADCAST_SUCCESS; 13631 } 13632 } 13633 13634 // Handle special intents: if this broadcast is from the package 13635 // manager about a package being removed, we need to remove all of 13636 // its activities from the history stack. 13637 final boolean uidRemoved = Intent.ACTION_UID_REMOVED.equals( 13638 intent.getAction()); 13639 if (Intent.ACTION_PACKAGE_REMOVED.equals(intent.getAction()) 13640 || Intent.ACTION_PACKAGE_CHANGED.equals(intent.getAction()) 13641 || Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction()) 13642 || uidRemoved) { 13643 if (checkComponentPermission( 13644 android.Manifest.permission.BROADCAST_PACKAGE_REMOVED, 13645 callingPid, callingUid, -1, true) 13646 == PackageManager.PERMISSION_GRANTED) { 13647 if (uidRemoved) { 13648 final Bundle intentExtras = intent.getExtras(); 13649 final int uid = intentExtras != null 13650 ? intentExtras.getInt(Intent.EXTRA_UID) : -1; 13651 if (uid >= 0) { 13652 BatteryStatsImpl bs = mBatteryStatsService.getActiveStatistics(); 13653 synchronized (bs) { 13654 bs.removeUidStatsLocked(uid); 13655 } 13656 mAppOpsService.uidRemoved(uid); 13657 } 13658 } else { 13659 // If resources are unavailable just force stop all 13660 // those packages and flush the attribute cache as well. 13661 if (Intent.ACTION_EXTERNAL_APPLICATIONS_UNAVAILABLE.equals(intent.getAction())) { 13662 String list[] = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 13663 if (list != null && (list.length > 0)) { 13664 for (String pkg : list) { 13665 forceStopPackageLocked(pkg, -1, false, true, true, false, false, userId, 13666 "storage unmount"); 13667 } 13668 sendPackageBroadcastLocked( 13669 IApplicationThread.EXTERNAL_STORAGE_UNAVAILABLE, list, userId); 13670 } 13671 } else { 13672 Uri data = intent.getData(); 13673 String ssp; 13674 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 13675 boolean removed = Intent.ACTION_PACKAGE_REMOVED.equals( 13676 intent.getAction()); 13677 boolean fullUninstall = removed && 13678 !intent.getBooleanExtra(Intent.EXTRA_REPLACING, false); 13679 if (!intent.getBooleanExtra(Intent.EXTRA_DONT_KILL_APP, false)) { 13680 forceStopPackageLocked(ssp, UserHandle.getAppId( 13681 intent.getIntExtra(Intent.EXTRA_UID, -1)), false, true, true, 13682 false, fullUninstall, userId, 13683 removed ? "pkg removed" : "pkg changed"); 13684 } 13685 if (removed) { 13686 sendPackageBroadcastLocked(IApplicationThread.PACKAGE_REMOVED, 13687 new String[] {ssp}, userId); 13688 if (!intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)) { 13689 mAppOpsService.packageRemoved( 13690 intent.getIntExtra(Intent.EXTRA_UID, -1), ssp); 13691 13692 // Remove all permissions granted from/to this package 13693 removeUriPermissionsForPackageLocked(ssp, userId, true); 13694 } 13695 } 13696 } 13697 } 13698 } 13699 } else { 13700 String msg = "Permission Denial: " + intent.getAction() 13701 + " broadcast from " + callerPackage + " (pid=" + callingPid 13702 + ", uid=" + callingUid + ")" 13703 + " requires " 13704 + android.Manifest.permission.BROADCAST_PACKAGE_REMOVED; 13705 Slog.w(TAG, msg); 13706 throw new SecurityException(msg); 13707 } 13708 13709 // Special case for adding a package: by default turn on compatibility 13710 // mode. 13711 } else if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction())) { 13712 Uri data = intent.getData(); 13713 String ssp; 13714 if (data != null && (ssp=data.getSchemeSpecificPart()) != null) { 13715 mCompatModePackages.handlePackageAddedLocked(ssp, 13716 intent.getBooleanExtra(Intent.EXTRA_REPLACING, false)); 13717 } 13718 } 13719 13720 /* 13721 * If this is the time zone changed action, queue up a message that will reset the timezone 13722 * of all currently running processes. This message will get queued up before the broadcast 13723 * happens. 13724 */ 13725 if (Intent.ACTION_TIMEZONE_CHANGED.equals(intent.getAction())) { 13726 mHandler.sendEmptyMessage(UPDATE_TIME_ZONE); 13727 } 13728 13729 /* 13730 * If the user set the time, let all running processes know. 13731 */ 13732 if (Intent.ACTION_TIME_CHANGED.equals(intent.getAction())) { 13733 final int is24Hour = intent.getBooleanExtra( 13734 Intent.EXTRA_TIME_PREF_24_HOUR_FORMAT, false) ? 1 : 0; 13735 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_TIME, is24Hour, 0)); 13736 } 13737 13738 if (Intent.ACTION_CLEAR_DNS_CACHE.equals(intent.getAction())) { 13739 mHandler.sendEmptyMessage(CLEAR_DNS_CACHE_MSG); 13740 } 13741 13742 if (Proxy.PROXY_CHANGE_ACTION.equals(intent.getAction())) { 13743 ProxyProperties proxy = intent.getParcelableExtra("proxy"); 13744 mHandler.sendMessage(mHandler.obtainMessage(UPDATE_HTTP_PROXY_MSG, proxy)); 13745 } 13746 13747 // Add to the sticky list if requested. 13748 if (sticky) { 13749 if (checkPermission(android.Manifest.permission.BROADCAST_STICKY, 13750 callingPid, callingUid) 13751 != PackageManager.PERMISSION_GRANTED) { 13752 String msg = "Permission Denial: broadcastIntent() requesting a sticky broadcast from pid=" 13753 + callingPid + ", uid=" + callingUid 13754 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 13755 Slog.w(TAG, msg); 13756 throw new SecurityException(msg); 13757 } 13758 if (requiredPermission != null) { 13759 Slog.w(TAG, "Can't broadcast sticky intent " + intent 13760 + " and enforce permission " + requiredPermission); 13761 return ActivityManager.BROADCAST_STICKY_CANT_HAVE_PERMISSION; 13762 } 13763 if (intent.getComponent() != null) { 13764 throw new SecurityException( 13765 "Sticky broadcasts can't target a specific component"); 13766 } 13767 // We use userId directly here, since the "all" target is maintained 13768 // as a separate set of sticky broadcasts. 13769 if (userId != UserHandle.USER_ALL) { 13770 // But first, if this is not a broadcast to all users, then 13771 // make sure it doesn't conflict with an existing broadcast to 13772 // all users. 13773 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get( 13774 UserHandle.USER_ALL); 13775 if (stickies != null) { 13776 ArrayList<Intent> list = stickies.get(intent.getAction()); 13777 if (list != null) { 13778 int N = list.size(); 13779 int i; 13780 for (i=0; i<N; i++) { 13781 if (intent.filterEquals(list.get(i))) { 13782 throw new IllegalArgumentException( 13783 "Sticky broadcast " + intent + " for user " 13784 + userId + " conflicts with existing global broadcast"); 13785 } 13786 } 13787 } 13788 } 13789 } 13790 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 13791 if (stickies == null) { 13792 stickies = new ArrayMap<String, ArrayList<Intent>>(); 13793 mStickyBroadcasts.put(userId, stickies); 13794 } 13795 ArrayList<Intent> list = stickies.get(intent.getAction()); 13796 if (list == null) { 13797 list = new ArrayList<Intent>(); 13798 stickies.put(intent.getAction(), list); 13799 } 13800 int N = list.size(); 13801 int i; 13802 for (i=0; i<N; i++) { 13803 if (intent.filterEquals(list.get(i))) { 13804 // This sticky already exists, replace it. 13805 list.set(i, new Intent(intent)); 13806 break; 13807 } 13808 } 13809 if (i >= N) { 13810 list.add(new Intent(intent)); 13811 } 13812 } 13813 13814 int[] users; 13815 if (userId == UserHandle.USER_ALL) { 13816 // Caller wants broadcast to go to all started users. 13817 users = mStartedUserArray; 13818 } else { 13819 // Caller wants broadcast to go to one specific user. 13820 users = new int[] {userId}; 13821 } 13822 13823 // Figure out who all will receive this broadcast. 13824 List receivers = null; 13825 List<BroadcastFilter> registeredReceivers = null; 13826 // Need to resolve the intent to interested receivers... 13827 if ((intent.getFlags()&Intent.FLAG_RECEIVER_REGISTERED_ONLY) 13828 == 0) { 13829 receivers = collectReceiverComponents(intent, resolvedType, users); 13830 } 13831 if (intent.getComponent() == null) { 13832 registeredReceivers = mReceiverResolver.queryIntent(intent, 13833 resolvedType, false, userId); 13834 } 13835 13836 final boolean replacePending = 13837 (intent.getFlags()&Intent.FLAG_RECEIVER_REPLACE_PENDING) != 0; 13838 13839 if (DEBUG_BROADCAST) Slog.v(TAG, "Enqueing broadcast: " + intent.getAction() 13840 + " replacePending=" + replacePending); 13841 13842 int NR = registeredReceivers != null ? registeredReceivers.size() : 0; 13843 if (!ordered && NR > 0) { 13844 // If we are not serializing this broadcast, then send the 13845 // registered receivers separately so they don't wait for the 13846 // components to be launched. 13847 final BroadcastQueue queue = broadcastQueueForIntent(intent); 13848 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 13849 callerPackage, callingPid, callingUid, resolvedType, requiredPermission, 13850 appOp, registeredReceivers, resultTo, resultCode, resultData, map, 13851 ordered, sticky, false, userId); 13852 if (DEBUG_BROADCAST) Slog.v( 13853 TAG, "Enqueueing parallel broadcast " + r); 13854 final boolean replaced = replacePending && queue.replaceParallelBroadcastLocked(r); 13855 if (!replaced) { 13856 queue.enqueueParallelBroadcastLocked(r); 13857 queue.scheduleBroadcastsLocked(); 13858 } 13859 registeredReceivers = null; 13860 NR = 0; 13861 } 13862 13863 // Merge into one list. 13864 int ir = 0; 13865 if (receivers != null) { 13866 // A special case for PACKAGE_ADDED: do not allow the package 13867 // being added to see this broadcast. This prevents them from 13868 // using this as a back door to get run as soon as they are 13869 // installed. Maybe in the future we want to have a special install 13870 // broadcast or such for apps, but we'd like to deliberately make 13871 // this decision. 13872 String skipPackages[] = null; 13873 if (Intent.ACTION_PACKAGE_ADDED.equals(intent.getAction()) 13874 || Intent.ACTION_PACKAGE_RESTARTED.equals(intent.getAction()) 13875 || Intent.ACTION_PACKAGE_DATA_CLEARED.equals(intent.getAction())) { 13876 Uri data = intent.getData(); 13877 if (data != null) { 13878 String pkgName = data.getSchemeSpecificPart(); 13879 if (pkgName != null) { 13880 skipPackages = new String[] { pkgName }; 13881 } 13882 } 13883 } else if (Intent.ACTION_EXTERNAL_APPLICATIONS_AVAILABLE.equals(intent.getAction())) { 13884 skipPackages = intent.getStringArrayExtra(Intent.EXTRA_CHANGED_PACKAGE_LIST); 13885 } 13886 if (skipPackages != null && (skipPackages.length > 0)) { 13887 for (String skipPackage : skipPackages) { 13888 if (skipPackage != null) { 13889 int NT = receivers.size(); 13890 for (int it=0; it<NT; it++) { 13891 ResolveInfo curt = (ResolveInfo)receivers.get(it); 13892 if (curt.activityInfo.packageName.equals(skipPackage)) { 13893 receivers.remove(it); 13894 it--; 13895 NT--; 13896 } 13897 } 13898 } 13899 } 13900 } 13901 13902 int NT = receivers != null ? receivers.size() : 0; 13903 int it = 0; 13904 ResolveInfo curt = null; 13905 BroadcastFilter curr = null; 13906 while (it < NT && ir < NR) { 13907 if (curt == null) { 13908 curt = (ResolveInfo)receivers.get(it); 13909 } 13910 if (curr == null) { 13911 curr = registeredReceivers.get(ir); 13912 } 13913 if (curr.getPriority() >= curt.priority) { 13914 // Insert this broadcast record into the final list. 13915 receivers.add(it, curr); 13916 ir++; 13917 curr = null; 13918 it++; 13919 NT++; 13920 } else { 13921 // Skip to the next ResolveInfo in the final list. 13922 it++; 13923 curt = null; 13924 } 13925 } 13926 } 13927 while (ir < NR) { 13928 if (receivers == null) { 13929 receivers = new ArrayList(); 13930 } 13931 receivers.add(registeredReceivers.get(ir)); 13932 ir++; 13933 } 13934 13935 if ((receivers != null && receivers.size() > 0) 13936 || resultTo != null) { 13937 BroadcastQueue queue = broadcastQueueForIntent(intent); 13938 BroadcastRecord r = new BroadcastRecord(queue, intent, callerApp, 13939 callerPackage, callingPid, callingUid, resolvedType, 13940 requiredPermission, appOp, receivers, resultTo, resultCode, 13941 resultData, map, ordered, sticky, false, userId); 13942 if (DEBUG_BROADCAST) Slog.v( 13943 TAG, "Enqueueing ordered broadcast " + r 13944 + ": prev had " + queue.mOrderedBroadcasts.size()); 13945 if (DEBUG_BROADCAST) { 13946 int seq = r.intent.getIntExtra("seq", -1); 13947 Slog.i(TAG, "Enqueueing broadcast " + r.intent.getAction() + " seq=" + seq); 13948 } 13949 boolean replaced = replacePending && queue.replaceOrderedBroadcastLocked(r); 13950 if (!replaced) { 13951 queue.enqueueOrderedBroadcastLocked(r); 13952 queue.scheduleBroadcastsLocked(); 13953 } 13954 } 13955 13956 return ActivityManager.BROADCAST_SUCCESS; 13957 } 13958 13959 final Intent verifyBroadcastLocked(Intent intent) { 13960 // Refuse possible leaked file descriptors 13961 if (intent != null && intent.hasFileDescriptors() == true) { 13962 throw new IllegalArgumentException("File descriptors passed in Intent"); 13963 } 13964 13965 int flags = intent.getFlags(); 13966 13967 if (!mProcessesReady) { 13968 // if the caller really truly claims to know what they're doing, go 13969 // ahead and allow the broadcast without launching any receivers 13970 if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT) != 0) { 13971 intent = new Intent(intent); 13972 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 13973 } else if ((flags&Intent.FLAG_RECEIVER_REGISTERED_ONLY) == 0) { 13974 Slog.e(TAG, "Attempt to launch receivers of broadcast intent " + intent 13975 + " before boot completion"); 13976 throw new IllegalStateException("Cannot broadcast before boot completed"); 13977 } 13978 } 13979 13980 if ((flags&Intent.FLAG_RECEIVER_BOOT_UPGRADE) != 0) { 13981 throw new IllegalArgumentException( 13982 "Can't use FLAG_RECEIVER_BOOT_UPGRADE here"); 13983 } 13984 13985 return intent; 13986 } 13987 13988 public final int broadcastIntent(IApplicationThread caller, 13989 Intent intent, String resolvedType, IIntentReceiver resultTo, 13990 int resultCode, String resultData, Bundle map, 13991 String requiredPermission, int appOp, boolean serialized, boolean sticky, int userId) { 13992 enforceNotIsolatedCaller("broadcastIntent"); 13993 synchronized(this) { 13994 intent = verifyBroadcastLocked(intent); 13995 13996 final ProcessRecord callerApp = getRecordForAppLocked(caller); 13997 final int callingPid = Binder.getCallingPid(); 13998 final int callingUid = Binder.getCallingUid(); 13999 final long origId = Binder.clearCallingIdentity(); 14000 int res = broadcastIntentLocked(callerApp, 14001 callerApp != null ? callerApp.info.packageName : null, 14002 intent, resolvedType, resultTo, 14003 resultCode, resultData, map, requiredPermission, appOp, serialized, sticky, 14004 callingPid, callingUid, userId); 14005 Binder.restoreCallingIdentity(origId); 14006 return res; 14007 } 14008 } 14009 14010 int broadcastIntentInPackage(String packageName, int uid, 14011 Intent intent, String resolvedType, IIntentReceiver resultTo, 14012 int resultCode, String resultData, Bundle map, 14013 String requiredPermission, boolean serialized, boolean sticky, int userId) { 14014 synchronized(this) { 14015 intent = verifyBroadcastLocked(intent); 14016 14017 final long origId = Binder.clearCallingIdentity(); 14018 int res = broadcastIntentLocked(null, packageName, intent, resolvedType, 14019 resultTo, resultCode, resultData, map, requiredPermission, 14020 AppOpsManager.OP_NONE, serialized, sticky, -1, uid, userId); 14021 Binder.restoreCallingIdentity(origId); 14022 return res; 14023 } 14024 } 14025 14026 public final void unbroadcastIntent(IApplicationThread caller, Intent intent, int userId) { 14027 // Refuse possible leaked file descriptors 14028 if (intent != null && intent.hasFileDescriptors() == true) { 14029 throw new IllegalArgumentException("File descriptors passed in Intent"); 14030 } 14031 14032 userId = handleIncomingUser(Binder.getCallingPid(), 14033 Binder.getCallingUid(), userId, true, false, "removeStickyBroadcast", null); 14034 14035 synchronized(this) { 14036 if (checkCallingPermission(android.Manifest.permission.BROADCAST_STICKY) 14037 != PackageManager.PERMISSION_GRANTED) { 14038 String msg = "Permission Denial: unbroadcastIntent() from pid=" 14039 + Binder.getCallingPid() 14040 + ", uid=" + Binder.getCallingUid() 14041 + " requires " + android.Manifest.permission.BROADCAST_STICKY; 14042 Slog.w(TAG, msg); 14043 throw new SecurityException(msg); 14044 } 14045 ArrayMap<String, ArrayList<Intent>> stickies = mStickyBroadcasts.get(userId); 14046 if (stickies != null) { 14047 ArrayList<Intent> list = stickies.get(intent.getAction()); 14048 if (list != null) { 14049 int N = list.size(); 14050 int i; 14051 for (i=0; i<N; i++) { 14052 if (intent.filterEquals(list.get(i))) { 14053 list.remove(i); 14054 break; 14055 } 14056 } 14057 if (list.size() <= 0) { 14058 stickies.remove(intent.getAction()); 14059 } 14060 } 14061 if (stickies.size() <= 0) { 14062 mStickyBroadcasts.remove(userId); 14063 } 14064 } 14065 } 14066 } 14067 14068 private final boolean finishReceiverLocked(IBinder receiver, int resultCode, 14069 String resultData, Bundle resultExtras, boolean resultAbort) { 14070 final BroadcastRecord r = broadcastRecordForReceiverLocked(receiver); 14071 if (r == null) { 14072 Slog.w(TAG, "finishReceiver called but not found on queue"); 14073 return false; 14074 } 14075 14076 return r.queue.finishReceiverLocked(r, resultCode, resultData, resultExtras, resultAbort, false); 14077 } 14078 14079 void backgroundServicesFinishedLocked(int userId) { 14080 for (BroadcastQueue queue : mBroadcastQueues) { 14081 queue.backgroundServicesFinishedLocked(userId); 14082 } 14083 } 14084 14085 public void finishReceiver(IBinder who, int resultCode, String resultData, 14086 Bundle resultExtras, boolean resultAbort) { 14087 if (DEBUG_BROADCAST) Slog.v(TAG, "Finish receiver: " + who); 14088 14089 // Refuse possible leaked file descriptors 14090 if (resultExtras != null && resultExtras.hasFileDescriptors()) { 14091 throw new IllegalArgumentException("File descriptors passed in Bundle"); 14092 } 14093 14094 final long origId = Binder.clearCallingIdentity(); 14095 try { 14096 boolean doNext = false; 14097 BroadcastRecord r; 14098 14099 synchronized(this) { 14100 r = broadcastRecordForReceiverLocked(who); 14101 if (r != null) { 14102 doNext = r.queue.finishReceiverLocked(r, resultCode, 14103 resultData, resultExtras, resultAbort, true); 14104 } 14105 } 14106 14107 if (doNext) { 14108 r.queue.processNextBroadcast(false); 14109 } 14110 trimApplications(); 14111 } finally { 14112 Binder.restoreCallingIdentity(origId); 14113 } 14114 } 14115 14116 // ========================================================= 14117 // INSTRUMENTATION 14118 // ========================================================= 14119 14120 public boolean startInstrumentation(ComponentName className, 14121 String profileFile, int flags, Bundle arguments, 14122 IInstrumentationWatcher watcher, IUiAutomationConnection uiAutomationConnection, 14123 int userId) { 14124 enforceNotIsolatedCaller("startInstrumentation"); 14125 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 14126 userId, false, true, "startInstrumentation", null); 14127 // Refuse possible leaked file descriptors 14128 if (arguments != null && arguments.hasFileDescriptors()) { 14129 throw new IllegalArgumentException("File descriptors passed in Bundle"); 14130 } 14131 14132 synchronized(this) { 14133 InstrumentationInfo ii = null; 14134 ApplicationInfo ai = null; 14135 try { 14136 ii = mContext.getPackageManager().getInstrumentationInfo( 14137 className, STOCK_PM_FLAGS); 14138 ai = AppGlobals.getPackageManager().getApplicationInfo( 14139 ii.targetPackage, STOCK_PM_FLAGS, userId); 14140 } catch (PackageManager.NameNotFoundException e) { 14141 } catch (RemoteException e) { 14142 } 14143 if (ii == null) { 14144 reportStartInstrumentationFailure(watcher, className, 14145 "Unable to find instrumentation info for: " + className); 14146 return false; 14147 } 14148 if (ai == null) { 14149 reportStartInstrumentationFailure(watcher, className, 14150 "Unable to find instrumentation target package: " + ii.targetPackage); 14151 return false; 14152 } 14153 14154 int match = mContext.getPackageManager().checkSignatures( 14155 ii.targetPackage, ii.packageName); 14156 if (match < 0 && match != PackageManager.SIGNATURE_FIRST_NOT_SIGNED) { 14157 String msg = "Permission Denial: starting instrumentation " 14158 + className + " from pid=" 14159 + Binder.getCallingPid() 14160 + ", uid=" + Binder.getCallingPid() 14161 + " not allowed because package " + ii.packageName 14162 + " does not have a signature matching the target " 14163 + ii.targetPackage; 14164 reportStartInstrumentationFailure(watcher, className, msg); 14165 throw new SecurityException(msg); 14166 } 14167 14168 final long origId = Binder.clearCallingIdentity(); 14169 // Instrumentation can kill and relaunch even persistent processes 14170 forceStopPackageLocked(ii.targetPackage, -1, true, false, true, true, false, userId, 14171 "start instr"); 14172 ProcessRecord app = addAppLocked(ai, false); 14173 app.instrumentationClass = className; 14174 app.instrumentationInfo = ai; 14175 app.instrumentationProfileFile = profileFile; 14176 app.instrumentationArguments = arguments; 14177 app.instrumentationWatcher = watcher; 14178 app.instrumentationUiAutomationConnection = uiAutomationConnection; 14179 app.instrumentationResultClass = className; 14180 Binder.restoreCallingIdentity(origId); 14181 } 14182 14183 return true; 14184 } 14185 14186 /** 14187 * Report errors that occur while attempting to start Instrumentation. Always writes the 14188 * error to the logs, but if somebody is watching, send the report there too. This enables 14189 * the "am" command to report errors with more information. 14190 * 14191 * @param watcher The IInstrumentationWatcher. Null if there isn't one. 14192 * @param cn The component name of the instrumentation. 14193 * @param report The error report. 14194 */ 14195 private void reportStartInstrumentationFailure(IInstrumentationWatcher watcher, 14196 ComponentName cn, String report) { 14197 Slog.w(TAG, report); 14198 try { 14199 if (watcher != null) { 14200 Bundle results = new Bundle(); 14201 results.putString(Instrumentation.REPORT_KEY_IDENTIFIER, "ActivityManagerService"); 14202 results.putString("Error", report); 14203 watcher.instrumentationStatus(cn, -1, results); 14204 } 14205 } catch (RemoteException e) { 14206 Slog.w(TAG, e); 14207 } 14208 } 14209 14210 void finishInstrumentationLocked(ProcessRecord app, int resultCode, Bundle results) { 14211 if (app.instrumentationWatcher != null) { 14212 try { 14213 // NOTE: IInstrumentationWatcher *must* be oneway here 14214 app.instrumentationWatcher.instrumentationFinished( 14215 app.instrumentationClass, 14216 resultCode, 14217 results); 14218 } catch (RemoteException e) { 14219 } 14220 } 14221 if (app.instrumentationUiAutomationConnection != null) { 14222 try { 14223 app.instrumentationUiAutomationConnection.shutdown(); 14224 } catch (RemoteException re) { 14225 /* ignore */ 14226 } 14227 // Only a UiAutomation can set this flag and now that 14228 // it is finished we make sure it is reset to its default. 14229 mUserIsMonkey = false; 14230 } 14231 app.instrumentationWatcher = null; 14232 app.instrumentationUiAutomationConnection = null; 14233 app.instrumentationClass = null; 14234 app.instrumentationInfo = null; 14235 app.instrumentationProfileFile = null; 14236 app.instrumentationArguments = null; 14237 14238 forceStopPackageLocked(app.info.packageName, -1, false, false, true, true, false, app.userId, 14239 "finished inst"); 14240 } 14241 14242 public void finishInstrumentation(IApplicationThread target, 14243 int resultCode, Bundle results) { 14244 int userId = UserHandle.getCallingUserId(); 14245 // Refuse possible leaked file descriptors 14246 if (results != null && results.hasFileDescriptors()) { 14247 throw new IllegalArgumentException("File descriptors passed in Intent"); 14248 } 14249 14250 synchronized(this) { 14251 ProcessRecord app = getRecordForAppLocked(target); 14252 if (app == null) { 14253 Slog.w(TAG, "finishInstrumentation: no app for " + target); 14254 return; 14255 } 14256 final long origId = Binder.clearCallingIdentity(); 14257 finishInstrumentationLocked(app, resultCode, results); 14258 Binder.restoreCallingIdentity(origId); 14259 } 14260 } 14261 14262 // ========================================================= 14263 // CONFIGURATION 14264 // ========================================================= 14265 14266 public ConfigurationInfo getDeviceConfigurationInfo() { 14267 ConfigurationInfo config = new ConfigurationInfo(); 14268 synchronized (this) { 14269 config.reqTouchScreen = mConfiguration.touchscreen; 14270 config.reqKeyboardType = mConfiguration.keyboard; 14271 config.reqNavigation = mConfiguration.navigation; 14272 if (mConfiguration.navigation == Configuration.NAVIGATION_DPAD 14273 || mConfiguration.navigation == Configuration.NAVIGATION_TRACKBALL) { 14274 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_FIVE_WAY_NAV; 14275 } 14276 if (mConfiguration.keyboard != Configuration.KEYBOARD_UNDEFINED 14277 && mConfiguration.keyboard != Configuration.KEYBOARD_NOKEYS) { 14278 config.reqInputFeatures |= ConfigurationInfo.INPUT_FEATURE_HARD_KEYBOARD; 14279 } 14280 config.reqGlEsVersion = GL_ES_VERSION; 14281 } 14282 return config; 14283 } 14284 14285 ActivityStack getFocusedStack() { 14286 return mStackSupervisor.getFocusedStack(); 14287 } 14288 14289 public Configuration getConfiguration() { 14290 Configuration ci; 14291 synchronized(this) { 14292 ci = new Configuration(mConfiguration); 14293 } 14294 return ci; 14295 } 14296 14297 public void updatePersistentConfiguration(Configuration values) { 14298 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 14299 "updateConfiguration()"); 14300 enforceCallingPermission(android.Manifest.permission.WRITE_SETTINGS, 14301 "updateConfiguration()"); 14302 if (values == null) { 14303 throw new NullPointerException("Configuration must not be null"); 14304 } 14305 14306 synchronized(this) { 14307 final long origId = Binder.clearCallingIdentity(); 14308 updateConfigurationLocked(values, null, true, false); 14309 Binder.restoreCallingIdentity(origId); 14310 } 14311 } 14312 14313 public void updateConfiguration(Configuration values) { 14314 enforceCallingPermission(android.Manifest.permission.CHANGE_CONFIGURATION, 14315 "updateConfiguration()"); 14316 14317 synchronized(this) { 14318 if (values == null && mWindowManager != null) { 14319 // sentinel: fetch the current configuration from the window manager 14320 values = mWindowManager.computeNewConfiguration(); 14321 } 14322 14323 if (mWindowManager != null) { 14324 mProcessList.applyDisplaySize(mWindowManager); 14325 } 14326 14327 final long origId = Binder.clearCallingIdentity(); 14328 if (values != null) { 14329 Settings.System.clearConfiguration(values); 14330 } 14331 updateConfigurationLocked(values, null, false, false); 14332 Binder.restoreCallingIdentity(origId); 14333 } 14334 } 14335 14336 /** 14337 * Do either or both things: (1) change the current configuration, and (2) 14338 * make sure the given activity is running with the (now) current 14339 * configuration. Returns true if the activity has been left running, or 14340 * false if <var>starting</var> is being destroyed to match the new 14341 * configuration. 14342 * @param persistent TODO 14343 */ 14344 boolean updateConfigurationLocked(Configuration values, 14345 ActivityRecord starting, boolean persistent, boolean initLocale) { 14346 int changes = 0; 14347 14348 if (values != null) { 14349 Configuration newConfig = new Configuration(mConfiguration); 14350 changes = newConfig.updateFrom(values); 14351 if (changes != 0) { 14352 if (DEBUG_SWITCH || DEBUG_CONFIGURATION) { 14353 Slog.i(TAG, "Updating configuration to: " + values); 14354 } 14355 14356 EventLog.writeEvent(EventLogTags.CONFIGURATION_CHANGED, changes); 14357 14358 if (values.locale != null && !initLocale) { 14359 saveLocaleLocked(values.locale, 14360 !values.locale.equals(mConfiguration.locale), 14361 values.userSetLocale); 14362 } 14363 14364 mConfigurationSeq++; 14365 if (mConfigurationSeq <= 0) { 14366 mConfigurationSeq = 1; 14367 } 14368 newConfig.seq = mConfigurationSeq; 14369 mConfiguration = newConfig; 14370 Slog.i(TAG, "Config changes=" + Integer.toHexString(changes) + " " + newConfig); 14371 14372 final Configuration configCopy = new Configuration(mConfiguration); 14373 14374 // TODO: If our config changes, should we auto dismiss any currently 14375 // showing dialogs? 14376 mShowDialogs = shouldShowDialogs(newConfig); 14377 14378 AttributeCache ac = AttributeCache.instance(); 14379 if (ac != null) { 14380 ac.updateConfiguration(configCopy); 14381 } 14382 14383 // Make sure all resources in our process are updated 14384 // right now, so that anyone who is going to retrieve 14385 // resource values after we return will be sure to get 14386 // the new ones. This is especially important during 14387 // boot, where the first config change needs to guarantee 14388 // all resources have that config before following boot 14389 // code is executed. 14390 mSystemThread.applyConfigurationToResources(configCopy); 14391 14392 if (persistent && Settings.System.hasInterestingConfigurationChanges(changes)) { 14393 Message msg = mHandler.obtainMessage(UPDATE_CONFIGURATION_MSG); 14394 msg.obj = new Configuration(configCopy); 14395 mHandler.sendMessage(msg); 14396 } 14397 14398 for (int i=mLruProcesses.size()-1; i>=0; i--) { 14399 ProcessRecord app = mLruProcesses.get(i); 14400 try { 14401 if (app.thread != null) { 14402 if (DEBUG_CONFIGURATION) Slog.v(TAG, "Sending to proc " 14403 + app.processName + " new config " + mConfiguration); 14404 app.thread.scheduleConfigurationChanged(configCopy); 14405 } 14406 } catch (Exception e) { 14407 } 14408 } 14409 Intent intent = new Intent(Intent.ACTION_CONFIGURATION_CHANGED); 14410 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 14411 | Intent.FLAG_RECEIVER_REPLACE_PENDING 14412 | Intent.FLAG_RECEIVER_FOREGROUND); 14413 broadcastIntentLocked(null, null, intent, null, null, 0, null, null, 14414 null, AppOpsManager.OP_NONE, false, false, MY_PID, 14415 Process.SYSTEM_UID, UserHandle.USER_ALL); 14416 if ((changes&ActivityInfo.CONFIG_LOCALE) != 0) { 14417 intent = new Intent(Intent.ACTION_LOCALE_CHANGED); 14418 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 14419 broadcastIntentLocked(null, null, intent, 14420 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 14421 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 14422 } 14423 } 14424 } 14425 14426 boolean kept = true; 14427 final ActivityStack mainStack = mStackSupervisor.getFocusedStack(); 14428 // mainStack is null during startup. 14429 if (mainStack != null) { 14430 if (changes != 0 && starting == null) { 14431 // If the configuration changed, and the caller is not already 14432 // in the process of starting an activity, then find the top 14433 // activity to check if its configuration needs to change. 14434 starting = mainStack.topRunningActivityLocked(null); 14435 } 14436 14437 if (starting != null) { 14438 kept = mainStack.ensureActivityConfigurationLocked(starting, changes); 14439 // And we need to make sure at this point that all other activities 14440 // are made visible with the correct configuration. 14441 mStackSupervisor.ensureActivitiesVisibleLocked(starting, changes); 14442 } 14443 } 14444 14445 if (values != null && mWindowManager != null) { 14446 mWindowManager.setNewConfiguration(mConfiguration); 14447 } 14448 14449 return kept; 14450 } 14451 14452 /** 14453 * Decide based on the configuration whether we should shouw the ANR, 14454 * crash, etc dialogs. The idea is that if there is no affordnace to 14455 * press the on-screen buttons, we shouldn't show the dialog. 14456 * 14457 * A thought: SystemUI might also want to get told about this, the Power 14458 * dialog / global actions also might want different behaviors. 14459 */ 14460 private static final boolean shouldShowDialogs(Configuration config) { 14461 return !(config.keyboard == Configuration.KEYBOARD_NOKEYS 14462 && config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH); 14463 } 14464 14465 /** 14466 * Save the locale. You must be inside a synchronized (this) block. 14467 */ 14468 private void saveLocaleLocked(Locale l, boolean isDiff, boolean isPersist) { 14469 if(isDiff) { 14470 SystemProperties.set("user.language", l.getLanguage()); 14471 SystemProperties.set("user.region", l.getCountry()); 14472 } 14473 14474 if(isPersist) { 14475 SystemProperties.set("persist.sys.language", l.getLanguage()); 14476 SystemProperties.set("persist.sys.country", l.getCountry()); 14477 SystemProperties.set("persist.sys.localevar", l.getVariant()); 14478 } 14479 } 14480 14481 @Override 14482 public boolean targetTaskAffinityMatchesActivity(IBinder token, String destAffinity) { 14483 ActivityRecord srec = ActivityRecord.forToken(token); 14484 return srec != null && srec.task.affinity != null && 14485 srec.task.affinity.equals(destAffinity); 14486 } 14487 14488 public boolean navigateUpTo(IBinder token, Intent destIntent, int resultCode, 14489 Intent resultData) { 14490 14491 synchronized (this) { 14492 final ActivityStack stack = ActivityRecord.getStackLocked(token); 14493 if (stack != null) { 14494 return stack.navigateUpToLocked(token, destIntent, resultCode, resultData); 14495 } 14496 return false; 14497 } 14498 } 14499 14500 public int getLaunchedFromUid(IBinder activityToken) { 14501 ActivityRecord srec = ActivityRecord.forToken(activityToken); 14502 if (srec == null) { 14503 return -1; 14504 } 14505 return srec.launchedFromUid; 14506 } 14507 14508 public String getLaunchedFromPackage(IBinder activityToken) { 14509 ActivityRecord srec = ActivityRecord.forToken(activityToken); 14510 if (srec == null) { 14511 return null; 14512 } 14513 return srec.launchedFromPackage; 14514 } 14515 14516 // ========================================================= 14517 // LIFETIME MANAGEMENT 14518 // ========================================================= 14519 14520 // Returns which broadcast queue the app is the current [or imminent] receiver 14521 // on, or 'null' if the app is not an active broadcast recipient. 14522 private BroadcastQueue isReceivingBroadcast(ProcessRecord app) { 14523 BroadcastRecord r = app.curReceiver; 14524 if (r != null) { 14525 return r.queue; 14526 } 14527 14528 // It's not the current receiver, but it might be starting up to become one 14529 synchronized (this) { 14530 for (BroadcastQueue queue : mBroadcastQueues) { 14531 r = queue.mPendingBroadcast; 14532 if (r != null && r.curApp == app) { 14533 // found it; report which queue it's in 14534 return queue; 14535 } 14536 } 14537 } 14538 14539 return null; 14540 } 14541 14542 private final int computeOomAdjLocked(ProcessRecord app, int cachedAdj, ProcessRecord TOP_APP, 14543 boolean doingAll, long now) { 14544 if (mAdjSeq == app.adjSeq) { 14545 // This adjustment has already been computed. 14546 return app.curRawAdj; 14547 } 14548 14549 if (app.thread == null) { 14550 app.adjSeq = mAdjSeq; 14551 app.curSchedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 14552 app.curProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 14553 return (app.curAdj=app.curRawAdj=ProcessList.CACHED_APP_MAX_ADJ); 14554 } 14555 14556 app.adjTypeCode = ActivityManager.RunningAppProcessInfo.REASON_UNKNOWN; 14557 app.adjSource = null; 14558 app.adjTarget = null; 14559 app.empty = false; 14560 app.cached = false; 14561 14562 final int activitiesSize = app.activities.size(); 14563 14564 if (app.maxAdj <= ProcessList.FOREGROUND_APP_ADJ) { 14565 // The max adjustment doesn't allow this app to be anything 14566 // below foreground, so it is not worth doing work for it. 14567 app.adjType = "fixed"; 14568 app.adjSeq = mAdjSeq; 14569 app.curRawAdj = app.maxAdj; 14570 app.foregroundActivities = false; 14571 app.keeping = true; 14572 app.curSchedGroup = Process.THREAD_GROUP_DEFAULT; 14573 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT; 14574 // System processes can do UI, and when they do we want to have 14575 // them trim their memory after the user leaves the UI. To 14576 // facilitate this, here we need to determine whether or not it 14577 // is currently showing UI. 14578 app.systemNoUi = true; 14579 if (app == TOP_APP) { 14580 app.systemNoUi = false; 14581 } else if (activitiesSize > 0) { 14582 for (int j = 0; j < activitiesSize; j++) { 14583 final ActivityRecord r = app.activities.get(j); 14584 if (r.visible) { 14585 app.systemNoUi = false; 14586 } 14587 } 14588 } 14589 if (!app.systemNoUi) { 14590 app.curProcState = ActivityManager.PROCESS_STATE_PERSISTENT_UI; 14591 } 14592 return (app.curAdj=app.maxAdj); 14593 } 14594 14595 app.keeping = false; 14596 app.systemNoUi = false; 14597 14598 // Determine the importance of the process, starting with most 14599 // important to least, and assign an appropriate OOM adjustment. 14600 int adj; 14601 int schedGroup; 14602 int procState; 14603 boolean foregroundActivities = false; 14604 boolean interesting = false; 14605 BroadcastQueue queue; 14606 if (app == TOP_APP) { 14607 // The last app on the list is the foreground app. 14608 adj = ProcessList.FOREGROUND_APP_ADJ; 14609 schedGroup = Process.THREAD_GROUP_DEFAULT; 14610 app.adjType = "top-activity"; 14611 foregroundActivities = true; 14612 interesting = true; 14613 procState = ActivityManager.PROCESS_STATE_TOP; 14614 } else if (app.instrumentationClass != null) { 14615 // Don't want to kill running instrumentation. 14616 adj = ProcessList.FOREGROUND_APP_ADJ; 14617 schedGroup = Process.THREAD_GROUP_DEFAULT; 14618 app.adjType = "instrumentation"; 14619 interesting = true; 14620 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 14621 } else if ((queue = isReceivingBroadcast(app)) != null) { 14622 // An app that is currently receiving a broadcast also 14623 // counts as being in the foreground for OOM killer purposes. 14624 // It's placed in a sched group based on the nature of the 14625 // broadcast as reflected by which queue it's active in. 14626 adj = ProcessList.FOREGROUND_APP_ADJ; 14627 schedGroup = (queue == mFgBroadcastQueue) 14628 ? Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 14629 app.adjType = "broadcast"; 14630 procState = ActivityManager.PROCESS_STATE_RECEIVER; 14631 } else if (app.executingServices.size() > 0) { 14632 // An app that is currently executing a service callback also 14633 // counts as being in the foreground. 14634 adj = ProcessList.FOREGROUND_APP_ADJ; 14635 schedGroup = app.execServicesFg ? 14636 Process.THREAD_GROUP_DEFAULT : Process.THREAD_GROUP_BG_NONINTERACTIVE; 14637 app.adjType = "exec-service"; 14638 procState = ActivityManager.PROCESS_STATE_SERVICE; 14639 //Slog.i(TAG, "EXEC " + (app.execServicesFg ? "FG" : "BG") + ": " + app); 14640 } else { 14641 // As far as we know the process is empty. We may change our mind later. 14642 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 14643 // At this point we don't actually know the adjustment. Use the cached adj 14644 // value that the caller wants us to. 14645 adj = cachedAdj; 14646 procState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 14647 app.cached = true; 14648 app.empty = true; 14649 app.adjType = "cch-empty"; 14650 } 14651 14652 // Examine all activities if not already foreground. 14653 if (!foregroundActivities && activitiesSize > 0) { 14654 for (int j = 0; j < activitiesSize; j++) { 14655 final ActivityRecord r = app.activities.get(j); 14656 if (r.app != app) { 14657 Slog.w(TAG, "Wtf, activity " + r + " in proc activity list not using proc " 14658 + app + "?!?"); 14659 continue; 14660 } 14661 if (r.visible) { 14662 // App has a visible activity; only upgrade adjustment. 14663 if (adj > ProcessList.VISIBLE_APP_ADJ) { 14664 adj = ProcessList.VISIBLE_APP_ADJ; 14665 app.adjType = "visible"; 14666 } 14667 if (procState > ActivityManager.PROCESS_STATE_TOP) { 14668 procState = ActivityManager.PROCESS_STATE_TOP; 14669 } 14670 schedGroup = Process.THREAD_GROUP_DEFAULT; 14671 app.cached = false; 14672 app.empty = false; 14673 foregroundActivities = true; 14674 break; 14675 } else if (r.state == ActivityState.PAUSING || r.state == ActivityState.PAUSED) { 14676 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 14677 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 14678 app.adjType = "pausing"; 14679 } 14680 if (procState > ActivityManager.PROCESS_STATE_TOP) { 14681 procState = ActivityManager.PROCESS_STATE_TOP; 14682 } 14683 schedGroup = Process.THREAD_GROUP_DEFAULT; 14684 app.cached = false; 14685 app.empty = false; 14686 foregroundActivities = true; 14687 } else if (r.state == ActivityState.STOPPING) { 14688 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 14689 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 14690 app.adjType = "stopping"; 14691 } 14692 // For the process state, we will at this point consider the 14693 // process to be cached. It will be cached either as an activity 14694 // or empty depending on whether the activity is finishing. We do 14695 // this so that we can treat the process as cached for purposes of 14696 // memory trimming (determing current memory level, trim command to 14697 // send to process) since there can be an arbitrary number of stopping 14698 // processes and they should soon all go into the cached state. 14699 if (!r.finishing) { 14700 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 14701 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 14702 } 14703 } 14704 app.cached = false; 14705 app.empty = false; 14706 foregroundActivities = true; 14707 } else { 14708 if (procState > ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 14709 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 14710 app.adjType = "cch-act"; 14711 } 14712 } 14713 } 14714 } 14715 14716 if (adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 14717 if (app.foregroundServices) { 14718 // The user is aware of this app, so make it visible. 14719 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 14720 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 14721 app.cached = false; 14722 app.adjType = "fg-service"; 14723 schedGroup = Process.THREAD_GROUP_DEFAULT; 14724 } else if (app.forcingToForeground != null) { 14725 // The user is aware of this app, so make it visible. 14726 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 14727 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 14728 app.cached = false; 14729 app.adjType = "force-fg"; 14730 app.adjSource = app.forcingToForeground; 14731 schedGroup = Process.THREAD_GROUP_DEFAULT; 14732 } 14733 } 14734 14735 if (app.foregroundServices) { 14736 interesting = true; 14737 } 14738 14739 if (app == mHeavyWeightProcess) { 14740 if (adj > ProcessList.HEAVY_WEIGHT_APP_ADJ) { 14741 // We don't want to kill the current heavy-weight process. 14742 adj = ProcessList.HEAVY_WEIGHT_APP_ADJ; 14743 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 14744 app.cached = false; 14745 app.adjType = "heavy"; 14746 } 14747 if (procState > ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 14748 procState = ActivityManager.PROCESS_STATE_HEAVY_WEIGHT; 14749 } 14750 } 14751 14752 if (app == mHomeProcess) { 14753 if (adj > ProcessList.HOME_APP_ADJ) { 14754 // This process is hosting what we currently consider to be the 14755 // home app, so we don't want to let it go into the background. 14756 adj = ProcessList.HOME_APP_ADJ; 14757 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 14758 app.cached = false; 14759 app.adjType = "home"; 14760 } 14761 if (procState > ActivityManager.PROCESS_STATE_HOME) { 14762 procState = ActivityManager.PROCESS_STATE_HOME; 14763 } 14764 } 14765 14766 if (app == mPreviousProcess && app.activities.size() > 0) { 14767 if (adj > ProcessList.PREVIOUS_APP_ADJ) { 14768 // This was the previous process that showed UI to the user. 14769 // We want to try to keep it around more aggressively, to give 14770 // a good experience around switching between two apps. 14771 adj = ProcessList.PREVIOUS_APP_ADJ; 14772 schedGroup = Process.THREAD_GROUP_BG_NONINTERACTIVE; 14773 app.cached = false; 14774 app.adjType = "previous"; 14775 } 14776 if (procState > ActivityManager.PROCESS_STATE_LAST_ACTIVITY) { 14777 procState = ActivityManager.PROCESS_STATE_LAST_ACTIVITY; 14778 } 14779 } 14780 14781 if (false) Slog.i(TAG, "OOM " + app + ": initial adj=" + adj 14782 + " reason=" + app.adjType); 14783 14784 // By default, we use the computed adjustment. It may be changed if 14785 // there are applications dependent on our services or providers, but 14786 // this gives us a baseline and makes sure we don't get into an 14787 // infinite recursion. 14788 app.adjSeq = mAdjSeq; 14789 app.curRawAdj = adj; 14790 app.hasStartedServices = false; 14791 14792 if (mBackupTarget != null && app == mBackupTarget.app) { 14793 // If possible we want to avoid killing apps while they're being backed up 14794 if (adj > ProcessList.BACKUP_APP_ADJ) { 14795 if (DEBUG_BACKUP) Slog.v(TAG, "oom BACKUP_APP_ADJ for " + app); 14796 adj = ProcessList.BACKUP_APP_ADJ; 14797 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 14798 procState = ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 14799 } 14800 app.adjType = "backup"; 14801 app.cached = false; 14802 } 14803 if (procState > ActivityManager.PROCESS_STATE_BACKUP) { 14804 procState = ActivityManager.PROCESS_STATE_BACKUP; 14805 } 14806 } 14807 14808 boolean mayBeTop = false; 14809 14810 for (int is = app.services.size()-1; 14811 is >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 14812 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 14813 || procState > ActivityManager.PROCESS_STATE_TOP); 14814 is--) { 14815 ServiceRecord s = app.services.valueAt(is); 14816 if (s.startRequested) { 14817 app.hasStartedServices = true; 14818 if (procState > ActivityManager.PROCESS_STATE_SERVICE) { 14819 procState = ActivityManager.PROCESS_STATE_SERVICE; 14820 } 14821 if (app.hasShownUi && app != mHomeProcess) { 14822 // If this process has shown some UI, let it immediately 14823 // go to the LRU list because it may be pretty heavy with 14824 // UI stuff. We'll tag it with a label just to help 14825 // debug and understand what is going on. 14826 if (adj > ProcessList.SERVICE_ADJ) { 14827 app.adjType = "cch-started-ui-services"; 14828 } 14829 } else { 14830 if (now < (s.lastActivity + ActiveServices.MAX_SERVICE_INACTIVITY)) { 14831 // This service has seen some activity within 14832 // recent memory, so we will keep its process ahead 14833 // of the background processes. 14834 if (adj > ProcessList.SERVICE_ADJ) { 14835 adj = ProcessList.SERVICE_ADJ; 14836 app.adjType = "started-services"; 14837 app.cached = false; 14838 } 14839 } 14840 // If we have let the service slide into the background 14841 // state, still have some text describing what it is doing 14842 // even though the service no longer has an impact. 14843 if (adj > ProcessList.SERVICE_ADJ) { 14844 app.adjType = "cch-started-services"; 14845 } 14846 } 14847 // Don't kill this process because it is doing work; it 14848 // has said it is doing work. 14849 app.keeping = true; 14850 } 14851 for (int conni = s.connections.size()-1; 14852 conni >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 14853 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 14854 || procState > ActivityManager.PROCESS_STATE_TOP); 14855 conni--) { 14856 ArrayList<ConnectionRecord> clist = s.connections.valueAt(conni); 14857 for (int i = 0; 14858 i < clist.size() && (adj > ProcessList.FOREGROUND_APP_ADJ 14859 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 14860 || procState > ActivityManager.PROCESS_STATE_TOP); 14861 i++) { 14862 // XXX should compute this based on the max of 14863 // all connected clients. 14864 ConnectionRecord cr = clist.get(i); 14865 if (cr.binding.client == app) { 14866 // Binding to ourself is not interesting. 14867 continue; 14868 } 14869 if ((cr.flags&Context.BIND_WAIVE_PRIORITY) == 0) { 14870 ProcessRecord client = cr.binding.client; 14871 int clientAdj = computeOomAdjLocked(client, cachedAdj, 14872 TOP_APP, doingAll, now); 14873 int clientProcState = client.curProcState; 14874 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 14875 // If the other app is cached for any reason, for purposes here 14876 // we are going to consider it empty. The specific cached state 14877 // doesn't propagate except under certain conditions. 14878 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 14879 } 14880 String adjType = null; 14881 if ((cr.flags&Context.BIND_ALLOW_OOM_MANAGEMENT) != 0) { 14882 // Not doing bind OOM management, so treat 14883 // this guy more like a started service. 14884 if (app.hasShownUi && app != mHomeProcess) { 14885 // If this process has shown some UI, let it immediately 14886 // go to the LRU list because it may be pretty heavy with 14887 // UI stuff. We'll tag it with a label just to help 14888 // debug and understand what is going on. 14889 if (adj > clientAdj) { 14890 adjType = "cch-bound-ui-services"; 14891 } 14892 app.cached = false; 14893 clientAdj = adj; 14894 clientProcState = procState; 14895 } else { 14896 if (now >= (s.lastActivity 14897 + ActiveServices.MAX_SERVICE_INACTIVITY)) { 14898 // This service has not seen activity within 14899 // recent memory, so allow it to drop to the 14900 // LRU list if there is no other reason to keep 14901 // it around. We'll also tag it with a label just 14902 // to help debug and undertand what is going on. 14903 if (adj > clientAdj) { 14904 adjType = "cch-bound-services"; 14905 } 14906 clientAdj = adj; 14907 } 14908 } 14909 } 14910 if (adj > clientAdj) { 14911 // If this process has recently shown UI, and 14912 // the process that is binding to it is less 14913 // important than being visible, then we don't 14914 // care about the binding as much as we care 14915 // about letting this process get into the LRU 14916 // list to be killed and restarted if needed for 14917 // memory. 14918 if (app.hasShownUi && app != mHomeProcess 14919 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 14920 adjType = "cch-bound-ui-services"; 14921 } else { 14922 if ((cr.flags&(Context.BIND_ABOVE_CLIENT 14923 |Context.BIND_IMPORTANT)) != 0) { 14924 adj = clientAdj; 14925 } else if ((cr.flags&Context.BIND_NOT_VISIBLE) != 0 14926 && clientAdj < ProcessList.PERCEPTIBLE_APP_ADJ 14927 && adj > ProcessList.PERCEPTIBLE_APP_ADJ) { 14928 adj = ProcessList.PERCEPTIBLE_APP_ADJ; 14929 } else if (clientAdj > ProcessList.VISIBLE_APP_ADJ) { 14930 adj = clientAdj; 14931 } else { 14932 if (adj > ProcessList.VISIBLE_APP_ADJ) { 14933 adj = ProcessList.VISIBLE_APP_ADJ; 14934 } 14935 } 14936 if (!client.cached) { 14937 app.cached = false; 14938 } 14939 if (client.keeping) { 14940 app.keeping = true; 14941 } 14942 adjType = "service"; 14943 } 14944 } 14945 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 14946 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 14947 schedGroup = Process.THREAD_GROUP_DEFAULT; 14948 } 14949 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 14950 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 14951 // Special handling of clients who are in the top state. 14952 // We *may* want to consider this process to be in the 14953 // top state as well, but only if there is not another 14954 // reason for it to be running. Being on the top is a 14955 // special state, meaning you are specifically running 14956 // for the current top app. If the process is already 14957 // running in the background for some other reason, it 14958 // is more important to continue considering it to be 14959 // in the background state. 14960 mayBeTop = true; 14961 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 14962 } else { 14963 // Special handling for above-top states (persistent 14964 // processes). These should not bring the current process 14965 // into the top state, since they are not on top. Instead 14966 // give them the best state after that. 14967 clientProcState = 14968 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 14969 } 14970 } 14971 } else { 14972 if (clientProcState < 14973 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND) { 14974 clientProcState = 14975 ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND; 14976 } 14977 } 14978 if (procState > clientProcState) { 14979 procState = clientProcState; 14980 } 14981 if (procState < ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 14982 && (cr.flags&Context.BIND_SHOWING_UI) != 0) { 14983 app.pendingUiClean = true; 14984 } 14985 if (adjType != null) { 14986 app.adjType = adjType; 14987 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 14988 .REASON_SERVICE_IN_USE; 14989 app.adjSource = cr.binding.client; 14990 app.adjSourceOom = clientAdj; 14991 app.adjTarget = s.name; 14992 } 14993 } 14994 if ((cr.flags&Context.BIND_TREAT_LIKE_ACTIVITY) != 0) { 14995 app.treatLikeActivity = true; 14996 } 14997 final ActivityRecord a = cr.activity; 14998 if ((cr.flags&Context.BIND_ADJUST_WITH_ACTIVITY) != 0) { 14999 if (a != null && adj > ProcessList.FOREGROUND_APP_ADJ && 15000 (a.visible || a.state == ActivityState.RESUMED 15001 || a.state == ActivityState.PAUSING)) { 15002 adj = ProcessList.FOREGROUND_APP_ADJ; 15003 if ((cr.flags&Context.BIND_NOT_FOREGROUND) == 0) { 15004 schedGroup = Process.THREAD_GROUP_DEFAULT; 15005 } 15006 app.cached = false; 15007 app.adjType = "service"; 15008 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15009 .REASON_SERVICE_IN_USE; 15010 app.adjSource = a; 15011 app.adjSourceOom = adj; 15012 app.adjTarget = s.name; 15013 } 15014 } 15015 } 15016 } 15017 } 15018 15019 for (int provi = app.pubProviders.size()-1; 15020 provi >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15021 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15022 || procState > ActivityManager.PROCESS_STATE_TOP); 15023 provi--) { 15024 ContentProviderRecord cpr = app.pubProviders.valueAt(provi); 15025 for (int i = cpr.connections.size()-1; 15026 i >= 0 && (adj > ProcessList.FOREGROUND_APP_ADJ 15027 || schedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE 15028 || procState > ActivityManager.PROCESS_STATE_TOP); 15029 i--) { 15030 ContentProviderConnection conn = cpr.connections.get(i); 15031 ProcessRecord client = conn.client; 15032 if (client == app) { 15033 // Being our own client is not interesting. 15034 continue; 15035 } 15036 int clientAdj = computeOomAdjLocked(client, cachedAdj, TOP_APP, doingAll, now); 15037 int clientProcState = client.curProcState; 15038 if (clientProcState >= ActivityManager.PROCESS_STATE_CACHED_ACTIVITY) { 15039 // If the other app is cached for any reason, for purposes here 15040 // we are going to consider it empty. 15041 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15042 } 15043 if (adj > clientAdj) { 15044 if (app.hasShownUi && app != mHomeProcess 15045 && clientAdj > ProcessList.PERCEPTIBLE_APP_ADJ) { 15046 app.adjType = "cch-ui-provider"; 15047 } else { 15048 adj = clientAdj > ProcessList.FOREGROUND_APP_ADJ 15049 ? clientAdj : ProcessList.FOREGROUND_APP_ADJ; 15050 app.adjType = "provider"; 15051 } 15052 app.cached &= client.cached; 15053 app.keeping |= client.keeping; 15054 app.adjTypeCode = ActivityManager.RunningAppProcessInfo 15055 .REASON_PROVIDER_IN_USE; 15056 app.adjSource = client; 15057 app.adjSourceOom = clientAdj; 15058 app.adjTarget = cpr.name; 15059 } 15060 if (clientProcState <= ActivityManager.PROCESS_STATE_TOP) { 15061 if (clientProcState == ActivityManager.PROCESS_STATE_TOP) { 15062 // Special handling of clients who are in the top state. 15063 // We *may* want to consider this process to be in the 15064 // top state as well, but only if there is not another 15065 // reason for it to be running. Being on the top is a 15066 // special state, meaning you are specifically running 15067 // for the current top app. If the process is already 15068 // running in the background for some other reason, it 15069 // is more important to continue considering it to be 15070 // in the background state. 15071 mayBeTop = true; 15072 clientProcState = ActivityManager.PROCESS_STATE_CACHED_EMPTY; 15073 } else { 15074 // Special handling for above-top states (persistent 15075 // processes). These should not bring the current process 15076 // into the top state, since they are not on top. Instead 15077 // give them the best state after that. 15078 clientProcState = 15079 ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15080 } 15081 } 15082 if (procState > clientProcState) { 15083 procState = clientProcState; 15084 } 15085 if (client.curSchedGroup == Process.THREAD_GROUP_DEFAULT) { 15086 schedGroup = Process.THREAD_GROUP_DEFAULT; 15087 } 15088 } 15089 // If the provider has external (non-framework) process 15090 // dependencies, ensure that its adjustment is at least 15091 // FOREGROUND_APP_ADJ. 15092 if (cpr.hasExternalProcessHandles()) { 15093 if (adj > ProcessList.FOREGROUND_APP_ADJ) { 15094 adj = ProcessList.FOREGROUND_APP_ADJ; 15095 schedGroup = Process.THREAD_GROUP_DEFAULT; 15096 app.cached = false; 15097 app.keeping = true; 15098 app.adjType = "provider"; 15099 app.adjTarget = cpr.name; 15100 } 15101 if (procState > ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND) { 15102 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15103 } 15104 } 15105 } 15106 15107 if (mayBeTop && procState > ActivityManager.PROCESS_STATE_TOP) { 15108 // A client of one of our services or providers is in the top state. We 15109 // *may* want to be in the top state, but not if we are already running in 15110 // the background for some other reason. For the decision here, we are going 15111 // to pick out a few specific states that we want to remain in when a client 15112 // is top (states that tend to be longer-term) and otherwise allow it to go 15113 // to the top state. 15114 switch (procState) { 15115 case ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND: 15116 case ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND: 15117 case ActivityManager.PROCESS_STATE_SERVICE: 15118 // These all are longer-term states, so pull them up to the top 15119 // of the background states, but not all the way to the top state. 15120 procState = ActivityManager.PROCESS_STATE_IMPORTANT_FOREGROUND; 15121 break; 15122 default: 15123 // Otherwise, top is a better choice, so take it. 15124 procState = ActivityManager.PROCESS_STATE_TOP; 15125 break; 15126 } 15127 } 15128 15129 if (procState >= ActivityManager.PROCESS_STATE_CACHED_EMPTY) { 15130 if (app.hasClientActivities) { 15131 // This is a cached process, but with client activities. Mark it so. 15132 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT; 15133 app.adjType = "cch-client-act"; 15134 } else if (app.treatLikeActivity) { 15135 // This is a cached process, but somebody wants us to treat it like it has 15136 // an activity, okay! 15137 procState = ActivityManager.PROCESS_STATE_CACHED_ACTIVITY; 15138 app.adjType = "cch-as-act"; 15139 } 15140 } 15141 15142 if (adj == ProcessList.SERVICE_ADJ) { 15143 if (doingAll) { 15144 app.serviceb = mNewNumAServiceProcs > (mNumServiceProcs/3); 15145 mNewNumServiceProcs++; 15146 //Slog.i(TAG, "ADJ " + app + " serviceb=" + app.serviceb); 15147 if (!app.serviceb) { 15148 // This service isn't far enough down on the LRU list to 15149 // normally be a B service, but if we are low on RAM and it 15150 // is large we want to force it down since we would prefer to 15151 // keep launcher over it. 15152 if (mLastMemoryLevel > ProcessStats.ADJ_MEM_FACTOR_NORMAL 15153 && app.lastPss >= mProcessList.getCachedRestoreThresholdKb()) { 15154 app.serviceHighRam = true; 15155 app.serviceb = true; 15156 //Slog.i(TAG, "ADJ " + app + " high ram!"); 15157 } else { 15158 mNewNumAServiceProcs++; 15159 //Slog.i(TAG, "ADJ " + app + " not high ram!"); 15160 } 15161 } else { 15162 app.serviceHighRam = false; 15163 } 15164 } 15165 if (app.serviceb) { 15166 adj = ProcessList.SERVICE_B_ADJ; 15167 } 15168 } 15169 15170 app.curRawAdj = adj; 15171 15172 //Slog.i(TAG, "OOM ADJ " + app + ": pid=" + app.pid + 15173 // " adj=" + adj + " curAdj=" + app.curAdj + " maxAdj=" + app.maxAdj); 15174 if (adj > app.maxAdj) { 15175 adj = app.maxAdj; 15176 if (app.maxAdj <= ProcessList.PERCEPTIBLE_APP_ADJ) { 15177 schedGroup = Process.THREAD_GROUP_DEFAULT; 15178 } 15179 } 15180 if (adj < ProcessList.CACHED_APP_MIN_ADJ) { 15181 app.keeping = true; 15182 } 15183 15184 // Do final modification to adj. Everything we do between here and applying 15185 // the final setAdj must be done in this function, because we will also use 15186 // it when computing the final cached adj later. Note that we don't need to 15187 // worry about this for max adj above, since max adj will always be used to 15188 // keep it out of the cached vaues. 15189 app.curAdj = app.modifyRawOomAdj(adj); 15190 app.curSchedGroup = schedGroup; 15191 app.curProcState = procState; 15192 app.foregroundActivities = foregroundActivities; 15193 15194 return app.curRawAdj; 15195 } 15196 15197 /** 15198 * Schedule PSS collection of a process. 15199 */ 15200 void requestPssLocked(ProcessRecord proc, int procState) { 15201 if (mPendingPssProcesses.contains(proc)) { 15202 return; 15203 } 15204 if (mPendingPssProcesses.size() == 0) { 15205 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 15206 } 15207 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of: " + proc); 15208 proc.pssProcState = procState; 15209 mPendingPssProcesses.add(proc); 15210 } 15211 15212 /** 15213 * Schedule PSS collection of all processes. 15214 */ 15215 void requestPssAllProcsLocked(long now, boolean always, boolean memLowered) { 15216 if (!always) { 15217 if (now < (mLastFullPssTime + 15218 (memLowered ? FULL_PSS_LOWERED_INTERVAL : FULL_PSS_MIN_INTERVAL))) { 15219 return; 15220 } 15221 } 15222 if (DEBUG_PSS) Slog.d(TAG, "Requesting PSS of all procs! memLowered=" + memLowered); 15223 mLastFullPssTime = now; 15224 mPendingPssProcesses.ensureCapacity(mLruProcesses.size()); 15225 mPendingPssProcesses.clear(); 15226 for (int i=mLruProcesses.size()-1; i>=0; i--) { 15227 ProcessRecord app = mLruProcesses.get(i); 15228 if (memLowered || now > (app.lastStateTime+ProcessList.PSS_ALL_INTERVAL)) { 15229 app.pssProcState = app.setProcState; 15230 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 15231 isSleeping(), now); 15232 mPendingPssProcesses.add(app); 15233 } 15234 } 15235 mBgHandler.sendEmptyMessage(COLLECT_PSS_BG_MSG); 15236 } 15237 15238 /** 15239 * Ask a given process to GC right now. 15240 */ 15241 final void performAppGcLocked(ProcessRecord app) { 15242 try { 15243 app.lastRequestedGc = SystemClock.uptimeMillis(); 15244 if (app.thread != null) { 15245 if (app.reportLowMemory) { 15246 app.reportLowMemory = false; 15247 app.thread.scheduleLowMemory(); 15248 } else { 15249 app.thread.processInBackground(); 15250 } 15251 } 15252 } catch (Exception e) { 15253 // whatever. 15254 } 15255 } 15256 15257 /** 15258 * Returns true if things are idle enough to perform GCs. 15259 */ 15260 private final boolean canGcNowLocked() { 15261 boolean processingBroadcasts = false; 15262 for (BroadcastQueue q : mBroadcastQueues) { 15263 if (q.mParallelBroadcasts.size() != 0 || q.mOrderedBroadcasts.size() != 0) { 15264 processingBroadcasts = true; 15265 } 15266 } 15267 return !processingBroadcasts 15268 && (isSleeping() || mStackSupervisor.allResumedActivitiesIdle()); 15269 } 15270 15271 /** 15272 * Perform GCs on all processes that are waiting for it, but only 15273 * if things are idle. 15274 */ 15275 final void performAppGcsLocked() { 15276 final int N = mProcessesToGc.size(); 15277 if (N <= 0) { 15278 return; 15279 } 15280 if (canGcNowLocked()) { 15281 while (mProcessesToGc.size() > 0) { 15282 ProcessRecord proc = mProcessesToGc.remove(0); 15283 if (proc.curRawAdj > ProcessList.PERCEPTIBLE_APP_ADJ || proc.reportLowMemory) { 15284 if ((proc.lastRequestedGc+GC_MIN_INTERVAL) 15285 <= SystemClock.uptimeMillis()) { 15286 // To avoid spamming the system, we will GC processes one 15287 // at a time, waiting a few seconds between each. 15288 performAppGcLocked(proc); 15289 scheduleAppGcsLocked(); 15290 return; 15291 } else { 15292 // It hasn't been long enough since we last GCed this 15293 // process... put it in the list to wait for its time. 15294 addProcessToGcListLocked(proc); 15295 break; 15296 } 15297 } 15298 } 15299 15300 scheduleAppGcsLocked(); 15301 } 15302 } 15303 15304 /** 15305 * If all looks good, perform GCs on all processes waiting for them. 15306 */ 15307 final void performAppGcsIfAppropriateLocked() { 15308 if (canGcNowLocked()) { 15309 performAppGcsLocked(); 15310 return; 15311 } 15312 // Still not idle, wait some more. 15313 scheduleAppGcsLocked(); 15314 } 15315 15316 /** 15317 * Schedule the execution of all pending app GCs. 15318 */ 15319 final void scheduleAppGcsLocked() { 15320 mHandler.removeMessages(GC_BACKGROUND_PROCESSES_MSG); 15321 15322 if (mProcessesToGc.size() > 0) { 15323 // Schedule a GC for the time to the next process. 15324 ProcessRecord proc = mProcessesToGc.get(0); 15325 Message msg = mHandler.obtainMessage(GC_BACKGROUND_PROCESSES_MSG); 15326 15327 long when = proc.lastRequestedGc + GC_MIN_INTERVAL; 15328 long now = SystemClock.uptimeMillis(); 15329 if (when < (now+GC_TIMEOUT)) { 15330 when = now + GC_TIMEOUT; 15331 } 15332 mHandler.sendMessageAtTime(msg, when); 15333 } 15334 } 15335 15336 /** 15337 * Add a process to the array of processes waiting to be GCed. Keeps the 15338 * list in sorted order by the last GC time. The process can't already be 15339 * on the list. 15340 */ 15341 final void addProcessToGcListLocked(ProcessRecord proc) { 15342 boolean added = false; 15343 for (int i=mProcessesToGc.size()-1; i>=0; i--) { 15344 if (mProcessesToGc.get(i).lastRequestedGc < 15345 proc.lastRequestedGc) { 15346 added = true; 15347 mProcessesToGc.add(i+1, proc); 15348 break; 15349 } 15350 } 15351 if (!added) { 15352 mProcessesToGc.add(0, proc); 15353 } 15354 } 15355 15356 /** 15357 * Set up to ask a process to GC itself. This will either do it 15358 * immediately, or put it on the list of processes to gc the next 15359 * time things are idle. 15360 */ 15361 final void scheduleAppGcLocked(ProcessRecord app) { 15362 long now = SystemClock.uptimeMillis(); 15363 if ((app.lastRequestedGc+GC_MIN_INTERVAL) > now) { 15364 return; 15365 } 15366 if (!mProcessesToGc.contains(app)) { 15367 addProcessToGcListLocked(app); 15368 scheduleAppGcsLocked(); 15369 } 15370 } 15371 15372 final void checkExcessivePowerUsageLocked(boolean doKills) { 15373 updateCpuStatsNow(); 15374 15375 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 15376 boolean doWakeKills = doKills; 15377 boolean doCpuKills = doKills; 15378 if (mLastPowerCheckRealtime == 0) { 15379 doWakeKills = false; 15380 } 15381 if (mLastPowerCheckUptime == 0) { 15382 doCpuKills = false; 15383 } 15384 if (stats.isScreenOn()) { 15385 doWakeKills = false; 15386 } 15387 final long curRealtime = SystemClock.elapsedRealtime(); 15388 final long realtimeSince = curRealtime - mLastPowerCheckRealtime; 15389 final long curUptime = SystemClock.uptimeMillis(); 15390 final long uptimeSince = curUptime - mLastPowerCheckUptime; 15391 mLastPowerCheckRealtime = curRealtime; 15392 mLastPowerCheckUptime = curUptime; 15393 if (realtimeSince < WAKE_LOCK_MIN_CHECK_DURATION) { 15394 doWakeKills = false; 15395 } 15396 if (uptimeSince < CPU_MIN_CHECK_DURATION) { 15397 doCpuKills = false; 15398 } 15399 int i = mLruProcesses.size(); 15400 while (i > 0) { 15401 i--; 15402 ProcessRecord app = mLruProcesses.get(i); 15403 if (!app.keeping) { 15404 long wtime; 15405 synchronized (stats) { 15406 wtime = stats.getProcessWakeTime(app.info.uid, 15407 app.pid, curRealtime); 15408 } 15409 long wtimeUsed = wtime - app.lastWakeTime; 15410 long cputimeUsed = app.curCpuTime - app.lastCpuTime; 15411 if (DEBUG_POWER) { 15412 StringBuilder sb = new StringBuilder(128); 15413 sb.append("Wake for "); 15414 app.toShortString(sb); 15415 sb.append(": over "); 15416 TimeUtils.formatDuration(realtimeSince, sb); 15417 sb.append(" used "); 15418 TimeUtils.formatDuration(wtimeUsed, sb); 15419 sb.append(" ("); 15420 sb.append((wtimeUsed*100)/realtimeSince); 15421 sb.append("%)"); 15422 Slog.i(TAG, sb.toString()); 15423 sb.setLength(0); 15424 sb.append("CPU for "); 15425 app.toShortString(sb); 15426 sb.append(": over "); 15427 TimeUtils.formatDuration(uptimeSince, sb); 15428 sb.append(" used "); 15429 TimeUtils.formatDuration(cputimeUsed, sb); 15430 sb.append(" ("); 15431 sb.append((cputimeUsed*100)/uptimeSince); 15432 sb.append("%)"); 15433 Slog.i(TAG, sb.toString()); 15434 } 15435 // If a process has held a wake lock for more 15436 // than 50% of the time during this period, 15437 // that sounds bad. Kill! 15438 if (doWakeKills && realtimeSince > 0 15439 && ((wtimeUsed*100)/realtimeSince) >= 50) { 15440 synchronized (stats) { 15441 stats.reportExcessiveWakeLocked(app.info.uid, app.processName, 15442 realtimeSince, wtimeUsed); 15443 } 15444 killUnneededProcessLocked(app, "excessive wake held " + wtimeUsed 15445 + " during " + realtimeSince); 15446 app.baseProcessTracker.reportExcessiveWake(app.pkgList); 15447 } else if (doCpuKills && uptimeSince > 0 15448 && ((cputimeUsed*100)/uptimeSince) >= 50) { 15449 synchronized (stats) { 15450 stats.reportExcessiveCpuLocked(app.info.uid, app.processName, 15451 uptimeSince, cputimeUsed); 15452 } 15453 killUnneededProcessLocked(app, "excessive cpu " + cputimeUsed 15454 + " during " + uptimeSince); 15455 app.baseProcessTracker.reportExcessiveCpu(app.pkgList); 15456 } else { 15457 app.lastWakeTime = wtime; 15458 app.lastCpuTime = app.curCpuTime; 15459 } 15460 } 15461 } 15462 } 15463 15464 private final boolean applyOomAdjLocked(ProcessRecord app, boolean wasKeeping, 15465 ProcessRecord TOP_APP, boolean doingAll, long now) { 15466 boolean success = true; 15467 15468 if (app.curRawAdj != app.setRawAdj) { 15469 if (wasKeeping && !app.keeping) { 15470 // This app is no longer something we want to keep. Note 15471 // its current wake lock time to later know to kill it if 15472 // it is not behaving well. 15473 BatteryStatsImpl stats = mBatteryStatsService.getActiveStatistics(); 15474 synchronized (stats) { 15475 app.lastWakeTime = stats.getProcessWakeTime(app.info.uid, 15476 app.pid, SystemClock.elapsedRealtime()); 15477 } 15478 app.lastCpuTime = app.curCpuTime; 15479 } 15480 15481 app.setRawAdj = app.curRawAdj; 15482 } 15483 15484 int changes = 0; 15485 15486 if (app.curAdj != app.setAdj) { 15487 ProcessList.setOomAdj(app.pid, app.curAdj); 15488 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v( 15489 TAG, "Set " + app.pid + " " + app.processName + 15490 " adj " + app.curAdj + ": " + app.adjType); 15491 app.setAdj = app.curAdj; 15492 } 15493 15494 if (app.setSchedGroup != app.curSchedGroup) { 15495 app.setSchedGroup = app.curSchedGroup; 15496 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 15497 "Setting process group of " + app.processName 15498 + " to " + app.curSchedGroup); 15499 if (app.waitingToKill != null && 15500 app.setSchedGroup == Process.THREAD_GROUP_BG_NONINTERACTIVE) { 15501 killUnneededProcessLocked(app, app.waitingToKill); 15502 success = false; 15503 } else { 15504 if (true) { 15505 long oldId = Binder.clearCallingIdentity(); 15506 try { 15507 Process.setProcessGroup(app.pid, app.curSchedGroup); 15508 } catch (Exception e) { 15509 Slog.w(TAG, "Failed setting process group of " + app.pid 15510 + " to " + app.curSchedGroup); 15511 e.printStackTrace(); 15512 } finally { 15513 Binder.restoreCallingIdentity(oldId); 15514 } 15515 } else { 15516 if (app.thread != null) { 15517 try { 15518 app.thread.setSchedulingGroup(app.curSchedGroup); 15519 } catch (RemoteException e) { 15520 } 15521 } 15522 } 15523 Process.setSwappiness(app.pid, 15524 app.curSchedGroup <= Process.THREAD_GROUP_BG_NONINTERACTIVE); 15525 } 15526 } 15527 if (app.repForegroundActivities != app.foregroundActivities) { 15528 app.repForegroundActivities = app.foregroundActivities; 15529 changes |= ProcessChangeItem.CHANGE_ACTIVITIES; 15530 } 15531 if (app.repProcState != app.curProcState) { 15532 app.repProcState = app.curProcState; 15533 changes |= ProcessChangeItem.CHANGE_PROCESS_STATE; 15534 if (app.thread != null) { 15535 try { 15536 if (false) { 15537 //RuntimeException h = new RuntimeException("here"); 15538 Slog.i(TAG, "Sending new process state " + app.repProcState 15539 + " to " + app /*, h*/); 15540 } 15541 app.thread.setProcessState(app.repProcState); 15542 } catch (RemoteException e) { 15543 } 15544 } 15545 } 15546 if (app.setProcState < 0 || ProcessList.procStatesDifferForMem(app.curProcState, 15547 app.setProcState)) { 15548 app.lastStateTime = now; 15549 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, true, 15550 isSleeping(), now); 15551 if (DEBUG_PSS) Slog.d(TAG, "Process state change from " 15552 + ProcessList.makeProcStateString(app.setProcState) + " to " 15553 + ProcessList.makeProcStateString(app.curProcState) + " next pss in " 15554 + (app.nextPssTime-now) + ": " + app); 15555 } else { 15556 if (now > app.nextPssTime || (now > (app.lastPssTime+ProcessList.PSS_MAX_INTERVAL) 15557 && now > (app.lastStateTime+ProcessList.PSS_MIN_TIME_FROM_STATE_CHANGE))) { 15558 requestPssLocked(app, app.setProcState); 15559 app.nextPssTime = ProcessList.computeNextPssTime(app.curProcState, false, 15560 isSleeping(), now); 15561 } else if (false && DEBUG_PSS) { 15562 Slog.d(TAG, "Not requesting PSS of " + app + ": next=" + (app.nextPssTime-now)); 15563 } 15564 } 15565 if (app.setProcState != app.curProcState) { 15566 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 15567 "Proc state change of " + app.processName 15568 + " to " + app.curProcState); 15569 app.setProcState = app.curProcState; 15570 if (app.setProcState >= ActivityManager.PROCESS_STATE_HOME) { 15571 app.notCachedSinceIdle = false; 15572 } 15573 if (!doingAll) { 15574 setProcessTrackerState(app, mProcessStats.getMemFactorLocked(), now); 15575 } else { 15576 app.procStateChanged = true; 15577 } 15578 } 15579 15580 if (changes != 0) { 15581 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Changes in " + app + ": " + changes); 15582 int i = mPendingProcessChanges.size()-1; 15583 ProcessChangeItem item = null; 15584 while (i >= 0) { 15585 item = mPendingProcessChanges.get(i); 15586 if (item.pid == app.pid) { 15587 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Re-using existing item: " + item); 15588 break; 15589 } 15590 i--; 15591 } 15592 if (i < 0) { 15593 // No existing item in pending changes; need a new one. 15594 final int NA = mAvailProcessChanges.size(); 15595 if (NA > 0) { 15596 item = mAvailProcessChanges.remove(NA-1); 15597 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Retreiving available item: " + item); 15598 } else { 15599 item = new ProcessChangeItem(); 15600 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Allocating new item: " + item); 15601 } 15602 item.changes = 0; 15603 item.pid = app.pid; 15604 item.uid = app.info.uid; 15605 if (mPendingProcessChanges.size() == 0) { 15606 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, 15607 "*** Enqueueing dispatch processes changed!"); 15608 mHandler.obtainMessage(DISPATCH_PROCESSES_CHANGED).sendToTarget(); 15609 } 15610 mPendingProcessChanges.add(item); 15611 } 15612 item.changes |= changes; 15613 item.processState = app.repProcState; 15614 item.foregroundActivities = app.repForegroundActivities; 15615 if (DEBUG_PROCESS_OBSERVERS) Slog.i(TAG, "Item " 15616 + Integer.toHexString(System.identityHashCode(item)) 15617 + " " + app.toShortString() + ": changes=" + item.changes 15618 + " procState=" + item.processState 15619 + " foreground=" + item.foregroundActivities 15620 + " type=" + app.adjType + " source=" + app.adjSource 15621 + " target=" + app.adjTarget); 15622 } 15623 15624 return success; 15625 } 15626 15627 private final void setProcessTrackerState(ProcessRecord proc, int memFactor, long now) { 15628 if (proc.thread != null && proc.baseProcessTracker != null) { 15629 proc.baseProcessTracker.setState(proc.repProcState, memFactor, now, proc.pkgList); 15630 } 15631 } 15632 15633 private final boolean updateOomAdjLocked(ProcessRecord app, int cachedAdj, 15634 ProcessRecord TOP_APP, boolean doingAll, long now) { 15635 if (app.thread == null) { 15636 return false; 15637 } 15638 15639 final boolean wasKeeping = app.keeping; 15640 15641 computeOomAdjLocked(app, cachedAdj, TOP_APP, doingAll, now); 15642 15643 return applyOomAdjLocked(app, wasKeeping, TOP_APP, doingAll, now); 15644 } 15645 15646 final void updateProcessForegroundLocked(ProcessRecord proc, boolean isForeground, 15647 boolean oomAdj) { 15648 if (isForeground != proc.foregroundServices) { 15649 proc.foregroundServices = isForeground; 15650 ArrayList<ProcessRecord> curProcs = mForegroundPackages.get(proc.info.packageName, 15651 proc.info.uid); 15652 if (isForeground) { 15653 if (curProcs == null) { 15654 curProcs = new ArrayList<ProcessRecord>(); 15655 mForegroundPackages.put(proc.info.packageName, proc.info.uid, curProcs); 15656 } 15657 if (!curProcs.contains(proc)) { 15658 curProcs.add(proc); 15659 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_FOREGROUND_START, 15660 proc.info.packageName, proc.info.uid); 15661 } 15662 } else { 15663 if (curProcs != null) { 15664 if (curProcs.remove(proc)) { 15665 mBatteryStatsService.noteEvent( 15666 BatteryStats.HistoryItem.EVENT_FOREGROUND_FINISH, 15667 proc.info.packageName, proc.info.uid); 15668 if (curProcs.size() <= 0) { 15669 mForegroundPackages.remove(proc.info.packageName, proc.info.uid); 15670 } 15671 } 15672 } 15673 } 15674 if (oomAdj) { 15675 updateOomAdjLocked(); 15676 } 15677 } 15678 } 15679 15680 private final ActivityRecord resumedAppLocked() { 15681 ActivityRecord act = mStackSupervisor.resumedAppLocked(); 15682 String pkg; 15683 int uid; 15684 if (act != null && !act.sleeping) { 15685 pkg = act.packageName; 15686 uid = act.info.applicationInfo.uid; 15687 } else { 15688 pkg = null; 15689 uid = -1; 15690 } 15691 // Has the UID or resumed package name changed? 15692 if (uid != mCurResumedUid || (pkg != mCurResumedPackage 15693 && (pkg == null || !pkg.equals(mCurResumedPackage)))) { 15694 if (mCurResumedPackage != null) { 15695 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_FINISH, 15696 mCurResumedPackage, mCurResumedUid); 15697 } 15698 mCurResumedPackage = pkg; 15699 mCurResumedUid = uid; 15700 if (mCurResumedPackage != null) { 15701 mBatteryStatsService.noteEvent(BatteryStats.HistoryItem.EVENT_TOP_START, 15702 mCurResumedPackage, mCurResumedUid); 15703 } 15704 } 15705 return act; 15706 } 15707 15708 final boolean updateOomAdjLocked(ProcessRecord app) { 15709 final ActivityRecord TOP_ACT = resumedAppLocked(); 15710 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 15711 final boolean wasCached = app.cached; 15712 15713 mAdjSeq++; 15714 15715 // This is the desired cached adjusment we want to tell it to use. 15716 // If our app is currently cached, we know it, and that is it. Otherwise, 15717 // we don't know it yet, and it needs to now be cached we will then 15718 // need to do a complete oom adj. 15719 final int cachedAdj = app.curRawAdj >= ProcessList.CACHED_APP_MIN_ADJ 15720 ? app.curRawAdj : ProcessList.UNKNOWN_ADJ; 15721 boolean success = updateOomAdjLocked(app, cachedAdj, TOP_APP, false, 15722 SystemClock.uptimeMillis()); 15723 if (wasCached != app.cached || app.curRawAdj == ProcessList.UNKNOWN_ADJ) { 15724 // Changed to/from cached state, so apps after it in the LRU 15725 // list may also be changed. 15726 updateOomAdjLocked(); 15727 } 15728 return success; 15729 } 15730 15731 final void updateOomAdjLocked() { 15732 final ActivityRecord TOP_ACT = resumedAppLocked(); 15733 final ProcessRecord TOP_APP = TOP_ACT != null ? TOP_ACT.app : null; 15734 final long now = SystemClock.uptimeMillis(); 15735 final long oldTime = now - ProcessList.MAX_EMPTY_TIME; 15736 final int N = mLruProcesses.size(); 15737 15738 if (false) { 15739 RuntimeException e = new RuntimeException(); 15740 e.fillInStackTrace(); 15741 Slog.i(TAG, "updateOomAdj: top=" + TOP_ACT, e); 15742 } 15743 15744 mAdjSeq++; 15745 mNewNumServiceProcs = 0; 15746 mNewNumAServiceProcs = 0; 15747 15748 final int emptyProcessLimit; 15749 final int cachedProcessLimit; 15750 if (mProcessLimit <= 0) { 15751 emptyProcessLimit = cachedProcessLimit = 0; 15752 } else if (mProcessLimit == 1) { 15753 emptyProcessLimit = 1; 15754 cachedProcessLimit = 0; 15755 } else { 15756 emptyProcessLimit = ProcessList.computeEmptyProcessLimit(mProcessLimit); 15757 cachedProcessLimit = mProcessLimit - emptyProcessLimit; 15758 } 15759 15760 // Let's determine how many processes we have running vs. 15761 // how many slots we have for background processes; we may want 15762 // to put multiple processes in a slot of there are enough of 15763 // them. 15764 int numSlots = (ProcessList.CACHED_APP_MAX_ADJ 15765 - ProcessList.CACHED_APP_MIN_ADJ + 1) / 2; 15766 int numEmptyProcs = N - mNumNonCachedProcs - mNumCachedHiddenProcs; 15767 if (numEmptyProcs > cachedProcessLimit) { 15768 // If there are more empty processes than our limit on cached 15769 // processes, then use the cached process limit for the factor. 15770 // This ensures that the really old empty processes get pushed 15771 // down to the bottom, so if we are running low on memory we will 15772 // have a better chance at keeping around more cached processes 15773 // instead of a gazillion empty processes. 15774 numEmptyProcs = cachedProcessLimit; 15775 } 15776 int emptyFactor = numEmptyProcs/numSlots; 15777 if (emptyFactor < 1) emptyFactor = 1; 15778 int cachedFactor = (mNumCachedHiddenProcs > 0 ? mNumCachedHiddenProcs : 1)/numSlots; 15779 if (cachedFactor < 1) cachedFactor = 1; 15780 int stepCached = 0; 15781 int stepEmpty = 0; 15782 int numCached = 0; 15783 int numEmpty = 0; 15784 int numTrimming = 0; 15785 15786 mNumNonCachedProcs = 0; 15787 mNumCachedHiddenProcs = 0; 15788 15789 // First update the OOM adjustment for each of the 15790 // application processes based on their current state. 15791 int curCachedAdj = ProcessList.CACHED_APP_MIN_ADJ; 15792 int nextCachedAdj = curCachedAdj+1; 15793 int curEmptyAdj = ProcessList.CACHED_APP_MIN_ADJ; 15794 int nextEmptyAdj = curEmptyAdj+2; 15795 for (int i=N-1; i>=0; i--) { 15796 ProcessRecord app = mLruProcesses.get(i); 15797 if (!app.killedByAm && app.thread != null) { 15798 app.procStateChanged = false; 15799 final boolean wasKeeping = app.keeping; 15800 computeOomAdjLocked(app, ProcessList.UNKNOWN_ADJ, TOP_APP, true, now); 15801 15802 // If we haven't yet assigned the final cached adj 15803 // to the process, do that now. 15804 if (app.curAdj >= ProcessList.UNKNOWN_ADJ) { 15805 switch (app.curProcState) { 15806 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 15807 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 15808 // This process is a cached process holding activities... 15809 // assign it the next cached value for that type, and then 15810 // step that cached level. 15811 app.curRawAdj = curCachedAdj; 15812 app.curAdj = app.modifyRawOomAdj(curCachedAdj); 15813 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning activity LRU #" + i 15814 + " adj: " + app.curAdj + " (curCachedAdj=" + curCachedAdj 15815 + ")"); 15816 if (curCachedAdj != nextCachedAdj) { 15817 stepCached++; 15818 if (stepCached >= cachedFactor) { 15819 stepCached = 0; 15820 curCachedAdj = nextCachedAdj; 15821 nextCachedAdj += 2; 15822 if (nextCachedAdj > ProcessList.CACHED_APP_MAX_ADJ) { 15823 nextCachedAdj = ProcessList.CACHED_APP_MAX_ADJ; 15824 } 15825 } 15826 } 15827 break; 15828 default: 15829 // For everything else, assign next empty cached process 15830 // level and bump that up. Note that this means that 15831 // long-running services that have dropped down to the 15832 // cached level will be treated as empty (since their process 15833 // state is still as a service), which is what we want. 15834 app.curRawAdj = curEmptyAdj; 15835 app.curAdj = app.modifyRawOomAdj(curEmptyAdj); 15836 if (DEBUG_LRU && false) Slog.d(TAG, "Assigning empty LRU #" + i 15837 + " adj: " + app.curAdj + " (curEmptyAdj=" + curEmptyAdj 15838 + ")"); 15839 if (curEmptyAdj != nextEmptyAdj) { 15840 stepEmpty++; 15841 if (stepEmpty >= emptyFactor) { 15842 stepEmpty = 0; 15843 curEmptyAdj = nextEmptyAdj; 15844 nextEmptyAdj += 2; 15845 if (nextEmptyAdj > ProcessList.CACHED_APP_MAX_ADJ) { 15846 nextEmptyAdj = ProcessList.CACHED_APP_MAX_ADJ; 15847 } 15848 } 15849 } 15850 break; 15851 } 15852 } 15853 15854 applyOomAdjLocked(app, wasKeeping, TOP_APP, true, now); 15855 15856 // Count the number of process types. 15857 switch (app.curProcState) { 15858 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY: 15859 case ActivityManager.PROCESS_STATE_CACHED_ACTIVITY_CLIENT: 15860 mNumCachedHiddenProcs++; 15861 numCached++; 15862 if (numCached > cachedProcessLimit) { 15863 killUnneededProcessLocked(app, "cached #" + numCached); 15864 } 15865 break; 15866 case ActivityManager.PROCESS_STATE_CACHED_EMPTY: 15867 if (numEmpty > ProcessList.TRIM_EMPTY_APPS 15868 && app.lastActivityTime < oldTime) { 15869 killUnneededProcessLocked(app, "empty for " 15870 + ((oldTime + ProcessList.MAX_EMPTY_TIME - app.lastActivityTime) 15871 / 1000) + "s"); 15872 } else { 15873 numEmpty++; 15874 if (numEmpty > emptyProcessLimit) { 15875 killUnneededProcessLocked(app, "empty #" + numEmpty); 15876 } 15877 } 15878 break; 15879 default: 15880 mNumNonCachedProcs++; 15881 break; 15882 } 15883 15884 if (app.isolated && app.services.size() <= 0) { 15885 // If this is an isolated process, and there are no 15886 // services running in it, then the process is no longer 15887 // needed. We agressively kill these because we can by 15888 // definition not re-use the same process again, and it is 15889 // good to avoid having whatever code was running in them 15890 // left sitting around after no longer needed. 15891 killUnneededProcessLocked(app, "isolated not needed"); 15892 } 15893 15894 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 15895 && !app.killedByAm) { 15896 numTrimming++; 15897 } 15898 } 15899 } 15900 15901 mNumServiceProcs = mNewNumServiceProcs; 15902 15903 // Now determine the memory trimming level of background processes. 15904 // Unfortunately we need to start at the back of the list to do this 15905 // properly. We only do this if the number of background apps we 15906 // are managing to keep around is less than half the maximum we desire; 15907 // if we are keeping a good number around, we'll let them use whatever 15908 // memory they want. 15909 final int numCachedAndEmpty = numCached + numEmpty; 15910 int memFactor; 15911 if (numCached <= ProcessList.TRIM_CACHED_APPS 15912 && numEmpty <= ProcessList.TRIM_EMPTY_APPS) { 15913 if (numCachedAndEmpty <= ProcessList.TRIM_CRITICAL_THRESHOLD) { 15914 memFactor = ProcessStats.ADJ_MEM_FACTOR_CRITICAL; 15915 } else if (numCachedAndEmpty <= ProcessList.TRIM_LOW_THRESHOLD) { 15916 memFactor = ProcessStats.ADJ_MEM_FACTOR_LOW; 15917 } else { 15918 memFactor = ProcessStats.ADJ_MEM_FACTOR_MODERATE; 15919 } 15920 } else { 15921 memFactor = ProcessStats.ADJ_MEM_FACTOR_NORMAL; 15922 } 15923 // We always allow the memory level to go up (better). We only allow it to go 15924 // down if we are in a state where that is allowed, *and* the total number of processes 15925 // has gone down since last time. 15926 if (DEBUG_OOM_ADJ) Slog.d(TAG, "oom: memFactor=" + memFactor + " last=" + mLastMemoryLevel 15927 + " allowLow=" + mAllowLowerMemLevel + " numProcs=" + mLruProcesses.size() 15928 + " last=" + mLastNumProcesses); 15929 if (memFactor > mLastMemoryLevel) { 15930 if (!mAllowLowerMemLevel || mLruProcesses.size() >= mLastNumProcesses) { 15931 memFactor = mLastMemoryLevel; 15932 if (DEBUG_OOM_ADJ) Slog.d(TAG, "Keeping last mem factor!"); 15933 } 15934 } 15935 mLastMemoryLevel = memFactor; 15936 mLastNumProcesses = mLruProcesses.size(); 15937 boolean allChanged = mProcessStats.setMemFactorLocked(memFactor, !isSleeping(), now); 15938 final int trackerMemFactor = mProcessStats.getMemFactorLocked(); 15939 if (memFactor != ProcessStats.ADJ_MEM_FACTOR_NORMAL) { 15940 if (mLowRamStartTime == 0) { 15941 mLowRamStartTime = now; 15942 } 15943 int step = 0; 15944 int fgTrimLevel; 15945 switch (memFactor) { 15946 case ProcessStats.ADJ_MEM_FACTOR_CRITICAL: 15947 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_CRITICAL; 15948 break; 15949 case ProcessStats.ADJ_MEM_FACTOR_LOW: 15950 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_LOW; 15951 break; 15952 default: 15953 fgTrimLevel = ComponentCallbacks2.TRIM_MEMORY_RUNNING_MODERATE; 15954 break; 15955 } 15956 int factor = numTrimming/3; 15957 int minFactor = 2; 15958 if (mHomeProcess != null) minFactor++; 15959 if (mPreviousProcess != null) minFactor++; 15960 if (factor < minFactor) factor = minFactor; 15961 int curLevel = ComponentCallbacks2.TRIM_MEMORY_COMPLETE; 15962 for (int i=N-1; i>=0; i--) { 15963 ProcessRecord app = mLruProcesses.get(i); 15964 if (allChanged || app.procStateChanged) { 15965 setProcessTrackerState(app, trackerMemFactor, now); 15966 app.procStateChanged = false; 15967 } 15968 if (app.curProcState >= ActivityManager.PROCESS_STATE_HOME 15969 && !app.killedByAm) { 15970 if (app.trimMemoryLevel < curLevel && app.thread != null) { 15971 try { 15972 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 15973 "Trimming memory of " + app.processName 15974 + " to " + curLevel); 15975 app.thread.scheduleTrimMemory(curLevel); 15976 } catch (RemoteException e) { 15977 } 15978 if (false) { 15979 // For now we won't do this; our memory trimming seems 15980 // to be good enough at this point that destroying 15981 // activities causes more harm than good. 15982 if (curLevel >= ComponentCallbacks2.TRIM_MEMORY_COMPLETE 15983 && app != mHomeProcess && app != mPreviousProcess) { 15984 // Need to do this on its own message because the stack may not 15985 // be in a consistent state at this point. 15986 // For these apps we will also finish their activities 15987 // to help them free memory. 15988 mStackSupervisor.scheduleDestroyAllActivities(app, "trim"); 15989 } 15990 } 15991 } 15992 app.trimMemoryLevel = curLevel; 15993 step++; 15994 if (step >= factor) { 15995 step = 0; 15996 switch (curLevel) { 15997 case ComponentCallbacks2.TRIM_MEMORY_COMPLETE: 15998 curLevel = ComponentCallbacks2.TRIM_MEMORY_MODERATE; 15999 break; 16000 case ComponentCallbacks2.TRIM_MEMORY_MODERATE: 16001 curLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 16002 break; 16003 } 16004 } 16005 } else if (app.curProcState == ActivityManager.PROCESS_STATE_HEAVY_WEIGHT) { 16006 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_BACKGROUND 16007 && app.thread != null) { 16008 try { 16009 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16010 "Trimming memory of heavy-weight " + app.processName 16011 + " to " + ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 16012 app.thread.scheduleTrimMemory( 16013 ComponentCallbacks2.TRIM_MEMORY_BACKGROUND); 16014 } catch (RemoteException e) { 16015 } 16016 } 16017 app.trimMemoryLevel = ComponentCallbacks2.TRIM_MEMORY_BACKGROUND; 16018 } else { 16019 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 16020 || app.systemNoUi) && app.pendingUiClean) { 16021 // If this application is now in the background and it 16022 // had done UI, then give it the special trim level to 16023 // have it free UI resources. 16024 final int level = ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN; 16025 if (app.trimMemoryLevel < level && app.thread != null) { 16026 try { 16027 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16028 "Trimming memory of bg-ui " + app.processName 16029 + " to " + level); 16030 app.thread.scheduleTrimMemory(level); 16031 } catch (RemoteException e) { 16032 } 16033 } 16034 app.pendingUiClean = false; 16035 } 16036 if (app.trimMemoryLevel < fgTrimLevel && app.thread != null) { 16037 try { 16038 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16039 "Trimming memory of fg " + app.processName 16040 + " to " + fgTrimLevel); 16041 app.thread.scheduleTrimMemory(fgTrimLevel); 16042 } catch (RemoteException e) { 16043 } 16044 } 16045 app.trimMemoryLevel = fgTrimLevel; 16046 } 16047 } 16048 } else { 16049 if (mLowRamStartTime != 0) { 16050 mLowRamTimeSinceLastIdle += now - mLowRamStartTime; 16051 mLowRamStartTime = 0; 16052 } 16053 for (int i=N-1; i>=0; i--) { 16054 ProcessRecord app = mLruProcesses.get(i); 16055 if (allChanged || app.procStateChanged) { 16056 setProcessTrackerState(app, trackerMemFactor, now); 16057 app.procStateChanged = false; 16058 } 16059 if ((app.curProcState >= ActivityManager.PROCESS_STATE_IMPORTANT_BACKGROUND 16060 || app.systemNoUi) && app.pendingUiClean) { 16061 if (app.trimMemoryLevel < ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN 16062 && app.thread != null) { 16063 try { 16064 if (DEBUG_SWITCH || DEBUG_OOM_ADJ) Slog.v(TAG, 16065 "Trimming memory of ui hidden " + app.processName 16066 + " to " + ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 16067 app.thread.scheduleTrimMemory( 16068 ComponentCallbacks2.TRIM_MEMORY_UI_HIDDEN); 16069 } catch (RemoteException e) { 16070 } 16071 } 16072 app.pendingUiClean = false; 16073 } 16074 app.trimMemoryLevel = 0; 16075 } 16076 } 16077 16078 if (mAlwaysFinishActivities) { 16079 // Need to do this on its own message because the stack may not 16080 // be in a consistent state at this point. 16081 mStackSupervisor.scheduleDestroyAllActivities(null, "always-finish"); 16082 } 16083 16084 if (allChanged) { 16085 requestPssAllProcsLocked(now, false, mProcessStats.isMemFactorLowered()); 16086 } 16087 16088 if (mProcessStats.shouldWriteNowLocked(now)) { 16089 mHandler.post(new Runnable() { 16090 @Override public void run() { 16091 synchronized (ActivityManagerService.this) { 16092 mProcessStats.writeStateAsyncLocked(); 16093 } 16094 } 16095 }); 16096 } 16097 16098 if (DEBUG_OOM_ADJ) { 16099 Slog.d(TAG, "Did OOM ADJ in " + (SystemClock.uptimeMillis()-now) + "ms"); 16100 } 16101 } 16102 16103 final void trimApplications() { 16104 synchronized (this) { 16105 int i; 16106 16107 // First remove any unused application processes whose package 16108 // has been removed. 16109 for (i=mRemovedProcesses.size()-1; i>=0; i--) { 16110 final ProcessRecord app = mRemovedProcesses.get(i); 16111 if (app.activities.size() == 0 16112 && app.curReceiver == null && app.services.size() == 0) { 16113 Slog.i( 16114 TAG, "Exiting empty application process " 16115 + app.processName + " (" 16116 + (app.thread != null ? app.thread.asBinder() : null) 16117 + ")\n"); 16118 if (app.pid > 0 && app.pid != MY_PID) { 16119 EventLog.writeEvent(EventLogTags.AM_KILL, app.userId, app.pid, 16120 app.processName, app.setAdj, "empty"); 16121 app.killedByAm = true; 16122 Process.killProcessQuiet(app.pid); 16123 } else { 16124 try { 16125 app.thread.scheduleExit(); 16126 } catch (Exception e) { 16127 // Ignore exceptions. 16128 } 16129 } 16130 cleanUpApplicationRecordLocked(app, false, true, -1); 16131 mRemovedProcesses.remove(i); 16132 16133 if (app.persistent) { 16134 if (app.persistent) { 16135 addAppLocked(app.info, false); 16136 } 16137 } 16138 } 16139 } 16140 16141 // Now update the oom adj for all processes. 16142 updateOomAdjLocked(); 16143 } 16144 } 16145 16146 /** This method sends the specified signal to each of the persistent apps */ 16147 public void signalPersistentProcesses(int sig) throws RemoteException { 16148 if (sig != Process.SIGNAL_USR1) { 16149 throw new SecurityException("Only SIGNAL_USR1 is allowed"); 16150 } 16151 16152 synchronized (this) { 16153 if (checkCallingPermission(android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES) 16154 != PackageManager.PERMISSION_GRANTED) { 16155 throw new SecurityException("Requires permission " 16156 + android.Manifest.permission.SIGNAL_PERSISTENT_PROCESSES); 16157 } 16158 16159 for (int i = mLruProcesses.size() - 1 ; i >= 0 ; i--) { 16160 ProcessRecord r = mLruProcesses.get(i); 16161 if (r.thread != null && r.persistent) { 16162 Process.sendSignal(r.pid, sig); 16163 } 16164 } 16165 } 16166 } 16167 16168 private void stopProfilerLocked(ProcessRecord proc, String path, int profileType) { 16169 if (proc == null || proc == mProfileProc) { 16170 proc = mProfileProc; 16171 path = mProfileFile; 16172 profileType = mProfileType; 16173 clearProfilerLocked(); 16174 } 16175 if (proc == null) { 16176 return; 16177 } 16178 try { 16179 proc.thread.profilerControl(false, path, null, profileType); 16180 } catch (RemoteException e) { 16181 throw new IllegalStateException("Process disappeared"); 16182 } 16183 } 16184 16185 private void clearProfilerLocked() { 16186 if (mProfileFd != null) { 16187 try { 16188 mProfileFd.close(); 16189 } catch (IOException e) { 16190 } 16191 } 16192 mProfileApp = null; 16193 mProfileProc = null; 16194 mProfileFile = null; 16195 mProfileType = 0; 16196 mAutoStopProfiler = false; 16197 } 16198 16199 public boolean profileControl(String process, int userId, boolean start, 16200 String path, ParcelFileDescriptor fd, int profileType) throws RemoteException { 16201 16202 try { 16203 synchronized (this) { 16204 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 16205 // its own permission. 16206 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 16207 != PackageManager.PERMISSION_GRANTED) { 16208 throw new SecurityException("Requires permission " 16209 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 16210 } 16211 16212 if (start && fd == null) { 16213 throw new IllegalArgumentException("null fd"); 16214 } 16215 16216 ProcessRecord proc = null; 16217 if (process != null) { 16218 proc = findProcessLocked(process, userId, "profileControl"); 16219 } 16220 16221 if (start && (proc == null || proc.thread == null)) { 16222 throw new IllegalArgumentException("Unknown process: " + process); 16223 } 16224 16225 if (start) { 16226 stopProfilerLocked(null, null, 0); 16227 setProfileApp(proc.info, proc.processName, path, fd, false); 16228 mProfileProc = proc; 16229 mProfileType = profileType; 16230 try { 16231 fd = fd.dup(); 16232 } catch (IOException e) { 16233 fd = null; 16234 } 16235 proc.thread.profilerControl(start, path, fd, profileType); 16236 fd = null; 16237 mProfileFd = null; 16238 } else { 16239 stopProfilerLocked(proc, path, profileType); 16240 if (fd != null) { 16241 try { 16242 fd.close(); 16243 } catch (IOException e) { 16244 } 16245 } 16246 } 16247 16248 return true; 16249 } 16250 } catch (RemoteException e) { 16251 throw new IllegalStateException("Process disappeared"); 16252 } finally { 16253 if (fd != null) { 16254 try { 16255 fd.close(); 16256 } catch (IOException e) { 16257 } 16258 } 16259 } 16260 } 16261 16262 private ProcessRecord findProcessLocked(String process, int userId, String callName) { 16263 userId = handleIncomingUser(Binder.getCallingPid(), Binder.getCallingUid(), 16264 userId, true, true, callName, null); 16265 ProcessRecord proc = null; 16266 try { 16267 int pid = Integer.parseInt(process); 16268 synchronized (mPidsSelfLocked) { 16269 proc = mPidsSelfLocked.get(pid); 16270 } 16271 } catch (NumberFormatException e) { 16272 } 16273 16274 if (proc == null) { 16275 ArrayMap<String, SparseArray<ProcessRecord>> all 16276 = mProcessNames.getMap(); 16277 SparseArray<ProcessRecord> procs = all.get(process); 16278 if (procs != null && procs.size() > 0) { 16279 proc = procs.valueAt(0); 16280 if (userId != UserHandle.USER_ALL && proc.userId != userId) { 16281 for (int i=1; i<procs.size(); i++) { 16282 ProcessRecord thisProc = procs.valueAt(i); 16283 if (thisProc.userId == userId) { 16284 proc = thisProc; 16285 break; 16286 } 16287 } 16288 } 16289 } 16290 } 16291 16292 return proc; 16293 } 16294 16295 public boolean dumpHeap(String process, int userId, boolean managed, 16296 String path, ParcelFileDescriptor fd) throws RemoteException { 16297 16298 try { 16299 synchronized (this) { 16300 // note: hijacking SET_ACTIVITY_WATCHER, but should be changed to 16301 // its own permission (same as profileControl). 16302 if (checkCallingPermission(android.Manifest.permission.SET_ACTIVITY_WATCHER) 16303 != PackageManager.PERMISSION_GRANTED) { 16304 throw new SecurityException("Requires permission " 16305 + android.Manifest.permission.SET_ACTIVITY_WATCHER); 16306 } 16307 16308 if (fd == null) { 16309 throw new IllegalArgumentException("null fd"); 16310 } 16311 16312 ProcessRecord proc = findProcessLocked(process, userId, "dumpHeap"); 16313 if (proc == null || proc.thread == null) { 16314 throw new IllegalArgumentException("Unknown process: " + process); 16315 } 16316 16317 boolean isDebuggable = "1".equals(SystemProperties.get(SYSTEM_DEBUGGABLE, "0")); 16318 if (!isDebuggable) { 16319 if ((proc.info.flags&ApplicationInfo.FLAG_DEBUGGABLE) == 0) { 16320 throw new SecurityException("Process not debuggable: " + proc); 16321 } 16322 } 16323 16324 proc.thread.dumpHeap(managed, path, fd); 16325 fd = null; 16326 return true; 16327 } 16328 } catch (RemoteException e) { 16329 throw new IllegalStateException("Process disappeared"); 16330 } finally { 16331 if (fd != null) { 16332 try { 16333 fd.close(); 16334 } catch (IOException e) { 16335 } 16336 } 16337 } 16338 } 16339 16340 /** In this method we try to acquire our lock to make sure that we have not deadlocked */ 16341 public void monitor() { 16342 synchronized (this) { } 16343 } 16344 16345 void onCoreSettingsChange(Bundle settings) { 16346 for (int i = mLruProcesses.size() - 1; i >= 0; i--) { 16347 ProcessRecord processRecord = mLruProcesses.get(i); 16348 try { 16349 if (processRecord.thread != null) { 16350 processRecord.thread.setCoreSettings(settings); 16351 } 16352 } catch (RemoteException re) { 16353 /* ignore */ 16354 } 16355 } 16356 } 16357 16358 // Multi-user methods 16359 16360 /** 16361 * Start user, if its not already running, but don't bring it to foreground. 16362 */ 16363 @Override 16364 public boolean startUserInBackground(final int userId) { 16365 return startUser(userId, /* foreground */ false); 16366 } 16367 16368 /** 16369 * Refreshes the list of users related to the current user when either a 16370 * user switch happens or when a new related user is started in the 16371 * background. 16372 */ 16373 private void updateCurrentProfileIdsLocked() { 16374 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 16375 mCurrentUserId, false /* enabledOnly */); 16376 int[] currentProfileIds = new int[profiles.size()]; // profiles will not be null 16377 for (int i = 0; i < currentProfileIds.length; i++) { 16378 currentProfileIds[i] = profiles.get(i).id; 16379 } 16380 mCurrentProfileIds = currentProfileIds; 16381 } 16382 16383 private Set getProfileIdsLocked(int userId) { 16384 Set userIds = new HashSet<Integer>(); 16385 final List<UserInfo> profiles = getUserManagerLocked().getProfiles( 16386 userId, false /* enabledOnly */); 16387 for (UserInfo user : profiles) { 16388 userIds.add(Integer.valueOf(user.id)); 16389 } 16390 return userIds; 16391 } 16392 16393 @Override 16394 public boolean switchUser(final int userId) { 16395 return startUser(userId, /* foregound */ true); 16396 } 16397 16398 private boolean startUser(final int userId, boolean foreground) { 16399 if (checkCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS_FULL) 16400 != PackageManager.PERMISSION_GRANTED) { 16401 String msg = "Permission Denial: switchUser() from pid=" 16402 + Binder.getCallingPid() 16403 + ", uid=" + Binder.getCallingUid() 16404 + " requires " + android.Manifest.permission.INTERACT_ACROSS_USERS_FULL; 16405 Slog.w(TAG, msg); 16406 throw new SecurityException(msg); 16407 } 16408 16409 if (DEBUG_MU) Slog.i(TAG_MU, "starting userid:" + userId + " fore:" + foreground); 16410 16411 final long ident = Binder.clearCallingIdentity(); 16412 try { 16413 synchronized (this) { 16414 final int oldUserId = mCurrentUserId; 16415 if (oldUserId == userId) { 16416 return true; 16417 } 16418 16419 mStackSupervisor.setLockTaskModeLocked(null); 16420 16421 final UserInfo userInfo = getUserManagerLocked().getUserInfo(userId); 16422 if (userInfo == null) { 16423 Slog.w(TAG, "No user info for user #" + userId); 16424 return false; 16425 } 16426 16427 if (foreground) { 16428 mWindowManager.startFreezingScreen(R.anim.screen_user_exit, 16429 R.anim.screen_user_enter); 16430 } 16431 16432 boolean needStart = false; 16433 16434 // If the user we are switching to is not currently started, then 16435 // we need to start it now. 16436 if (mStartedUsers.get(userId) == null) { 16437 mStartedUsers.put(userId, new UserStartedState(new UserHandle(userId), false)); 16438 updateStartedUserArrayLocked(); 16439 needStart = true; 16440 } 16441 16442 final Integer userIdInt = Integer.valueOf(userId); 16443 mUserLru.remove(userIdInt); 16444 mUserLru.add(userIdInt); 16445 16446 if (foreground) { 16447 mCurrentUserId = userId; 16448 updateCurrentProfileIdsLocked(); 16449 mWindowManager.setCurrentUser(userId, mCurrentProfileIds); 16450 // Once the internal notion of the active user has switched, we lock the device 16451 // with the option to show the user switcher on the keyguard. 16452 mWindowManager.lockNow(null); 16453 } else { 16454 final Integer currentUserIdInt = Integer.valueOf(mCurrentUserId); 16455 updateCurrentProfileIdsLocked(); 16456 mWindowManager.setCurrentProfileIds(mCurrentProfileIds); 16457 mUserLru.remove(currentUserIdInt); 16458 mUserLru.add(currentUserIdInt); 16459 } 16460 16461 final UserStartedState uss = mStartedUsers.get(userId); 16462 16463 // Make sure user is in the started state. If it is currently 16464 // stopping, we need to knock that off. 16465 if (uss.mState == UserStartedState.STATE_STOPPING) { 16466 // If we are stopping, we haven't sent ACTION_SHUTDOWN, 16467 // so we can just fairly silently bring the user back from 16468 // the almost-dead. 16469 uss.mState = UserStartedState.STATE_RUNNING; 16470 updateStartedUserArrayLocked(); 16471 needStart = true; 16472 } else if (uss.mState == UserStartedState.STATE_SHUTDOWN) { 16473 // This means ACTION_SHUTDOWN has been sent, so we will 16474 // need to treat this as a new boot of the user. 16475 uss.mState = UserStartedState.STATE_BOOTING; 16476 updateStartedUserArrayLocked(); 16477 needStart = true; 16478 } 16479 16480 if (uss.mState == UserStartedState.STATE_BOOTING) { 16481 // Booting up a new user, need to tell system services about it. 16482 // Note that this is on the same handler as scheduling of broadcasts, 16483 // which is important because it needs to go first. 16484 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_START_MSG, userId)); 16485 } 16486 16487 if (foreground) { 16488 mHandler.sendMessage(mHandler.obtainMessage(SYSTEM_USER_CURRENT_MSG, userId)); 16489 mHandler.removeMessages(REPORT_USER_SWITCH_MSG); 16490 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 16491 mHandler.sendMessage(mHandler.obtainMessage(REPORT_USER_SWITCH_MSG, 16492 oldUserId, userId, uss)); 16493 mHandler.sendMessageDelayed(mHandler.obtainMessage(USER_SWITCH_TIMEOUT_MSG, 16494 oldUserId, userId, uss), USER_SWITCH_TIMEOUT); 16495 } 16496 16497 if (needStart) { 16498 Intent intent = new Intent(Intent.ACTION_USER_STARTED); 16499 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 16500 | Intent.FLAG_RECEIVER_FOREGROUND); 16501 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 16502 broadcastIntentLocked(null, null, intent, 16503 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 16504 false, false, MY_PID, Process.SYSTEM_UID, userId); 16505 } 16506 16507 if ((userInfo.flags&UserInfo.FLAG_INITIALIZED) == 0) { 16508 if (userId != 0) { 16509 Intent intent = new Intent(Intent.ACTION_USER_INITIALIZE); 16510 intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND); 16511 broadcastIntentLocked(null, null, intent, null, 16512 new IIntentReceiver.Stub() { 16513 public void performReceive(Intent intent, int resultCode, 16514 String data, Bundle extras, boolean ordered, 16515 boolean sticky, int sendingUser) { 16516 userInitialized(uss, userId); 16517 } 16518 }, 0, null, null, null, AppOpsManager.OP_NONE, 16519 true, false, MY_PID, Process.SYSTEM_UID, 16520 userId); 16521 uss.initializing = true; 16522 } else { 16523 getUserManagerLocked().makeInitialized(userInfo.id); 16524 } 16525 } 16526 16527 if (foreground) { 16528 boolean homeInFront = mStackSupervisor.switchUserLocked(userId, uss); 16529 if (homeInFront) { 16530 startHomeActivityLocked(userId); 16531 } else { 16532 mStackSupervisor.resumeTopActivitiesLocked(); 16533 } 16534 EventLogTags.writeAmSwitchUser(userId); 16535 getUserManagerLocked().userForeground(userId); 16536 sendUserSwitchBroadcastsLocked(oldUserId, userId); 16537 } 16538 16539 if (needStart) { 16540 Intent intent = new Intent(Intent.ACTION_USER_STARTING); 16541 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 16542 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 16543 broadcastIntentLocked(null, null, intent, 16544 null, new IIntentReceiver.Stub() { 16545 @Override 16546 public void performReceive(Intent intent, int resultCode, String data, 16547 Bundle extras, boolean ordered, boolean sticky, int sendingUser) 16548 throws RemoteException { 16549 } 16550 }, 0, null, null, 16551 android.Manifest.permission.INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 16552 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 16553 } 16554 } 16555 } finally { 16556 Binder.restoreCallingIdentity(ident); 16557 } 16558 16559 return true; 16560 } 16561 16562 void sendUserSwitchBroadcastsLocked(int oldUserId, int newUserId) { 16563 long ident = Binder.clearCallingIdentity(); 16564 try { 16565 Intent intent; 16566 if (oldUserId >= 0) { 16567 intent = new Intent(Intent.ACTION_USER_BACKGROUND); 16568 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 16569 | Intent.FLAG_RECEIVER_FOREGROUND); 16570 intent.putExtra(Intent.EXTRA_USER_HANDLE, oldUserId); 16571 broadcastIntentLocked(null, null, intent, 16572 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 16573 false, false, MY_PID, Process.SYSTEM_UID, oldUserId); 16574 } 16575 if (newUserId >= 0) { 16576 intent = new Intent(Intent.ACTION_USER_FOREGROUND); 16577 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 16578 | Intent.FLAG_RECEIVER_FOREGROUND); 16579 intent.putExtra(Intent.EXTRA_USER_HANDLE, newUserId); 16580 broadcastIntentLocked(null, null, intent, 16581 null, null, 0, null, null, null, AppOpsManager.OP_NONE, 16582 false, false, MY_PID, Process.SYSTEM_UID, newUserId); 16583 intent = new Intent(Intent.ACTION_USER_SWITCHED); 16584 intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY 16585 | Intent.FLAG_RECEIVER_FOREGROUND); 16586 intent.putExtra(Intent.EXTRA_USER_HANDLE, newUserId); 16587 broadcastIntentLocked(null, null, intent, 16588 null, null, 0, null, null, 16589 android.Manifest.permission.MANAGE_USERS, AppOpsManager.OP_NONE, 16590 false, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 16591 } 16592 } finally { 16593 Binder.restoreCallingIdentity(ident); 16594 } 16595 } 16596 16597 void dispatchUserSwitch(final UserStartedState uss, final int oldUserId, 16598 final int newUserId) { 16599 final int N = mUserSwitchObservers.beginBroadcast(); 16600 if (N > 0) { 16601 final IRemoteCallback callback = new IRemoteCallback.Stub() { 16602 int mCount = 0; 16603 @Override 16604 public void sendResult(Bundle data) throws RemoteException { 16605 synchronized (ActivityManagerService.this) { 16606 if (mCurUserSwitchCallback == this) { 16607 mCount++; 16608 if (mCount == N) { 16609 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 16610 } 16611 } 16612 } 16613 } 16614 }; 16615 synchronized (this) { 16616 uss.switching = true; 16617 mCurUserSwitchCallback = callback; 16618 } 16619 for (int i=0; i<N; i++) { 16620 try { 16621 mUserSwitchObservers.getBroadcastItem(i).onUserSwitching( 16622 newUserId, callback); 16623 } catch (RemoteException e) { 16624 } 16625 } 16626 } else { 16627 synchronized (this) { 16628 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 16629 } 16630 } 16631 mUserSwitchObservers.finishBroadcast(); 16632 } 16633 16634 void timeoutUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 16635 synchronized (this) { 16636 Slog.w(TAG, "User switch timeout: from " + oldUserId + " to " + newUserId); 16637 sendContinueUserSwitchLocked(uss, oldUserId, newUserId); 16638 } 16639 } 16640 16641 void sendContinueUserSwitchLocked(UserStartedState uss, int oldUserId, int newUserId) { 16642 mCurUserSwitchCallback = null; 16643 mHandler.removeMessages(USER_SWITCH_TIMEOUT_MSG); 16644 mHandler.sendMessage(mHandler.obtainMessage(CONTINUE_USER_SWITCH_MSG, 16645 oldUserId, newUserId, uss)); 16646 } 16647 16648 void userInitialized(UserStartedState uss, int newUserId) { 16649 completeSwitchAndInitalize(uss, newUserId, true, false); 16650 } 16651 16652 void continueUserSwitch(UserStartedState uss, int oldUserId, int newUserId) { 16653 completeSwitchAndInitalize(uss, newUserId, false, true); 16654 } 16655 16656 void completeSwitchAndInitalize(UserStartedState uss, int newUserId, 16657 boolean clearInitializing, boolean clearSwitching) { 16658 boolean unfrozen = false; 16659 synchronized (this) { 16660 if (clearInitializing) { 16661 uss.initializing = false; 16662 getUserManagerLocked().makeInitialized(uss.mHandle.getIdentifier()); 16663 } 16664 if (clearSwitching) { 16665 uss.switching = false; 16666 } 16667 if (!uss.switching && !uss.initializing) { 16668 mWindowManager.stopFreezingScreen(); 16669 unfrozen = true; 16670 } 16671 } 16672 if (unfrozen) { 16673 final int N = mUserSwitchObservers.beginBroadcast(); 16674 for (int i=0; i<N; i++) { 16675 try { 16676 mUserSwitchObservers.getBroadcastItem(i).onUserSwitchComplete(newUserId); 16677 } catch (RemoteException e) { 16678 } 16679 } 16680 mUserSwitchObservers.finishBroadcast(); 16681 } 16682 } 16683 16684 void scheduleStartProfilesLocked() { 16685 if (!mHandler.hasMessages(START_PROFILES_MSG)) { 16686 mHandler.sendMessageDelayed(mHandler.obtainMessage(START_PROFILES_MSG), 16687 DateUtils.SECOND_IN_MILLIS); 16688 } 16689 } 16690 16691 void startProfilesLocked() { 16692 if (DEBUG_MU) Slog.i(TAG_MU, "startProfilesLocked"); 16693 List<UserInfo> profiles = getUserManagerLocked().getProfiles( 16694 mCurrentUserId, false /* enabledOnly */); 16695 List<UserInfo> toStart = new ArrayList<UserInfo>(profiles.size()); 16696 for (UserInfo user : profiles) { 16697 if ((user.flags & UserInfo.FLAG_INITIALIZED) == UserInfo.FLAG_INITIALIZED 16698 && user.id != mCurrentUserId) { 16699 toStart.add(user); 16700 } 16701 } 16702 final int n = toStart.size(); 16703 int i = 0; 16704 for (; i < n && i < (MAX_RUNNING_USERS - 1); ++i) { 16705 startUserInBackground(toStart.get(i).id); 16706 } 16707 if (i < n) { 16708 Slog.w(TAG_MU, "More profiles than MAX_RUNNING_USERS"); 16709 } 16710 } 16711 16712 void finishUserSwitch(UserStartedState uss) { 16713 synchronized (this) { 16714 if (uss.mState == UserStartedState.STATE_BOOTING 16715 && mStartedUsers.get(uss.mHandle.getIdentifier()) == uss) { 16716 uss.mState = UserStartedState.STATE_RUNNING; 16717 final int userId = uss.mHandle.getIdentifier(); 16718 Intent intent = new Intent(Intent.ACTION_BOOT_COMPLETED, null); 16719 intent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 16720 intent.addFlags(Intent.FLAG_RECEIVER_NO_ABORT); 16721 broadcastIntentLocked(null, null, intent, 16722 null, null, 0, null, null, 16723 android.Manifest.permission.RECEIVE_BOOT_COMPLETED, AppOpsManager.OP_NONE, 16724 true, false, MY_PID, Process.SYSTEM_UID, userId); 16725 } 16726 16727 startProfilesLocked(); 16728 16729 int num = mUserLru.size(); 16730 int i = 0; 16731 while (num > MAX_RUNNING_USERS && i < mUserLru.size()) { 16732 Integer oldUserId = mUserLru.get(i); 16733 UserStartedState oldUss = mStartedUsers.get(oldUserId); 16734 if (oldUss == null) { 16735 // Shouldn't happen, but be sane if it does. 16736 mUserLru.remove(i); 16737 num--; 16738 continue; 16739 } 16740 if (oldUss.mState == UserStartedState.STATE_STOPPING 16741 || oldUss.mState == UserStartedState.STATE_SHUTDOWN) { 16742 // This user is already stopping, doesn't count. 16743 num--; 16744 i++; 16745 continue; 16746 } 16747 if (oldUserId == UserHandle.USER_OWNER || oldUserId == mCurrentUserId) { 16748 // Owner and current can't be stopped, but count as running. 16749 i++; 16750 continue; 16751 } 16752 // This is a user to be stopped. 16753 stopUserLocked(oldUserId, null); 16754 num--; 16755 i++; 16756 } 16757 } 16758 } 16759 16760 @Override 16761 public int stopUser(final int userId, final IStopUserCallback callback) { 16762 if (checkCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS_FULL) 16763 != PackageManager.PERMISSION_GRANTED) { 16764 String msg = "Permission Denial: switchUser() from pid=" 16765 + Binder.getCallingPid() 16766 + ", uid=" + Binder.getCallingUid() 16767 + " requires " + android.Manifest.permission.INTERACT_ACROSS_USERS_FULL; 16768 Slog.w(TAG, msg); 16769 throw new SecurityException(msg); 16770 } 16771 if (userId <= 0) { 16772 throw new IllegalArgumentException("Can't stop primary user " + userId); 16773 } 16774 synchronized (this) { 16775 return stopUserLocked(userId, callback); 16776 } 16777 } 16778 16779 private int stopUserLocked(final int userId, final IStopUserCallback callback) { 16780 if (DEBUG_MU) Slog.i(TAG_MU, "stopUserLocked userId=" + userId); 16781 if (mCurrentUserId == userId) { 16782 return ActivityManager.USER_OP_IS_CURRENT; 16783 } 16784 16785 final UserStartedState uss = mStartedUsers.get(userId); 16786 if (uss == null) { 16787 // User is not started, nothing to do... but we do need to 16788 // callback if requested. 16789 if (callback != null) { 16790 mHandler.post(new Runnable() { 16791 @Override 16792 public void run() { 16793 try { 16794 callback.userStopped(userId); 16795 } catch (RemoteException e) { 16796 } 16797 } 16798 }); 16799 } 16800 return ActivityManager.USER_OP_SUCCESS; 16801 } 16802 16803 if (callback != null) { 16804 uss.mStopCallbacks.add(callback); 16805 } 16806 16807 if (uss.mState != UserStartedState.STATE_STOPPING 16808 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 16809 uss.mState = UserStartedState.STATE_STOPPING; 16810 updateStartedUserArrayLocked(); 16811 16812 long ident = Binder.clearCallingIdentity(); 16813 try { 16814 // We are going to broadcast ACTION_USER_STOPPING and then 16815 // once that is done send a final ACTION_SHUTDOWN and then 16816 // stop the user. 16817 final Intent stoppingIntent = new Intent(Intent.ACTION_USER_STOPPING); 16818 stoppingIntent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY); 16819 stoppingIntent.putExtra(Intent.EXTRA_USER_HANDLE, userId); 16820 stoppingIntent.putExtra(Intent.EXTRA_SHUTDOWN_USERSPACE_ONLY, true); 16821 final Intent shutdownIntent = new Intent(Intent.ACTION_SHUTDOWN); 16822 // This is the result receiver for the final shutdown broadcast. 16823 final IIntentReceiver shutdownReceiver = new IIntentReceiver.Stub() { 16824 @Override 16825 public void performReceive(Intent intent, int resultCode, String data, 16826 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 16827 finishUserStop(uss); 16828 } 16829 }; 16830 // This is the result receiver for the initial stopping broadcast. 16831 final IIntentReceiver stoppingReceiver = new IIntentReceiver.Stub() { 16832 @Override 16833 public void performReceive(Intent intent, int resultCode, String data, 16834 Bundle extras, boolean ordered, boolean sticky, int sendingUser) { 16835 // On to the next. 16836 synchronized (ActivityManagerService.this) { 16837 if (uss.mState != UserStartedState.STATE_STOPPING) { 16838 // Whoops, we are being started back up. Abort, abort! 16839 return; 16840 } 16841 uss.mState = UserStartedState.STATE_SHUTDOWN; 16842 } 16843 mSystemServiceManager.stopUser(userId); 16844 broadcastIntentLocked(null, null, shutdownIntent, 16845 null, shutdownReceiver, 0, null, null, null, AppOpsManager.OP_NONE, 16846 true, false, MY_PID, Process.SYSTEM_UID, userId); 16847 } 16848 }; 16849 // Kick things off. 16850 broadcastIntentLocked(null, null, stoppingIntent, 16851 null, stoppingReceiver, 0, null, null, 16852 android.Manifest.permission.INTERACT_ACROSS_USERS, AppOpsManager.OP_NONE, 16853 true, false, MY_PID, Process.SYSTEM_UID, UserHandle.USER_ALL); 16854 } finally { 16855 Binder.restoreCallingIdentity(ident); 16856 } 16857 } 16858 16859 return ActivityManager.USER_OP_SUCCESS; 16860 } 16861 16862 void finishUserStop(UserStartedState uss) { 16863 final int userId = uss.mHandle.getIdentifier(); 16864 boolean stopped; 16865 ArrayList<IStopUserCallback> callbacks; 16866 synchronized (this) { 16867 callbacks = new ArrayList<IStopUserCallback>(uss.mStopCallbacks); 16868 if (mStartedUsers.get(userId) != uss) { 16869 stopped = false; 16870 } else if (uss.mState != UserStartedState.STATE_SHUTDOWN) { 16871 stopped = false; 16872 } else { 16873 stopped = true; 16874 // User can no longer run. 16875 mStartedUsers.remove(userId); 16876 mUserLru.remove(Integer.valueOf(userId)); 16877 updateStartedUserArrayLocked(); 16878 16879 // Clean up all state and processes associated with the user. 16880 // Kill all the processes for the user. 16881 forceStopUserLocked(userId, "finish user"); 16882 } 16883 } 16884 16885 for (int i=0; i<callbacks.size(); i++) { 16886 try { 16887 if (stopped) callbacks.get(i).userStopped(userId); 16888 else callbacks.get(i).userStopAborted(userId); 16889 } catch (RemoteException e) { 16890 } 16891 } 16892 16893 if (stopped) { 16894 mSystemServiceManager.cleanupUser(userId); 16895 synchronized (this) { 16896 mStackSupervisor.removeUserLocked(userId); 16897 } 16898 } 16899 } 16900 16901 @Override 16902 public UserInfo getCurrentUser() { 16903 if ((checkCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS) 16904 != PackageManager.PERMISSION_GRANTED) && ( 16905 checkCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS_FULL) 16906 != PackageManager.PERMISSION_GRANTED)) { 16907 String msg = "Permission Denial: getCurrentUser() from pid=" 16908 + Binder.getCallingPid() 16909 + ", uid=" + Binder.getCallingUid() 16910 + " requires " + android.Manifest.permission.INTERACT_ACROSS_USERS; 16911 Slog.w(TAG, msg); 16912 throw new SecurityException(msg); 16913 } 16914 synchronized (this) { 16915 return getUserManagerLocked().getUserInfo(mCurrentUserId); 16916 } 16917 } 16918 16919 int getCurrentUserIdLocked() { 16920 return mCurrentUserId; 16921 } 16922 16923 @Override 16924 public boolean isUserRunning(int userId, boolean orStopped) { 16925 if (checkCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS) 16926 != PackageManager.PERMISSION_GRANTED) { 16927 String msg = "Permission Denial: isUserRunning() from pid=" 16928 + Binder.getCallingPid() 16929 + ", uid=" + Binder.getCallingUid() 16930 + " requires " + android.Manifest.permission.INTERACT_ACROSS_USERS; 16931 Slog.w(TAG, msg); 16932 throw new SecurityException(msg); 16933 } 16934 synchronized (this) { 16935 return isUserRunningLocked(userId, orStopped); 16936 } 16937 } 16938 16939 boolean isUserRunningLocked(int userId, boolean orStopped) { 16940 UserStartedState state = mStartedUsers.get(userId); 16941 if (state == null) { 16942 return false; 16943 } 16944 if (orStopped) { 16945 return true; 16946 } 16947 return state.mState != UserStartedState.STATE_STOPPING 16948 && state.mState != UserStartedState.STATE_SHUTDOWN; 16949 } 16950 16951 @Override 16952 public int[] getRunningUserIds() { 16953 if (checkCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS) 16954 != PackageManager.PERMISSION_GRANTED) { 16955 String msg = "Permission Denial: isUserRunning() from pid=" 16956 + Binder.getCallingPid() 16957 + ", uid=" + Binder.getCallingUid() 16958 + " requires " + android.Manifest.permission.INTERACT_ACROSS_USERS; 16959 Slog.w(TAG, msg); 16960 throw new SecurityException(msg); 16961 } 16962 synchronized (this) { 16963 return mStartedUserArray; 16964 } 16965 } 16966 16967 private void updateStartedUserArrayLocked() { 16968 int num = 0; 16969 for (int i=0; i<mStartedUsers.size(); i++) { 16970 UserStartedState uss = mStartedUsers.valueAt(i); 16971 // This list does not include stopping users. 16972 if (uss.mState != UserStartedState.STATE_STOPPING 16973 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 16974 num++; 16975 } 16976 } 16977 mStartedUserArray = new int[num]; 16978 num = 0; 16979 for (int i=0; i<mStartedUsers.size(); i++) { 16980 UserStartedState uss = mStartedUsers.valueAt(i); 16981 if (uss.mState != UserStartedState.STATE_STOPPING 16982 && uss.mState != UserStartedState.STATE_SHUTDOWN) { 16983 mStartedUserArray[num] = mStartedUsers.keyAt(i); 16984 num++; 16985 } 16986 } 16987 } 16988 16989 @Override 16990 public void registerUserSwitchObserver(IUserSwitchObserver observer) { 16991 if (checkCallingPermission(android.Manifest.permission.INTERACT_ACROSS_USERS_FULL) 16992 != PackageManager.PERMISSION_GRANTED) { 16993 String msg = "Permission Denial: registerUserSwitchObserver() from pid=" 16994 + Binder.getCallingPid() 16995 + ", uid=" + Binder.getCallingUid() 16996 + " requires " + android.Manifest.permission.INTERACT_ACROSS_USERS_FULL; 16997 Slog.w(TAG, msg); 16998 throw new SecurityException(msg); 16999 } 17000 17001 mUserSwitchObservers.register(observer); 17002 } 17003 17004 @Override 17005 public void unregisterUserSwitchObserver(IUserSwitchObserver observer) { 17006 mUserSwitchObservers.unregister(observer); 17007 } 17008 17009 private boolean userExists(int userId) { 17010 if (userId == 0) { 17011 return true; 17012 } 17013 UserManagerService ums = getUserManagerLocked(); 17014 return ums != null ? (ums.getUserInfo(userId) != null) : false; 17015 } 17016 17017 int[] getUsersLocked() { 17018 UserManagerService ums = getUserManagerLocked(); 17019 return ums != null ? ums.getUserIds() : new int[] { 0 }; 17020 } 17021 17022 UserManagerService getUserManagerLocked() { 17023 if (mUserManager == null) { 17024 IBinder b = ServiceManager.getService(Context.USER_SERVICE); 17025 mUserManager = (UserManagerService)IUserManager.Stub.asInterface(b); 17026 } 17027 return mUserManager; 17028 } 17029 17030 private int applyUserId(int uid, int userId) { 17031 return UserHandle.getUid(userId, uid); 17032 } 17033 17034 ApplicationInfo getAppInfoForUser(ApplicationInfo info, int userId) { 17035 if (info == null) return null; 17036 ApplicationInfo newInfo = new ApplicationInfo(info); 17037 newInfo.uid = applyUserId(info.uid, userId); 17038 newInfo.dataDir = USER_DATA_DIR + userId + "/" 17039 + info.packageName; 17040 return newInfo; 17041 } 17042 17043 ActivityInfo getActivityInfoForUser(ActivityInfo aInfo, int userId) { 17044 if (aInfo == null 17045 || (userId < 1 && aInfo.applicationInfo.uid < UserHandle.PER_USER_RANGE)) { 17046 return aInfo; 17047 } 17048 17049 ActivityInfo info = new ActivityInfo(aInfo); 17050 info.applicationInfo = getAppInfoForUser(info.applicationInfo, userId); 17051 return info; 17052 } 17053 17054 private final class LocalService extends ActivityManagerInternal { 17055 @Override 17056 public void goingToSleep() { 17057 ActivityManagerService.this.goingToSleep(); 17058 } 17059 17060 @Override 17061 public void wakingUp() { 17062 ActivityManagerService.this.wakingUp(); 17063 } 17064 } 17065} 17066